Служба WCF, как увеличить время ожидания?

94

Может показаться глупым вопрос, но все в WCF кажется намного сложнее, чем в asmx, как я могу увеличить тайм-аут службы svc?

Вот что у меня есть на данный момент:

<bindings>
      <basicHttpBinding>
        <binding name="IncreasedTimeout" 
          openTimeout="12:00:00" 
          receiveTimeout="12:00:00" closeTimeout="12:00:00"
          sendTimeout="12:00:00">
        </binding>
      </basicHttpBinding>
</bindings>

И затем моя конечная точка отображается следующим образом:

<endpoint address="" 
  binding="basicHttpBinding" bindingConfiguration="IncreasedTimeout"
             contract="ServiceLibrary.IDownloads">
             <identity>
                <dns value="localhost" />
             </identity>
          </endpoint>

Точная ошибка, которую я получаю:

Истекло время ожидания канала запроса при ожидании ответа после 00: 00: 59.9990000. Увеличьте значение тайм-аута, передаваемое вызову Request, или увеличьте значение SendTimeout в Binding. Время, отведенное для этой операции, могло быть частью более длительного тайм-аута.

В тестовом клиенте WCF есть значок конфигурации, который содержит конфигурацию времени выполнения моей службы:

Как видите, это не те значения, которые я для него установил? Что я делаю не так?

<bindings>
            <basicHttpBinding>
                <binding name="BasicHttpBinding_IDownloads" closeTimeout="00:01:00"
                    openTimeout="00:01:00" receiveTimeout="00:10:00" sendTimeout="00:01:00"
                    allowCookies="false" bypassProxyOnLocal="false" hostNameComparisonMode="StrongWildcard"
                    maxBufferSize="65536" maxBufferPoolSize="524288" maxReceivedMessageSize="65536"
                    messageEncoding="Text" textEncoding="utf-8" transferMode="Buffered"
                    useDefaultWebProxy="true">
                    <readerQuotas maxDepth="32" maxStringContentLength="8192" maxArrayLength="16384"
                        maxBytesPerRead="4096" maxNameTableCharCount="16384" />
                    <security mode="None">
                        <transport clientCredentialType="None" proxyCredentialType="None"
                            realm="">
                            <extendedProtectionPolicy policyEnforcement="Never" />
                        </transport>
                        <message clientCredentialType="UserName" algorithmSuite="Default" />
                    </security>
                </binding>
            </basicHttpBinding>
        </bindings>
JL.
источник

Ответы:

179

В вашей конфигурации привязки есть четыре значения тайм-аута, которые вы можете настроить:

<bindings>
  <basicHttpBinding>
    <binding name="IncreasedTimeout"
             sendTimeout="00:25:00">
    </binding>
  </basicHttpBinding>

Самый важный из них - это sendTimeout, в котором указано, как долго клиент будет ждать ответа от вашей службы WCF. Можно указать hours:minutes:secondsв настройках - в моем примере я выставил таймаут 25 минут.

Как openTimeoutследует из названия, это количество времени, которое вы готовы подождать, когда откроете соединение с вашей службой WCF. Точно так же closeTimeoutэто время, когда вы закрываете соединение (удаляете клиентский прокси), которое вы будете ждать, прежде чем будет сгенерировано исключение.

Это receiveTimeoutнемного похоже на зеркало для sendTimeout- в то время как тайм-аут отправки - это количество времени, в течение которого вы будете ждать ответа от сервера, receiveTimeoutэто количество времени, которое вы дадите своему клиенту для получения и обработки ответа от сервера. сервер.

Если вы отправляете туда и обратно «нормальные» сообщения, оба могут быть довольно короткими - особенно receiveTimeout, поскольку получение сообщения SOAP, его расшифровка, проверка и десериализация не должны занимать почти никакого времени. С потоковой передачей дело обстоит иначе - в этом случае вам может потребоваться больше времени на клиенте, чтобы фактически завершить «загрузку» потока, который вы получаете обратно с сервера.

