大WCF Web服务请求失败(400)HTTP错误请求

问题描述:

我遇到了这个显然常见的问题,并且无法解决它。大WCF Web服务请求失败(400)HTTP错误请求

如果我用一个数组参数中相对较少数量的项目调用我的WCF Web服务(我测试了50个),一切都很好。

但是,如果我用500个项目调用Web服务,我会收到错误的请求错误。

有趣的是,我在服务器上运行了Wireshark,看起来该请求甚至没有到达服务器 - 客户端正在生成400错误。

唯一的例外是:

System.ServiceModel.ProtocolException: The remote server returned an unexpected response: (400) Bad Request. ---> System.Net.WebException: The remote server returned an error: (400) Bad Request. 

我的客户端配置文件的system.serviceModel部分是:

<system.serviceModel> 
    <bindings> 
     <wsHttpBinding> 
      <binding name="WSHttpBinding_IMyService" closeTimeout="00:01:00" 
       openTimeout="00:01:00" receiveTimeout="00:10:00" sendTimeout="00:01:00" 
       bypassProxyOnLocal="false" transactionFlow="false" hostNameComparisonMode="StrongWildcard" 
       maxBufferPoolSize="524288" maxReceivedMessageSize="2147483647" 
       messageEncoding="Text" textEncoding="utf-8" useDefaultWebProxy="true" 
       allowCookies="false"> 
       <readerQuotas maxDepth="32" maxStringContentLength="8192" maxArrayLength="2147483647" 
        maxBytesPerRead="4096" maxNameTableCharCount="16384" /> 
       <reliableSession ordered="true" inactivityTimeout="00:10:00" 
        enabled="false" /> 
       <security mode="None"> 
        <transport clientCredentialType="Windows" proxyCredentialType="None" 
         realm="" /> 
        <message clientCredentialType="Windows" negotiateServiceCredential="true" 
         establishSecurityContext="true" /> 
       </security> 
      </binding> 
     </wsHttpBinding> 
    </bindings> 
    <client> 
     <endpoint address="http://serviceserver/MyService.svc" 
      binding="wsHttpBinding" bindingConfiguration="WSHttpBinding_IMyService" 
      contract="SmsSendingService.IMyService" name="WSHttpBinding_IMyService" /> 
    </client> 
</system.serviceModel> 

在服务器端,我的web.config文件中有如下system.serviceModel栏目:

<system.serviceModel> 
    <services> 
     <service name="MyService.MyService" behaviorConfiguration="MyService.MyServiceBehaviour" > 
      <endpoint address="" binding="wsHttpBinding" bindingConfiguration="MyService.MyServiceBinding" contract="MyService.IMyService"> 
      </endpoint> 
      <endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange"/> 
     </service> 
    </services> 
    <bindings> 
     <wsHttpBinding> 
     <binding name="MyService.MyServiceBinding"> 
      <security mode="None"></security> 
     </binding> 
     </wsHttpBinding> 
    </bindings> 
    <behaviors> 
     <serviceBehaviors> 
      <behavior name="MyService.MyServiceBehaviour"> 
       <!-- To avoid disclosing metadata information, set the value below to false and remove the metadata endpoint above before deployment --> 
       <serviceMetadata httpGetEnabled="true"/> 
       <!-- To receive exception details in faults for debugging purposes, set the value below to true. Set to false before deployment to avoid disclosing exception information --> 
       <serviceDebug includeExceptionDetailInFaults="true"/> 
      </behavior> 
     </serviceBehaviors> 
    </behaviors> 
</system.serviceModel> 

我已经looked atanswers一个fairly largenumberthis questionno success

任何人都可以帮助我吗?

+0

如果它没有打到服务器,可能是发送的数据有问题。也许请求中有一些非法字符?此外,假设这是SOAP – 2009-04-24 05:26:15

+1

所以你已经尝试将所有'最大'属性(例如.maxReceivedMessageSize ...)设置为一个非常高的数字? – mundeep 2009-04-24 05:26:36

+0

是的,它是SOAP。请求中不应该有任何错误 - 正如我所说的,对于多达50个使用相同应用程序生成的元素,一切正常...... – Damovisa 2009-04-24 05:27:49

尝试在服务器上设置maxReceivedMessageSize,例如,到4MB:

<binding name="MyService.MyServiceBinding" 
      maxReceivedMessageSize="4194304"> 

