La devolución de llamada no se mantendrá indefinidamente, buscará los valores de tiempo de espera que haya establecido en su configuración. Si habilita sesiones confiables, puede establecer los tiempos de inactividad de sus clientes. Puede configurar los tiempos de espera de esta manera:
<netTcpBinding>
<binding
closeTimeout="00:01:00"
openTimeout="00:01:00"
receiveTimeout="00:10:00"
sendTimeout="00:01:00"
transactionFlow="false"
......>
<reliableSession ordered="true" inactivityTimeout="00:10:00" enabled="true" />
</binding>
</netTcpBinding>
Cuando se alcanzan estos valores y no hay todavía ninguna respuesta, el canal de comunicación se convierte criticado y es necesario volver a crear un proxy cliente para consumir el servicio. El valor predeterminado para receiveTimeout
es 10 minutos, así que puede aumentar eso, pero también asegúrese de aumentar su inactivityTimeout
también, su inactivityTimeout
debe ser mayor que receiveTimeout
.
EDIT:
Se podía seguir cambiando su receiveTimeout
programación basada en los valores de su cliente envía de vuelta al servidor, la clave es mantener las nuevos valores de tiempo igual en el servicio y el cliente. Se podría ir haciendo esto en el cliente (un ejemplo que me llevo de un servicio de chat estoy haciendo con WCF y consumir con los clientes de Silverlight):
//Create different clients dynamically
MyChatServiceClient _client1 = new MyChatServiceClient("NetTcpBinding_IMyChatService_1");
MyChatServiceClient _client2 = new MyChatServiceClient("NetTcpBinding_IMyChatService_2");
En la configuración del cliente:
<!--In your config file, define multiple endpoints/behaviors with different values based on your needs-->
<bindings>
<customBinding>
<binding name="NetTcpBinding_IMyChatService_1" receiveTimeout="00:01:00" ...>
<binaryMessageEncoding />
<tcpTransport maxReceivedMessageSize="283647" maxBufferSize="283647" />
</binding>
<binding name="NetTcpBinding_IMyChatService_2" receiveTimeout="00:22:00" ...>
<binaryMessageEncoding />
<tcpTransport maxReceivedMessageSize="2147483647" maxBufferSize="2147483647" />
</binding>
</customBinding>
</bindings>
<client>
<endpoint address="net.tcp://192.168.1.51:4520/VideoChatServer/"
binding="customBinding" bindingConfiguration="NetTcpBinding_IMyChatService_1"
contract="IMyChatService" name="NetTcpBinding_IMyChatService_1" />
<endpoint address="net.tcp://192.168.1.51:4522/VideoChatServer/"
binding="customBinding" bindingConfiguration="NetTcpBinding_IMyChatService_2"
contract="IMyChatService" name="NetTcpBinding_IMyChatService_2" />
</client>
Así se puede definir varios puntos finales o fijaciones en la configuración de su cliente o el servidor, a continuación, basado en lo que sea evento en su aplicación que puede crear una instancia _clientProxyX consumir _serviceInstanceX que tendrá diferentes unión/punto final valores pero al mismo contrato como su anterior instancia de servicio. En el ejemplo anterior, el primer enlace tiene un tiempo de espera de 1 minuto, y el segundo enlace es de 2 minutos. Un punto importante a considerar es que si desea recrear nuevos proxies de clientes como este, entonces necesita derribar su antiguo cliente proxy y crear uno nuevo, que efectivamente desconecte a sus clientes del servicio, al menos momentáneamente.
También puede modificar esos valores (openTimeout
, closeTimeout
etc.) programáticamente en ambos servidores al crear un nuevo host de servicio. Se puede crear un nuevo huésped, basado en una de las configuraciones de enlace que ha definido en su configuración, o crear una nueva configuración mediante programación, algo como esto:
var host = new ServiceHost(typeof(MyChatService));
var webHttpBinding = new System.ServiceModel.WebHttpBinding();
//Modify new timeout values before starting the host
webHttpBinding.OpenTimeout = new TimeSpan(1, 0, 0);
webHttpBinding.CloseTimeout = new TimeSpan(1, 0, 0);
host.AddServiceEndpoint(webHttpBinding, "http://192.168.1.51/myService.svc");
//start the host after necessary adjustments
host.Open();
Esto parece bastante desordenado lo sé, pero el punto es que WCF te da mucha flexibilidad para poder modificar tus configuraciones de enlace mediante programación. Asegúrese de verificar this gran respuesta sobre la modificación de sus archivos de configuración WCF. Y también puede crear fácilmente un service configuration programmtically completo.
Quiero manejar eventos periódicos, ¿sería aceptable tener un mensaje "Keep-Alive" del servidor cada x minutos y establecer el tiempo de espera en 2 * x? –
Entonces, ¿desea seguir cambiando el receiveTimeout en función de lo que devuelve su cliente al servidor, correcto? No lo he hecho antes, pero no creo que sea necesariamente una mala práctica. ¿Por qué no pones los tiempos de espera en "infinito"? También podría hacerlo mediante programación de esta manera: binding.ReceiveTimeout = new TimeSpan (300,0,0,0,0); esto hará que su receiveTimeout 300 días. –