WCF Service using wsHttpBinding hangs after 10 concurrent requests
WCF service hosted in IIS uses default wsHttpBinding.
Clients call WCF service and do not explicitly close the connection(via proxy.close).
After 10 connections to the service, client requests appear to hang.
Capturing a dump of the IIS worker process when the requests were hung showed that the WCF service is not accepting any more connections because we have hit the ServiceThrottle limit for MaxConcurrentSessions.
More details about debugging this can be found here:
.NET Framework 4.0 will have performance counters(PercentOfMaxCalls, PercentOfMaxSessions, PercentOfMaxInstances), that can be used to find the percentage of throttle values being used currently.
By default, wsHttpBinding uses message level security and this has a session timeout value of 10 minutes.
So, when a client makes a connection to the service, a secure session is established and this will remain active till either the client calls a close on the proxy or the session timeout occurs on the service.
We have a few options to fix this:
1) Clients call proxy.close once they are done, this way the sessions are cleaned up on the server.
2) Increase the ServiceThrottle values on the service.
4.0 uses higher values for ServiceThrottle: http://blogs.msdn.com/wenlong/archive/2009/07/26/wcf-4-higher-default-throttling-settings-for-wcf-services.aspx
· MaxConcurrentSessions: default is 100 * ProcessorCount (Default for 3.0 is 10)
· MaxConcurrentCalls: default is 16 * ProcessorCount (Default for 3.0 is 16)
· MaxConcurrentInstances: default is the total of the above two, which follows the same pattern as before. (Default for 3.0 is 26)
3) If you cannot rely on clients to close the proxy and you want to force the closing of the sessions on the server, you have the following options:
· If you do not require message security, then you can disable it and the service will behave as Per-call service.
· If you need message security and want to turn off sessions, you can do so by setting the following value to false.
· Another option is to lower the ReceiveTimeout on the binding which is used by the service to drop the connection and hence the session in this case if the client hasn’t sent any ‘application messages’ for the duration of the timespan specified in the ReceiveTimeout.