WCF服务-调用客户端以使用json访问其余对象未提供正确的内容类型 [英] WCF Service - calling a client to access rest using json is not giving correct content type

查看:113
本文介绍了WCF服务-调用客户端以使用json访问其余对象未提供正确的内容类型的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我遇到了一个问题(我已经将自己的头发拔了好几天),因此我试图使用WCF服务来调用另一个RESTful服务.

i have an issue (of which i've been pulling my hair out for a number of days) whereby I'm attempting to use a WCF service to call another RESTful service.

但是,当通过它进行跟踪时,无法在消息上放置正确的json内容类型.

however, when tracing this through it fails to put the correct json content type on the message.

客户端中的呼叫示例(这是在调用代码的WCF服务中)

example of call in client (this is within a WCF service which calls the code)

[AspNetCompatibilityRequirements(RequirementsMode = AspNetCompatibilityRequirementsMode.Allowed)]
[ServiceBehavior()]
public partial class MyRestServiceClient : System.ServiceModel.ClientBase<IMyRestService>, IMyRestService
{
    [WebInvoke(Method = "POST", UriTemplate = "/MyService/ReferenceTypes.json", RequestFormat = WebMessageFormat.Json)]
    public MyServiceLists GetReferenceTypes()
    {
        try
        {
            return base.Channel.GetReferenceTypes();
        }
        catch (Exception e)
        {
            throw e; //throws exception here - method not allowed 
        }
    }
}

不是放置application/json的内容类型,而是放置application/xml到调用中.这是从进行呼叫的WCF服务上进行的活动跟踪中得出的. 活动日志中已发送消息"信息的示例:

Instead of putting content type of application/json it places application/xml instead to the call. this was worked out from the activity tracing placed on the WCF service doing the call. example of the "message sent" info from Activity log:

<E2ETraceEvent xmlns="http://schemas.microsoft.com/2004/06/E2ETraceEvent">
<System xmlns="http://schemas.microsoft.com/2004/06/windows/eventlog/system">
<EventID>262164</EventID>
<Type>3</Type>
<SubType Name="Information">0</SubType>
<Level>8</Level>
<TimeCreated SystemTime="2012-03-05T12:26:52.8913972Z" />
<Source Name="System.ServiceModel" />
<Correlation ActivityID="{7759c13c-972d-46a2-8048-2dcaf1c066bf}" />
<Execution ProcessName="aspnet_wp" ProcessID="2408" ThreadID="11" />
<Channel />
<Computer>Z1020734</Computer>
</System>
<ApplicationData>
<TraceData>
<DataItem>
<TraceRecord xmlns="http://schemas.microsoft.com/2004/10/E2ETraceEvent/TraceRecord" Severity="Information">
<TraceIdentifier>http://msdn.microsoft.com/en-GB/library/System.ServiceModel.Channels.MessageSent.aspx</TraceIdentifier>
<Description>Sent a message over a channel.</Description>
<AppDomain>/LM/w3svc/1/ROOT/My.Services-2-129754240054859056</AppDomain>
<Source>System.ServiceModel.Channels.HttpOutput+WebRequestHttpOutput/18905726</Source>
<ExtendedData xmlns="http://schemas.microsoft.com/2006/08/ServiceModel/MessageTraceRecord">
<MessageProperties>
**<Encoder>application/xml; charset=utf-8</Encoder>**
<AllowOutputBatching>False</AllowOutputBatching>
<Via>http://mymachine/My.services.stub.REST/</Via>
</MessageProperties>
<MessageHeaders></MessageHeaders>
</ExtendedData>
</TraceRecord>
</DataItem>
</TraceData>
</ApplicationData>
</E2ETraceEvent>

我已经为客户端使用了webHttpBinding,然后我也尝试了使用自定义Web内容类型映射器的自定义绑定等效项,该映射器强制Json内容类型无效.

I have used a webHttpBinding for the client, then i've also tried the custom binding equivalent with a custom web content type mapper that forces a Json content type to no avail.

客户端端点指向同一台机器上的Restful服务(使用Rest 40模板). 有关尝试调用Rest终结点的WCf服务的web.config,请参见下面的内容:

the client end point is pointing to a Restful service (using the Rest 40 template) on the same machine. see below for web.config of the WCf service that is trying to call the Rest endpoint:

<?xml version="1.0"?>
<configuration>
  <connectionStrings>
  </connectionStrings>
  <appSettings>
  </appSettings>
  <system.webServer>
    <modules runAllManagedModulesForAllRequests="true"/>
  </system.webServer>
  <system.serviceModel>
    <serviceHostingEnvironment  multipleSiteBindingsEnabled="true"/>
    <services>
      <service name="My.Services.MyService" behaviorConfiguration="My.Services.MyServiceBehavior" >
        <endpoint address="" binding="customBinding" bindingConfiguration="CustomBinding_IMyService" contract="My.Common.ServiceContracts.IMyService"/>
       </service>
      <service name="My.Services.SomeOtherService" behaviorConfiguration="My.Services.SomeOtherBehavior" >
        <endpoint address="" binding="customBinding"  bindingConfiguration="customBinding_ISomeOtherService" contract="My.Common.ServiceContracts.ISomeOtherService"/>
      </service>
    </services>
    <bindings>
      <webHttpBinding>
        <binding name="webHttpCustomBinding">
          <security mode="TransportCredentialOnly">
            <transport proxyCredentialType="None" clientCredentialType="Windows">
            </transport>
          </security>
        </binding>
      </webHttpBinding>

      <customBinding>
        <binding name ="CustomBinding_IIMyRestService">
           <webMessageEncoding webContentTypeMapperType="My.Common.ServiceModel.JsonContentTypeMapper, My.Common" ></webMessageEncoding>
          <httpTransport  authenticationScheme="Negotiate" ></httpTransport>
         </binding>
        <binding name="CustomBinding_IMyService">
          <textMessageEncoding messageVersion="Soap12" />
          <httpTransport maxBufferPoolSize="1000000" maxReceivedMessageSize="1000000"
            authenticationScheme="Negotiate" maxBufferSize="1000000"   />
        </binding>
        <binding name="customBinding_ISomeOtherService">
          <textMessageEncoding messageVersion="Soap12" />
          <httpTransport  />
        </binding>
      </customBinding>
    </bindings>
    <client>
      <endpoint address="http://MyMachine/My.services.stub.REST/" binding="customBinding" bindingConfiguration="CustomBinding_IMyRestService" name="RestService" contract="My.Common.ServiceContracts.IIMyRestService" behaviorConfiguration="webhttp"/>
 </client>
    <behaviors>
      <endpointBehaviors>
        <behavior name="webhttp">
        </behavior>
 </endpointBehaviors>
      <serviceBehaviors>
        <behavior name="My.Services.MyServiceBehavior">
          <serviceMetadata httpGetEnabled="false" httpsGetEnabled="false" />
          <serviceDebug includeExceptionDetailInFaults="true" />
        </behavior>
        <behavior name="My.Services.SomeOtherServiceBehavior">
          <serviceMetadata httpGetEnabled="true" httpsGetEnabled="true" />
          <serviceDebug includeExceptionDetailInFaults="true" />
        </behavior>
      </serviceBehaviors>
    </behaviors>
  </system.serviceModel>
  <system.net>
    <defaultProxy useDefaultCredentials="true"/>
  </system.net>
 <system.diagnostics>
    <trace autoflush="true"/>
    <sources>
      <source name="System.ServiceModel" switchValue="Information, ActivityTracing" propagateActivity="true">
        <listeners>
          <add name="sdt" type="System.Diagnostics.XmlWriterTraceListener" initializeData="c:\temp\my.Services.svclog"/>
        </listeners>
      </source>
    </sources>
  </system.diagnostics> 
  <system.web>
    <compilation debug="true" targetFramework="4.0" />
  </system.web>
</configuration>

注意:我用相同的功能和配置编写的控制台应用程序确实可以正常工作,并提供了正确的内容类型.

Note: a console app i've written with the same function and config does work correctly, and gives the correct content type.

感谢您能提供的任何帮助.

Any help you can give is appreciated.

推荐答案

不确定您是否已解决此问题,但我遇到了同样的问题.
从现有服务调用中调用服务时,需要将新调用包装在新的OperationContextScope中.

Not sure if you have gotten this resolved yet, but I ran into the same issue.
When calling a service from within an existing service call, you need to wrap the new call in a new OperationContextScope.

您可以在此处查看详细信息: WCF Rest Client发送不正确的内容类型

You can see the details here: WCF Rest Client sending incorrect content-type

这篇关于WCF服务-调用客户端以使用json访问其余对象未提供正确的内容类型的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