Невозможно установить maxReceivedMessageSize через web.config
-
10-07-2019 - |
Вопрос
Я исследовал код 400 — BadRequest за последние два часа.Многие предложения направлены на то, чтобы убедиться, что атрибутbindingConfiguration установлен правильно, и в моем случае это так.
Теперь мне нужна ВАША помощь, прежде чем разрушать здание, в котором я нахожусь :-)
Я запускаю сервис WCF RestFull (очень легкий, использую этот ресурс для вдохновения: http://msdn.microsoft.com/en-us/magazine/dd315413.aspx), который (на данный момент) принимает XmlElement (POX), предоставленный через команду POST.
В настоящее время я ТОЛЬКО использую построитель запросов Fiddler перед реализацией настоящего клиента (поскольку это смешанные среды).
Когда я делаю это для XML размером менее 65 КБ, все работает нормально, а больше выдает это исключение:Превышена квота максимального размера входящих сообщений (65536).Чтобы увеличить квоту, используйте свойство MaxReceivedMessageSize соответствующего элемента привязки.
Вот мой файл web.config (для которого я даже включил клиентский тег (в отчаянные времена!)):
<system.web>
<httpRuntime maxRequestLength="1500000" executionTimeout="180"/>
</system.web>
<system.serviceModel>
<diagnostics>
<messageLogging logEntireMessage="true" logMalformedMessages="true" logMessagesAtServiceLevel="true" logMessagesAtTransportLevel="true" />
</diagnostics>
<bindings>
<webHttpBinding>
<binding name="WebHttpBinding" maxReceivedMessageSize="1500000" maxBufferPoolSize="1500000" maxBufferSize="1500000" closeTimeout="00:03:00" openTimeout="00:03:00" receiveTimeout="00:10:00" sendTimeout="00:03:00">
<readerQuotas maxStringContentLength="1500000" maxArrayLength="1500000" maxBytesPerRead="1500000" />
<security mode="None"/>
</binding>
</webHttpBinding>
</bindings>
<client>
<endpoint address="" binding="webHttpBinding" bindingConfiguration="WebHttpBinding" contract="Commerce.ICatalogue"/>
</client>
<services>
<service behaviorConfiguration="ServiceBehavior" name="Catalogue">
<endpoint address=""
behaviorConfiguration="RestFull"
binding="webHttpBinding"
bindingConfiguration="WebHttpBinding"
contract="Commerce.ICatalogue" />
<!-- endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange" / -->
</service>
</services>
<behaviors>
<endpointBehaviors>
<behavior name="RestFull">
<webHttp/>
</behavior>
</endpointBehaviors>
<serviceBehaviors>
<behavior name="ServiceBehavior">
<serviceDebug httpHelpPageEnabled="true" includeExceptionDetailInFaults="true"/>
<serviceMetadata httpGetEnabled="true"/>
</behavior>
</serviceBehaviors>
</behaviors>
</system.serviceModel>
Заранее благодарим за любую помощь, которая приведет к успешному вызову с >65 КБ XML ;-)
Решение
Хорошо, этот действительно вызвал у меня трудности с разрешением, за которые я пощадлю других.
Проблема заключалась в том, что я использовал <%@ ServiceHost Factory="System.ServiceModel.Activation.WebServiceHostFactory" Service="fullyQualifiedClassName" %>
, что является хорошим и простым подходом к реализации на заводе.
Однако у этого подхода есть свои недостатки; поскольку в файле web.config не требуется настройка, класс WebServiceHostFactory по своему дизайну никогда не считывает данные из файла web.config. Я знаю; Я мог унаследовать от этого класса и внести соответствующие изменения, чтобы он действительно мог считываться из файла конфигурации, но это, казалось, немного выходило за рамки.
Моим решением было вернуться к более традиционному способу реализации WCF; <%@ ServiceHost Service="fullyQualifiedClassName" CodeBehind="~/App_Code/Catalogue.cs" %>
, а затем используйте мои уже настроенные значения в файле web.config.
Вот мой модифицированный файл web.config (в отношении головной боли Maddox):
<system.serviceModel>
<bindings>
<webHttpBinding>
<binding name="XmlMessageBinding" maxReceivedMessageSize="5000000" maxBufferPoolSize="5000000" maxBufferSize="5000000" closeTimeout="00:03:00" openTimeout="00:03:00" receiveTimeout="00:10:00" sendTimeout="00:03:00">
<readerQuotas maxStringContentLength="5000000" maxArrayLength="5000000" maxBytesPerRead="5000000" />
<security mode="None"/>
</binding>
</webHttpBinding>
</bindings>
<services>
<service name="fullyQualifiedClassName" behaviorConfiguration="DevelopmentBehavior">
<endpoint name="REST" address="" binding="webHttpBinding" contract="fullyQualifiedInterfaceName" behaviorConfiguration="RestEndpointBehavior" bindingConfiguration="XmlMessageBinding" />
</service>
</services>
<behaviors>
<endpointBehaviors>
<behavior name="RestEndpointBehavior">
<webHttp/>
</behavior>
</endpointBehaviors>
<serviceBehaviors>
<behavior name="DevelopmentBehavior">
<serviceDebug httpHelpPageEnabled="true" includeExceptionDetailInFaults="true"/>
<serviceMetadata httpGetEnabled="true"/>
</behavior>
<behavior name="ProductionBehavior">
<serviceDebug httpHelpPageEnabled="false" includeExceptionDetailInFaults="false"/>
<serviceMetadata httpGetEnabled="false"/>
</behavior>
</serviceBehaviors>
</behaviors>
</system.serviceModel>
Еще одним преимуществом этого изменения является то, что теперь вы можете ссылаться на свою службу WCF-отдыха непосредственно из .NET; этого нельзя сделать с помощью модели Factory и моей реализации XmlElement с помощью решения.
Я надеюсь, что это может помочь другим с похожими проблемами ...
Другие советы
Я знаю, что это очень старый вопрос, и на него уже есть ответ...
В любом случае...
Что я сделал для решения этой «проблемы»: я создал Factory, унаследованную от WebServiceHostFactory, и создал собственный хост службы, унаследованный от WebServiceHost.
И в хосте я переопределил метод OnOpening вот так
protected override void OnOpening()
{
base.OnOpening();
foreach (var endpoint in Description.Endpoints)
{
var binding = endpoint.Binding as System.ServiceModel.Channels.CustomBinding;
foreach (var element in binding.Elements)
{
var httpElement = element as System.ServiceModel.Channels.HttpTransportBindingElement;
if (httpElement != null)
{
httpElement.MaxBufferSize = 2147483647;
httpElement.MaxReceivedMessageSize = 2147483647;
}
}
}
}
Я думаю, что у меня была та же проблема, но когда я настроил привязку по умолчанию для webHttp, то это сработало:
<bindings>
<webHttpBinding>
<binding maxReceivedMessageSize="2000000"
maxBufferSize="2000000">
<readerQuotas maxStringContentLength="2000000"/>
</binding>
</webHttpBinding>
</bindings>
Обратите внимание: на привязке нет имени. Р>
Это запись в блоге, которую я написал, которая воспроизводит эту проблему с абсолютно минимальной частью сервера и клиента WCF:
WCF - исправление длины строки на стороне клиента исключения
В частности, вам может потребоваться настраиваемая конфигурация привязки. По крайней мере, воспроизведение этого образца может дать вам некоторые идеи для вашей конкретной ситуации.