的主要原因默认(65535我相信)是如此之低,是减少服务(DoS)攻击拒绝的风险。您需要将其设置为大于服务器上的最大请求大小以及客户端上的最大响应大小。如果您处于Intranet环境中,DoS攻击的风险可能很低,因此使用比您预期的要高得多的值可能是安全的。

顺便说一句,用于连接到WCF服务解决问题的一些提示:

  • this MSDN article描述在服务器上启用跟踪。

  • 在客户端上使用HTTP调试工具(如Fiddler)检查HTTP流量。

+1

令人惊叹 - 就是这样。 谢谢你的答复! – Damovisa 2009-04-24 06:06:59

+2

感谢您启用追踪的链接! – 2009-08-27 20:04:04

对于调试客户端,关闭Tools \ Options \ Debugging \ General \'Enable Just My Code',点击Debug \ Exceptions \'捕获所有首次机会异常'来管理CLR异常可能很有用,如果在协议例外之前和消息触及连线之前,客户端内部存在异常情况。 (我的猜测是某种序列化失败。)

+0

我会给它一个去,谢谢:) – Damovisa 2009-04-24 05:41:55

我也收到此问题但还没有一个很长的时间挖我找到了答案在这里之后,我的工作,因为我是使用自定义绑定(用于BinaryXML)以上的: -

Sending large XML from Silverlight to WCF

作为正在使用customBinding,所述maxReceivedMessageSize必须在web.config装订元件下httpTransport元素上设置:

<httpsTransport maxReceivedMessageSize="4194304" /> 

使用.NET 4.0时需要考虑的一点是,如果在配置中找不到有效的端点,则会自动创建并使用默认端点。

默认端点将使用所有默认值,所以如果您认为您的maxReceivedMessageSize等有一个大值的有效服务配置,但配置出现问题,您仍然会收到400个错误请求,因为默认端点将被创建和使用。

这所以很难检测默默地做。如果您在服务器上启用跟踪,但是没有其他指示(据我所知),您将看到此消息(例如,“为服务找到没有端点,创建默认端点”或类似信息)。下ReaderQuotas

只是想指出

除了MaxRecivedMessageSize,也有属性,你会打的项目数量限制,而不是大小限制。 MSDN链接是here

在web.config中在.NET 4.0中的服务器,你还需要在默认绑定改变。设置下列3个参数:

< basicHttpBinding> 
    < !--http://www.intertech.com/Blog/post/NET-40-WCF-Default-Bindings.aspx 
    - Enable transfer of large strings with maxBufferSize, maxReceivedMessageSize and maxStringContentLength 
    --> 
    < binding **maxBufferSize="2147483647" maxReceivedMessageSize="2147483647"**> 
     < readerQuotas **maxStringContentLength="2147483647"**/>    
    < /binding> 

我找到了对错误请求400问题的答案。

这是默认的服务器绑定设置。您需要添加到服务器和客户端默认设置。

binding name =“”openTimeout =“00:10:00”closeTimeout =“00:10:00”receiveTimeout =“00:10:00”sendTimeout =“00:10:00”maxReceivedMessageSize =“2147483647” maxBufferPoolSize = “2147483647” MAXBUFFERSIZE = “2147483647”>

您也可以打开WCF日志记录有关原始错误的详细信息。这帮助我解决了这个问题。

以下内容添加到你的web.config,它的日志保存到C:\登录\ Traces.svclog

<system.diagnostics> 
    <sources> 
     <source name="System.ServiceModel" 
        switchValue="Information, ActivityTracing" 
        propagateActivity="true"> 
      <listeners> 
       <add name="traceListener" 
        type="System.Diagnostics.XmlWriterTraceListener" 
        initializeData= "c:\log\Traces.svclog" /> 
      </listeners> 
     </source> 
    </sources> 
</system.diagnostics> 

在我的情况下,它不能正常工作,甚至尝试所有的解决方案和设置的所有限制之后最大。在最后,我发现IIS /网站上安装了一个微软IIS过滤模块Url Scan 3.1,它有自己的限制,根据内容大小拒绝传入的请求并返回“404未找到页面”。

它的极限在%windir%\System32\inetsrv\urlscan\UrlScan.ini文件通过设置MaxAllowedContentLength所需要的值进行更新。

例如,以下将允许高达300 MB的请求

MaxAllowedContentLength = 314572800

希望这将帮助别人!