Pregunta Solicitud de servicio web de WCF grande que falla con (400) HTTP Bad Request


Me he encontrado con este problema aparentemente común y no he podido resolverlo.

Si llamo a mi servicio web WCF con un número relativamente pequeño de elementos en un parámetro de matriz (he probado hasta 50), todo está bien.

Sin embargo, si llamo al servicio web con 500 elementos, aparece el error de Solicitud incorrecta.

Curiosamente, he corrido Wireshark en el servidor y parece que la solicitud ni siquiera está llegando al servidor: el error 400 se está generando en el lado del cliente.

La excepción es:

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.

los system.serviceModel La sección de mi archivo de configuración del cliente es:

<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>

En el lado del servidor, mi archivo web.config tiene lo siguiente system.serviceModel sección:

<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>

He mirado un realmente largo  número de respuestas a esta pregunta con sin éxito.

Puede alguien ayudarme con esto?


74
2018-04-24 05:12


origen


Respuestas:


Intente establecer maxReceivedMessageSize en el servidor también, p. a 4 MB:

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

La razón principal por la que el valor predeterminado (65535 creo) es tan bajo es para reducir el riesgo de ataques de denegación de servicio (DoS). Debe configurarlo más grande que el tamaño máximo de solicitud en el servidor y el tamaño máximo de respuesta en el cliente. Si se encuentra en un entorno Intranet, el riesgo de ataques DoS es probablemente bajo, por lo que probablemente sea seguro usar un valor mucho más alto de lo que espera.

Por cierto, un par de consejos para solucionar problemas relacionados con los servicios de WCF:

  • Habilite el seguimiento en el servidor como se describe en este artículo de MSDN.

  • Use una herramienta de depuración HTTP como Violinista en el cliente para inspeccionar el tráfico HTTP.


107
2018-04-24 06:00



También estaba recibiendo este problema, sin embargo, nada de lo anterior funcionó para mí, ya que estaba usando un enlace personalizado (para BinaryXML) después de un largo tiempo de excavación encontré la respuesta aquí:

Envío de XML grande de Silverlight a WCF

Como estoy usando un CustomBinding, el maxReceivedMessageSize tiene que establecerse en el elemento httpTransport bajo el elemento de enlace en el web.config:

<httpsTransport maxReceivedMessageSize="4194304" /> 

7
2017-11-12 11:58



Por lo que vale, una consideración adicional al usar .NET 4.0 es que si no se encuentra un punto final válido en su configuración, se creará y usará automáticamente un punto final predeterminado.

El punto final predeterminado usará todos los valores predeterminados, por lo que si cree que tiene una configuración de servicio válida con un valor grande para maxReceivedMessageSize, etc., pero hay algún problema con la configuración, aún obtendría 400 Bad Request, ya que un punto final predeterminado sería creado y usado.

Esto se hace en silencio, por lo que es difícil de detectar. Verá mensajes a este efecto (por ejemplo, 'No se encontró un punto final para el servicio, creando un punto final predeterminado' o similar) si activa el rastreo en el servidor, pero no hay otra indicación (que yo sepa).


7
2018-01-26 18:39



En el servidor en .NET 4.0 en web.config también necesita cambiar en el enlace predeterminado. Establecer los 3 parms siguientes:

 < 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>

5
2018-05-12 16:55



Puede ser útil depurar el cliente, desactivar Tools \ Options \ Debugging \ General \ 'Enable Just My Code', hacer clic en Debug \ Exceptions \ 'catch all first chance excepciones' para las excepciones de CLR administradas, y ver si hay una excepción bajo el capó en el cliente antes de la excepción de protocolo y antes de que el mensaje llegue al cable. (Mi suposición sería algún tipo de falla de serialización).


4
2018-04-24 05:28



También puede activar el registro de WCF para obtener más información sobre el error original. Esto me ayudó a resolver este problema.

Agregue lo siguiente a su web.config, guarda el registro en C: \ log \ 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>

4
2018-01-26 22:39



Solo quiero señalar

Además de MaxRecivedMessageSize, también hay atributos en ReaderQuotas, puede pulsar el límite de número de elementos en lugar de límite de tamaño. El enlace de MSDN es aquí


3
2018-04-26 20:58



Encontré la respuesta al problema de Bad Request 400.

Era la configuración de enlace de servidor predeterminada. Debería agregar a la configuración predeterminada del servidor y del cliente.

binding name = "" openTimeout = "00:10:00" closeTimeout = "00:10:00" receiveTimeout = "00:10:00" sendTimeout = "00:10:00" maxReceivedMessageSize = "2147483647" maxBufferPoolSize = "2147483647 "maxBufferSize =" 2147483647 ">                                                 


3
2018-03-05 05:13