Introduction
WCF client interacts with WCF host service through the following major activities:
- Address (location of the service E.g.: http:// or net.tcp://)
- Contract (Class Interface between client and server)
- Binding (Transport between client and server through encoding and Protocol)
WCF Configuration
WCF configuration should be done for both client and Server application through SVCConfigEditor.exe. The Service and client endpoint configuration should be done in both Client and Server app.config respectively. Usually for Client Server application, Binding should be done using NetTcp. This NetTcp Binding configuration should be specified in both client and server app.config bindings section of the service model. There are several timeout configurations that need to be specified in the binding such as CloseTimeout
, OpenTimeout
, ReceiveTimeout
and SendTimeout
. By default, the timeout duration is set for 1 min (00:01:00) for all these Binding Timeouts. Also, there is an InactivityTimeout
configuration required for ReliableSession
. The default Timeout duration for session inactivity is 10 minutes (00:10:00). These values will be picked up from the application when the client invokes the service from the service host.
Implementation of Code
Create Service Contract and Operation Contract Methods (Interface)
<ServiceContract()> _
Public Interface IntrWCFOprContr
<OperationContract()> _
Function CheckForService() As Boolean
End Interface
Interface Implementation
Public Class ClsWCFImpl
Implements IntrWCFOprContr
Public Function CheckForService () As Boolean _
Implements IntrWCFOprContr.CheckForService
End Function
WCF Client (VB.NET Windows Application)
Imports WCFOperation
Private Sub frmWCFClient_Load(ByVal eventSender As System.Object,
ByVal eventArgs As System.EventArgs) Handles MyBase.Load
Using serviceinvoke As New ChannelFactory(Of ClsWCFImpl)(New NetTcpBinding,
"net.tcp://localhost:4001/ClsWCFImpl ")
Try
Dim service As ClsWCFImpl
service = serviceinvoke.CreateChannel()
If serviceinvoke.State = CommunicationState.Opened Then
If service.CheckForService() then
Else
End If
End If
Catch ex As TimeoutException
Trace.WriteLine("An exception of type '" + ex.GetType().ToString() _
+ " occurred " _
+ ex.Message, "Exceptions")
End Try
End Using
End Sub
WCF Service Host (Windows Service)
Imports WCFOperation
Public TheHost As ServiceHost
Protected Overrides Sub OnStart(ByVal args() As String)
Try
If TheHost Is Nothing Then
TheHost = New ServiceHost(GetType(ClsWCFImpl))
TheHost.Open()
End If
Catch ex As CommunicationObjectFaultedException
Trace.WriteLine("An exception of type '" + ex.GetType().ToString() _
+ "occurred while OnStart Function in WCF Service. The message of the exception is: " _
+ ex.Message, "Exceptions")
End Try
End Sub
Protected Overrides Sub OnStop()
Try
Trace.WriteLine("Windows Service - OnStop " & Date.Now.ToString, "Informational")
If TheHost IsNot Nothing Then
TheHost.Close()
End If
End Try
End Sub
How It Works
The above code represents WCF client windows application hosted in a Windows Service. The WCF client will check for host status. If the host is opened (Service running), the communication starts between the WCF client and Service host through the endpoint address mentioned. The above sample works fine with the default WCF configuration as long as there is no delay in the database calls such as Executing stored procedure, queries and filling DataTable
s and DataSet
s using Dataadapter
s.
Problem
The same code sample will throw an Operation Timeout Error under the following circumstances:
- If there is a delay for More than a Minute in database responses
- OLEDB/SQL/ODBC Command Execution
- Dataadapter.Fill with
DataTable
or DataSet
- Reading data using
DataReader
The delay can happen in so many ways such as execution from Database, execution of Business logic from different layers, delay response from other interfaces referenced in the application. Because of these delays, the WCF client goes Idle from the WCF host. If the client goes Idle from the WCF service, it will throw the below error.
Error
An exception of type 'System.TimeoutException
occurred while <Function Name> Function'. The message of the exception is: This request operation sent to net.tcp://localhost:4001/ ClsWCFImpl did not receive a reply within the configured timeout (00:01:00). The time allotted to this operation may have been a portion of a longer timeout. This may be because the service is still processing the operation or because the service was unable to send a reply message. Please consider increasing the operation timeout (by casting the channel/proxy to IContextChannel
and setting the OperationTimeout
property) and ensure that the service is able to connect to the client.
Solution
To avoid this timeout error, we need to configure the OperationTimeout
property for Proxy in the WCF client code. This configuration is something new unlike other configurations such as Send Timeout, Receive Timeout, etc., which I discussed early in the article. To set this operation timeout property configuration, we have to cast our proxy to IContextChannel
in WCF client application before calling the operation contract methods. Here I am repeating the same WCF client Windows application code with the Operation timeout changes highlighted in yellow:
Imports WCFOperation
Private Sub frmWCFClient_Load(ByVal eventSender As System.Object,
ByVal eventArgs As System.EventArgs) Handles MyBase.Load
Using serviceinvoke As New ChannelFactory(Of ClsWCFImpl)(New NetTcpBinding,
"net.tcp://localhost:4001/ClsWCFImpl ")
Try
Dim service As ClsWCFImpl
service = serviceinvoke.CreateChannel()
If serviceinvoke.State = CommunicationState.Opened Then
DirectCast(service, IContextChannel).OperationTimeout = New TimeSpan(0, 0, 240)
If service.CheckForService() then
Else
End If
End If
Catch ex As TimeoutException
Trace.WriteLine("An exception of type '" + ex.GetType().ToString() _
+ " occurred " _
+ ex.Message, "Exceptions")
End Try
End Using
End Sub
Here, timeout duration is set as 240 seconds. The duration can also be set in Hours or Minutes format based on the requirement in the application and tentative delay expected from database or from other interfaces response. It is better to keep the timeout duration in the app.config of the application and keep changing it when required.
Conclusion
This operation timeout configuration is for the service that was able to connect to the client with the specified duration. The same solution is also applicable when hosting WCF in a managed .NET application such as Console or web application (ASP.NET).
Wish you all the best !!!
History
- 31st July, 2008: Initial post