Также есть openTimeout, receiveTimeout и closeTimeout. Документы MSDN по привязке предоставляют дополнительную информацию о том, для чего они нужны.

Чтобы серьезно разобраться во всех тонкостях WCF, я настоятельно рекомендую вам приобрести книгу Мишель Леру Бустаманте « Learning WCF »:

Изучение WCF http://ecx.images-amazon.com/images/I/51GNuqUJq%2BL._BO2,204,203,200_PIsitb-sticker-arrow-click,TopRight,35,-76_AA240_SH20_OU01_.jpg

и вы также потратите некоторое время на просмотр ее серии скринкастов " WCF Top to Bottom " из 15 частей - настоятельно рекомендуется!

Для более сложных тем я рекомендую вам прочитать книгу Juwal Lowy Programming WCF Services.

Программирование WCF http://ecx.images-amazon.com/images/I/41odWcLoGAL._BO2,204,203,200_PIsitb-sticker-arrow-click,TopRight,35,-76_AA240_SH20_OU01_.jpg

marc_s
источник
Я попытался добавить разделы привязки к <system.serviceModel> в web.config, но теперь он выдает ошибку .... любые дополнительные шаги, которые я пропустил ...
JL.
Я также изменил конечную точку в своей службе на <endpoint address = "" binding = "IncreasedTimeout" - это неправильно?
JL.
Думаю, я понял - binding = "basicHttpBinding" bindingConfiguration = "IncreasedTimeout"
JL.
точно - привязка - это тип используемого вами протокола - basicHttp, wsHttp, netTcp. Конфигурация привязки - это конфигурация, которую вы создаете в config для изменения тайм-аутов и т. Д.
marc_s
Забавно, что даже после того, как вы это сделаете, по-прежнему получаете ошибку тайм-аута, Марк, не могли бы вы дать как можно больше информации?
JL.
27

Наилучший способ - изменить любой параметр, который вы хотите в своем коде.

Посмотрите на пример ниже:

using(WCFServiceClient client = new WCFServiceClient ())
{ 
    client.Endpoint.Binding.SendTimeout = new TimeSpan(0, 1, 30);
}
user3891644
источник
это лучшее решение, скорее обновление конфигурации, чтобы я мог настроить другое значение для разных вызовов и служб, большое спасибо
Салим
26

Конфигурация тайм-аута должна быть установлена ​​на уровне клиента, поэтому конфигурация, которую я установил в web.config, не имела никакого эффекта, инструмент тестирования WCF имеет свою собственную конфигурацию, и именно здесь вам нужно установить тайм-аут.

JL.
источник
1
ну, да - обычно это должно быть установлено и на клиенте, и на сервере, даже - например, в случае "inactivityTimeout" в сессиях и тому подобном.
marc_s
8
JL: Вы можете показать, что именно вы сделали? У меня такая же проблема,
Ник Кан,
Если вы используете «Тестовый клиент WCF», щелкните правой кнопкой мыши «Файл конфигурации» в дереве служб, затем щелкните «Редактировать с помощью SvcConfigEditor» и измените время ожидания в привязках.
Radderz
4

Недавно получил ту же ошибку, но смог исправить ее, закрыв каждый клиентский вызов wcf. например.

WCFServiceClient client = new WCFServiceClient ();
//More codes here
// Always close the client.
client.Close();

или

using(WCFServiceClient client = new WCFServiceClient ())
{ 
    //More codes here 
}
Арджай
источник
10
Не используйте подход «использование»: omaralzabir.com/do-not-use-using-in-wcf-client
Alex Marshall
В комментариях к omaralzabir.com/do-not-use-using-in-wcf-client есть примеры того, как по-прежнему использовать using, не удаляя неисправный объект канала. Вот еще один блоггер с подходом, более совместимым с usingблоками: erwyn.bloggingabout.net/2006/12/09/WCF-Service-Proxy-Helper .
Грег