This article helps you to understand how per call WCF service works and how its instances get created. This article will also go through a tutorial for implementing and executing Per Call WCF Service.
A WCF service configured as InstanceContextMode.PerCall will create a dedicated instance for each request irrespective of existing or new clients. It does not save any client data in service memory. Once the service returns a response to the client, the instance gets disposed.
The following picture describes how PerCall instantiation happens
Create a new WCF Service Library by opening your visual studio -> click on File -> New -> Project -> WCF (from installed template) -> WCF Service Library.
Name it as PerCallService and click Ok.
Add new WCF ServiceContract by right click on PerCallService service library project and click on Add -> New Item -> interface.
Name it as IProductService and click Ok.
Add below code with OperationContracts for IProductService
using System.ServiceModel;
namespace PerCallService
{
[ServiceContract(Name = "ProductService",
Namespace = "http://northwind.com/productservice")]
public interface IProductService
{
[OperationContract]
void SetProductQty(int qty);
[OperationContract]
int GetProductQty();
}
}
In this step, we will implement the IProductService service contract created in previous the step. Add a new class by right click on PerCallService service library project and select on Add -> class.
Name it as ProductService and click Ok.
Add below code which implements OperationContract of the IProductService.
using System.ServiceModel;
namespace PerCallService
{
[ServiceBehavior(Name = "ProductService",
Namespace = "http://northwind.com/productservice",
InstanceContextMode= InstanceContextMode.PerCall)]
public class ProductService : IProductService
{
public void SetProductQty(int qty)
{
this.ProductQty = qty;
}
public int GetProductQty()
{
return this.ProductQty;
}
private int ProductQty
{
get;
set;
}
}
}
We added one private property ProductQty which is used for reading and writing value for ProductQty.
We implemented OperationContract SetProductQty which set the value of ProductQty given by the service client.
We implemented OperationContract GetProductQty which returns the value of ProductQty.
In the ServiceBehavior attribute, we marked service as PerCall.
Add ServiceHost file by right click on PerCallService service library project and select on Add -> New Item -> WCF Service or Text File -> name it as ProductServiceHost.svc.
Add below ServiceHost details to ProductServiceHost.svc.
<%@ ServiceHost Service="PerCallService.ProductService" %>
Open App.Config from solution explorer. Remove existing Service Endpoints that point to default Service1.
Add below service details which point to new ProductService.
<service name="PerCallService.ProductService">
<host>
<baseAddresses>
<add baseAddress =
"http://localhost:7741/PerCallService/ProductService" />
</baseAddresses>
</host>
<endpoint address="" binding="wsHttpBinding"
contract="PerCallService.IProductService"
bindingNamespace ="http://northwind.com/productservice" >
</endpoint>
<endpoint address="mex"
binding="mexHttpBinding"
contract="IMetadataExchange" />
</service>
Host ProductService in IIS, check how to host WCF service in IIS or in Windows Service
Create a new console application that will work as client for ProductService. Click on Solution Explorer -> Right click on Solution -> Add -> New Project -> Console Application
Name it as PerCallServiceClient and click Ok.
Add Service Reference to ProductService by right click on References (PerCallServiceClient project) -> Select Add Service Reference -> In Add Service Reference dialog box enter http://localhost:7741/ProductServiceHost.svc -> give namespace as ProductServiceRef.
Open Program.cs file of PerCallServiceClient console application. Add below code in main method.
static void Main(string[] args)
{
ProductServiceRef.ProductServiceClient client
= new ProductServiceRef.ProductServiceClient();
client.SetProductQty(10);
Console.WriteLine(client.GetProductQty());
Console.Read();
}
We called SetProductQty service operation first to set ProductQty as 10. However, when we call GetProductQty we get 0, as 10 is not saved in physical memory and SessionMode is set to PerCall so the service won't maintain any state data between client calls.
Now open ProductService WCF service from Service Library and change ServiceBehavior and remove InstanceContextMode. As we are using wsHttpBinding which supports reliable sessions PerSession would be the default value for InstanceContextMode.
Your ServiceBehavior should look like
[ServiceBehavior(Name = "ProductService",
Namespace = "http://northwind.com/productservice")]
public class ProductService :
IProductService
{
// implementation of operation contract.
}
Build service, publish it again, update service reference for the client application and execute client application. You will see the ProductQty as 10. As service is PerSession, the service maintains object state for multiple calls made from the same proxy.