Per-Session Instance Management in WCF

Objective

This article is part # 2 of Instance Management in WCF. This article will explain Session Full Instance management service. This will explain different Session Mode at Contract level. This will explain Per-session service also. This article will be explaining Session Full Service with a code also.

Part # 1 of this series could be found Here

Per-Session Service

 


 

  1. WCF can maintain a logical session between a client and service.
  2. The service instance remains in the memory throughout the session.
  3. The client session is per service endpoint per proxy.

     


     

Configuring Session Full service

There are three elements, which must be taken care while configuring a session full service.

 


 

Behavior Facet

  1. The Behavior part is required, so that WCF will keep the Service Instance Context alive throughout the session.

 

 

  1. InstanceContextMode.PerSession is default value for InstanceContextmode property.
  2. The session terminates when client closes the proxy.
  3. Proxy has to notify the service that session has been closed and service calls the Dispose () method on worker thread. 

Contract Facet

 In order to create all messages from a particular client to a particular instance WCF needs to identify the client and this is done by TRANSPORT SESSION.

 

 

  1. For this ServiceContract attribute having a property called SessionMode.
  2. Type of property SessionMode is enum SessionMode.
  3. It is inside namespace System.ServiceModel.
  4. Property SessionMode is a public property


 

  1. SessionMode enum is default to SessionMode.Allowed.
  2. The Configured value of SessionMode is exposed to client in MetaData.

SessionMode.Allowed

 

  1. When the SessionMode is configured with SessionMode.Allowed, transport session are allowed but not enforced.
  2. The Behavior of service will depend upon behavior configuration and binding.  


Code Example

Both code is same because SessionMode.Allowed is default.


 

SessionMode.Required

 

  1. SessionMode.Required value restricts to use Transport level session. 
  2. If a contract is configured as SessionMode.Required with a service end point who’s binding does not maintain a Transport level session a Run time error will encountered at loading of service. 

     



 

Code Example

SessionMode.NotAllowed 

  1. This disallows the use of Transport session.
  2. Regardless of the service configuration, when SessionMode.NowAllowed is configured at contract, the service will always behave as Per-call service.

     


     

Code Example

[ServiceContract(SessionMode=SessionMode.NotAllowed)]


public
interface
IService1

{

}

Explanation of Per-Session service instance with a Sample

 

Consider code below

Service contract

using System;

using System.Collections.Generic;

using System.Linq;

using System.Runtime.Serialization;

using System.ServiceModel;

using System.Text;

 

namespace PerSessionSample

{

 

[ServiceContract(SessionMode=SessionMode.Required)]


public
interface
IService1

{

 

[OperationContract]


int GetData();

 

}

 

}

 

Service

using System;

using System.Collections.Generic;

using System.Linq;

using System.Runtime.Serialization;

using System.ServiceModel;

using System.Text;

 

namespace PerSessionSample

{

[ServiceBehavior(InstanceContextMode = InstanceContextMode.PerSession)]


public
class
Service1 : IService1,IDisposable

{


int _counter = 0;


public Service1()

{

 

}


public
int GetData()

{

_counter++;


return _counter;

 

}


public
void Dispose()

{

}

 

 

}

}

Client

using System;

using System.Collections.Generic;

using System.Linq;

using System.Text;

using Test.ServiceReference1;

 

namespace Test

{


class
Program

{


static
void Main(string[] args)

{


Service1Client proxy1 = new
Service1Client();


Console.WriteLine(” 1st Output by Proxy 1″);


Console.WriteLine(proxy1.GetData().ToString());

 


Console.WriteLine(” 2nd Output by Proxy 1″);


Console.WriteLine(proxy1.GetData().ToString());

 

 

 

 


Service1Client proxy2 = new
Service1Client();


Console.WriteLine(“1st Output by Proxy 2″);


Console.WriteLine(proxy2.GetData().ToString());

 

proxy2.Close();

 

 


Service1Client proxy3 = new
Service1Client();


Console.WriteLine(“1st Output by Proxy 3″);


Console.WriteLine(proxy3.GetData().ToString());

 

 

 


Console.WriteLine(” 2nd Output by Proxy 3 “);


Console.WriteLine(proxy3.GetData().ToString());

 

 


Console.WriteLine(” 3rd Output by Proxy 1 “);


Console.WriteLine(proxy3.GetData().ToString());


Console.ReadKey(true);

 

 

}

}

}

 

Output


Explanation

  1. We could see from output is that Service Instance is particular and individual for each individual proxy.
  2. When proxy is getting closed or down, service instance is also being disposed on worker thread.

Conclusion

This article was part# 2 of multi series Instance Management Article. This article explained about Session Full Service Management.

Happy Coding

Session Id in WCF

Objective 

This article is part # 4 of Instance Management in WCF. This article will explain how to work with Session ID in WCF. This article will give theoretical introduction and explanation of coding sample also. It will explain 2 full coding sample that how to work with Session ID in WCF.

Part # 1 of this series could be found Part 1

Part # 2 of this series could be found Part 2

Part # 3 of this series could be found Part 3 

Note: There is no any attached code with this article because; I have amended same sample to give different demonstration. I am sorry for that, but once you will go through article, you will able to understand the concept behind. 

The Session ID in WCF

                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                    

                                                                                                                                                                                                                                                                                                                          

  1. Every session has a unique Session ID.
  2. Both client and service can obtain and use the Session ID.
  3. The Session ID is in form of GUID.
  4. The main use of Session ID is in logging.


    Session ID at Server side 

  1. Every Service operation has an operation call context accessible via the operational class.
  2. A Service can obtain a reference to the operation context of current method via the Current static method of the OperationConext class.

 

Session ID at client side

 

Fetching Session ID at client for a Per-Session configured service (Sample #1)

In below code sample

  1. Service is configured as Session full service.
  2. SessionMode of contract of service is set to Required.
  3. Client is referencing the service and creating different proxies.
  4. Expected output is , 

     

Service Interface (Contract)

using System;

using System.Collections.Generic;

using System.Linq;

using System.Runtime.Serialization;

using System.ServiceModel;

using System.Text;

namespace SessionTestingService

{

[ServiceContract(SessionMode=SessionMode.Required)]


public
interface
IService1

{

[OperationContract]


int GetData();

}

}

Service

using System;

using System.Collections.Generic;

using System.Linq;

using System.Runtime.Serialization;

using System.ServiceModel;

using System.Text;

namespace SessionTestingService

{

[ServiceBehavior(InstanceContextMode= InstanceContextMode.PerSession)]


public
class
Service1 : IService1

{


public
int GetData()

{


return 9;

}

}

}

Client

using System;

using System.Collections.Generic;

using System.Linq;

using System.Text;

using SessionIdSampleatClient.ServiceReference1;

namespace SessionIdSampleatClient

{


class
Program

{


static
void Main(string[] args)

{


Service1Client proxy = new
Service1Client();

proxy.Open();


string sessionid = proxy.InnerChannel.SessionId;


Console.WriteLine(“Session id of 1st Proxy = “+sessionid);

proxy.Close();


Service1Client proxy1 = new
Service1Client();

proxy1.Open();

sessionid = proxy1.InnerChannel.SessionId;


Console.WriteLine(“Session id of 2nd Proxy = “ + sessionid);

proxy1.Close();


Service1Client proxy3 = new
Service1Client();

proxy3.Open();

sessionid = proxy1.InnerChannel.SessionId;


Console.WriteLine(“Session id of 2nd Proxy = “ + sessionid);

proxy3.Close();


Console.ReadKey(true);

}

}

}

Output



Comparing Session ID at client and Service for a Per-Session configured service (Sample #2)

In below code sample

  1. Service is configured as Session full service.
  2. SessionMode of contract of service is set to Required.
  3. Service is exposing one Operation Contract, which is returning Session ID for a particular operation context.
  4. Client is creating a Proxy and fetching the session ID.
  5. There is a comparison between Session Id returned by service and Session Id fetched by client for a particular session. Whether both session ID is same or not.

Service Interface (Contract)

using System;

using System.Collections.Generic;

using System.Linq;

using System.Runtime.Serialization;

using System.ServiceModel;

using System.Text;

namespace SessionTestingService

{

[ServiceContract(SessionMode=SessionMode.Required)]


public
interface
IService1

{

[OperationContract]


string GetSessionID();

}

}

Service

using System;

using System.Collections.Generic;

using System.Linq;

using System.Runtime.Serialization;

using System.ServiceModel;

using System.Text;

namespace SessionTestingService

{

[ServiceBehavior(InstanceContextMode= InstanceContextMode.PerSession)]


public
class
Service1 : IService1

{


public
string GetSessionID()

{


string sessionId = OperationContext.Current.SessionId;


return sessionId;

}

}

}

Client

using System;

using System.Collections.Generic;

using System.Linq;

using System.Text;

using SessionIdSampleatClient.ServiceReference1;

namespace SessionIdSampleatClient

{


class
Program

{


static
void Main(string[] args)

{


Service1Client proxy = new
Service1Client();

proxy.Open();


Console.WriteLine(“Session Id Fetched from the Service “ + proxy.GetSessionID());


string sessionid = proxy.InnerChannel.SessionId;


Console.WriteLine(“Session id Fetched at the Client = “+sessionid);


int res = sessionid.CompareTo(proxy.GetSessionID());


if(res==0)

{


Console.WriteLine(“Service Session Id and Clinet Session Id is Same “);

}

proxy.Close();


Console.ReadKey(true);

}

}

}

Output



 Conclusion 

This article explained about, Session ID in WCF. This article gave theoretical introduction and explanation of coding sample also.

Happy Coding

Single Instance Management in WCF

Objective

This article is part # 3 of Instance Management in WCF.

This article will explain about Singleton Service Instance mode. This article will give theoretical introduction and explanation of coding sample also. It will also discuss about various disadvantages of Singleton Service Instance mode and its potential place of uses.

Part # 1 of this series could be found Here.

Part # 2 of this series could be found Here. 

Singleton Service


  1. The Singleton Service Instance created only once.
  2. It created when the service host is created.
  3. It lives forever.
  4. It got disposed only when host shuts down.
  5. Singleton service instance does not require client to maintain any logical session.
  6. It does not required to use binding that supports transport level session.


Code

[ServiceBehavior(InstanceContextMode =InstanceContextMode.Single)]


public
class
Service1 : IService1,IService2 ,IDisposable

{

}

Explanation with example

Service Contract 1

using System;

using System.Collections.Generic;

using System.Linq;

using System.Runtime.Serialization;

using System.ServiceModel;

using System.Text;

namespace SingleServiceInstanceService

{

[ServiceContract(SessionMode=SessionMode.Required)]


public
interface
IService1

{

[OperationContract]


int GetDataFromRequiredContract();

}

}

 Service Contract 2

using System;

using System.Collections.Generic;

using System.Linq;

using System.Runtime.Serialization;

using System.ServiceModel;

using System.Text;

namespace SingleServiceInstanceService

{

[ServiceContract(SessionMode = SessionMode.NotAllowed)]


public
interface
IService2

{

[OperationContract]


int GetDataFromNotAllowedContract();

}

}

 Service

using System;

using System.Collections.Generic;

using System.Linq;

using System.Runtime.Serialization;

using System.ServiceModel;

using System.Text;

namespace SingleServiceInstanceService

{

[ServiceBehavior(InstanceContextMode =InstanceContextMode.Single)]


public
class
Service1 : IService1,IService2 ,IDisposable

{


int _Counter = 0;


public Service1()

{

}


public
int GetDataFromRequiredContract()

{

_Counter++;


return _Counter;

}


public
int GetDataFromNotAllowedContract()

{

_Counter++;


return _Counter;

}


public
void Dispose()

{

}

}

} 

  1. There are two contracts IService1 and IService2.
  2. For IService1 session mode is set to SessionMode=SessionMode.Required
  3. For IService2 session mode is set to SessionMode = SessionMode.NotAllowed
  4. Service is implanting both the contracts.
  5. Service Behavior is configured to single instance mode

ServiceBehavior(InstanceContextMode =InstanceContextMode.Single)]

 

Web.Config 

<system.serviceModel>

<services>

<service
name=SingleServiceInstanceService.Service1
behaviorConfiguration=SingleServiceInstanceService.Service1Behavior>

<!– Service Endpoints –>

<endpoint
address=RequiredService
binding=wsHttpBinding
contract=SingleServiceInstanceService.IService1>

</endpoint>

<endpoint
address=AllowedService
binding=wsHttpBinding
contract=SingleServiceInstanceService.IService2>

</endpoint>

<endpoint
address=mex
binding=mexHttpBinding
contract=IMetadataExchange/>

</service>

</services>

<behaviors>

<serviceBehaviors>

<behavior
name=SingleServiceInstanceService.Service1Behavior>

<serviceMetadata
httpGetEnabled=true/>

<serviceDebug
includeExceptionDetailInFaults=false/>

</behavior>

</serviceBehaviors>

</behaviors>

</system.serviceModel>

.

  1. In System.ServiceModel, we need to expose two addresses. One each for individual contracts.

Client

using System;

using System.Collections.Generic;

using System.Linq;

using System.Text;

using Test.ServiceReference1;

namespace Test

{


class
Program

{


static
void Main(string[] args)

{


Service1Client proxy = new
Service1Client();


Console.WriteLine(proxy.GetDataFromRequiredContract().ToString());


Service2Client proxy2 = new
Service2Client();


Console.WriteLine(proxy2.GetDataFromNotAllowedContract().ToString());


Console.ReadKey(true);

}

}

}

Output

 

 

Explanation of output 

Since service instance is configured for Singleton, all the proxy will share the same service instance. That is why all proxy is incrementing the same value. And as the output, each time client is getting incremented value

Disadvantage 

  1. Having scalability problem.
  2. All requests to service will run on different worker thread, so it will cause synchronization problem.
  3. Only one client could have access to singleton service instance at a time. It will decrease throughput of the service.
  4. Responsiveness is very low
  5. Singleton Service instance should only be used, when no other options are available. For instance Global Log Book, Single Communication Port etc.

Conclusion 

This article explained about, Singleton Service Instance mode. This article gave theoretical introduction and explanation of coding sample also. It also discussed about various disadvantages of Singleton Service Instance mode and its potential place of uses.

Happy Coding


Streaming in WCF

Objective

In this article, I am going to explain various aspects of streaming of messages in WCF. For example;

  1. I/O Streams
  2. Streaming and Binding
  3. Streaming and Transport channel
  4. Stream management

Why we need Streaming?

In WCF any receiving message is delivered only once entire message has been received. What I mean here is that first message is buffered at the receiving side and once it is fully received it gets delivered to the receiving end. Main problem with this approach is that receiver end is unresponsive while message is getting buffered. So default way of message handling in WCF is ok for small size messages but for the large size messages this approach is not good. So to overcome this problem Streaming in WCF come into action.

I/O Streams

WCF uses .Net Stream class for the purpose of streaming. There are no any changes while defining contract. It simply looks like normal contracts. Below contract is returning stream and taking stream input.

using System;

using System.Collections.Generic;

using System.Linq;

using System.Runtime.Serialization;

using System.ServiceModel;

using System.Text;

using System.IO;

namespace OneWayService

{

[ServiceContract]


public
interface
IService1

{

[OperationContract]


Stream ReturnStreamfromSeervice();

[OperationContract]


void ProcessStreamFromClient(Stream stream);

}

}

  1. Parameter could be defined either as abstract base class Stream or Subclass MemoryStream
  2. Subclasses FileStream etc are not allowed as the type of parameters.

Steaming and Binding

  1. TCP, IPC and HTTP bindings support streaming.
  2. For all the Binding streaming is disabled by default.
  3. Streaming of the message should be enabled in the binding to override the buffering and enable the streaming.
  4. TransferMode property should be set according to the desired streaming mode in the bindings.
  5. Type of TransferMode property is enum TransferMode  

TransferMode enum type

using System;

namespace System.ServiceModel

{


public
enum
TransferMode

{

Buffered = 0,

Streamed = 1,

StreamedRequest = 2,

StreamedResponse = 3,

}

}

  1. This property is defined in all the binding classes.

TransferMode property in BasicHttpBinding class.

 using System;

using System.ServiceModel.Channels;

using System.Text;

using System.Xml;

namespace System.ServiceModel

{


public
class
BasicHttpBinding : Binding, IBindingRuntimePreferences

{


public
TransferMode TransferMode { get; set; }

}

}

  1. TransferMode.Streamed supports all type of streaming modes. This supports all stream operations like receiving, returning.
  2. If you want to have buffer request and stream response TransferMode.StreamedResponse.

Configuring Streaming in Config file

<system.serviceModel>

        <services>

            <service
name=OneWayService.Service1
behaviorConfiguration=OneWayService.Service1Behavior >

                <!– Service Endpoints –>

                <endpoint
address=“”
binding=basicHttpBinding
bindingConfiguration=StreamedHttp
contract=OneWayService.IService1 >

                    

                    <identity>

                        <dns
value=localhost/>

                    </identity>

                </endpoint>

                <endpoint
address=mex
binding=mexHttpBinding
contract=IMetadataExchange/>

            </service>

        </services>

<bindings>

<basicHttpBinding>

<binding
name =StreamedHttp
transferMode =Streamed />

</basicHttpBinding>

</bindings>

        <behaviors>

            <serviceBehaviors>

                <behavior
name=OneWayService.Service1Behavior>

                                        <serviceMetadata
httpGetEnabled=true/>

                                        <serviceDebug
includeExceptionDetailInFaults=false/>

                </behavior>

            </serviceBehaviors>

        </behaviors>

    </system.serviceModel>

Increasing Message size

The default message size is 64K. But the message size in case of streaming may be very large. So default message size could be increased.

MaxReceivedMessageSize property of BasicHttpBinding class is used to increase the message size. Typical way of increasing message size is in config file.

<basicHttpBinding>

<binding
name =StreamedHttp
transferMode =Streamed
maxReceivedMessageSize =100000/>

</basicHttpBinding>

 Conclusion

I have explained all the facets related to Streaming in WCF. Thanks for reading.

Happy Coding

Data Transfer in WCF

Objective

I have seen on web many people talking about, how to deal with DTO classes and business class in WCF. And those entire topics persuaded me to write this article. This article will mainly show

  1. What is Business class and how to create them?
  2. What is DTO class?
  3. How to convert a business class to DTO class and vice versa.
  4. How to perform CRUD operation on ADO.Net Entity Data model.
  5. How to expose operations as WCF Soap service.
  6. How to consume them in a simple console client.

But main objective behind this article is to show how to deal with DTO classes?

Data Transfer Object class explanation 

This is a normal class, which WCF or service uses to communicate with the client. This class is exposed as Data Contract . WCF cannot put Data Contract on the class which is having constructors and methods. So, the business class generated by ORM (here it is Entity model) having methods, constructor and all. And that cannot be exposed as Data Contract. So we need some converter which will convert business class to DTO and DTO class to Business class.


 

 Solution

Database

I am using the below table for sample. You could use any table. Name of the table is WCF and it is having two columns Name and EmpId and both are nvarchar.


Data Model

Step 1

Create a WCF Service application. To do this select Proejct -> New -> Web -> WCF Service Application. Delete all the default code created. Now you have an empty contract with the name IService1 and Service implantation as Service1.

Step 2

Right click at the project in solution explorer. And select Add New Item. From the dialog box click on Data tab and select ADO.Net Entity Model. From here create an entity model. Give some name and click on Add. After that click on Next.



From here select the Database , you want to work on


Select the table or tables and click Finish to create the Data model


You will get and .edmx file. Which will have all the tables drawn along with their relationship. Since we have selected only one table, so there is only one table depicted.


Go to solution explorer and click on Model1.Designer.cs (If you have changed the default name while creating data model to let ABC then select in solution explorer ABC.edmx.cs) 

Model1.edmx.cs

//——————————————————————————

// <auto-generated>

// This code was generated by a tool.

// Runtime Version:2.0.50727.3053

//

// Changes to this file may cause incorrect behavior and will be lost if

// the code is regenerated.

// </auto-generated>

//——————————————————————————

[assembly: global::System.Data.Objects.DataClasses.EdmSchemaAttribute()]

// Original file name:

// Generation date: 7/15/2009 8:35:01 PM

namespace DataContractSample

{


///
<summary>


/// There are no comments for kpmgdemoEntities in the schema.


///
</summary>


public
partial
class
kpmgdemoEntities : global::System.Data.Objects.ObjectContext

{


///
<summary>


/// Initializes a new kpmgdemoEntities object using the connection string found in the ‘kpmgdemoEntities’ section of the application configuration file.


///
</summary>


public kpmgdemoEntities() :


base(“name=kpmgdemoEntities”, “kpmgdemoEntities”)

{


this.OnContextCreated();

}


///
<summary>


/// Initialize a new kpmgdemoEntities object.


///
</summary>


public kpmgdemoEntities(string connectionString) :


base(connectionString, “kpmgdemoEntities”)

{


this.OnContextCreated();

}


///
<summary>


/// Initialize a new kpmgdemoEntities object.


///
</summary>


public kpmgdemoEntities(global::System.Data.EntityClient.EntityConnection connection) :


base(connection, “kpmgdemoEntities”)

{


this.OnContextCreated();

}


partial
void OnContextCreated();


///
<summary>


/// There are no comments for WCF in the schema.


///
</summary>


public
global::System.Data.Objects.ObjectQuery<WCF> WCF

{


get

{


if ((this._WCF == null))

{


this._WCF = base.CreateQuery<WCF>(“[WCF]“);

}


return
this._WCF;

}

}


private
global::System.Data.Objects.ObjectQuery<WCF> _WCF;


///
<summary>


/// There are no comments for WCF in the schema.


///
</summary>


public
void AddToWCF(WCF wCF)

{


base.AddObject(“WCF”, wCF);

}

}


///
<summary>


/// There are no comments for kpmgdemoModel.WCF in the schema.


///
</summary>


///
<KeyProperties>


/// EmpId


///
</KeyProperties>

[global::System.Data.Objects.DataClasses.EdmEntityTypeAttribute(NamespaceName=“kpmgdemoModel”, Name=“WCF”)]

[global::System.Runtime.Serialization.DataContractAttribute(IsReference=true)]

[global::System.Serializable()]


public
partial
class
WCF : global::System.Data.Objects.DataClasses.EntityObject

{


///
<summary>


/// Create a new WCF object.


///
</summary>


///
<param name=”name”>Initial value of Name.</param>


///
<param name=”empId”>Initial value of EmpId.</param>


public
static
WCF CreateWCF(string name, string empId)

{


WCF wCF = new
WCF();

wCF.Name = name;

wCF.EmpId = empId;


return wCF;

}


///
<summary>


/// There are no comments for Property Name in the schema.


///
</summary>

[global::System.Data.Objects.DataClasses.EdmScalarPropertyAttribute(IsNullable=false)]

[global::System.Runtime.Serialization.DataMemberAttribute()]


public
string Name

{


get

{


return
this._Name;

}


set

{


this.OnNameChanging(value);


this.ReportPropertyChanging(“Name”);


this._Name = global::System.Data.Objects.DataClasses.StructuralObject.SetValidValue(value, false);


this.ReportPropertyChanged(“Name”);


this.OnNameChanged();

}

}


private
string _Name;


partial
void OnNameChanging(string value);


partial
void OnNameChanged();


///
<summary>


/// There are no comments for Property EmpId in the schema.


///
</summary>

[global::System.Data.Objects.DataClasses.EdmScalarPropertyAttribute(EntityKeyProperty=true, IsNullable=false)]

[global::System.Runtime.Serialization.DataMemberAttribute()]


public
string EmpId

{


get

{


return
this._EmpId;

}


set

{


this.OnEmpIdChanging(value);


this.ReportPropertyChanging(“EmpId”);


this._EmpId = global::System.Data.Objects.DataClasses.StructuralObject.SetValidValue(value, false);


this.ReportPropertyChanged(“EmpId”);


this.OnEmpIdChanged();

}

}


private
string _EmpId;


partial
void OnEmpIdChanging(string value);


partial
void OnEmpIdChanged();

}

}

  1. This is the generated class by ADO.Net entity Data model.
  2. This class contains WCF (name of the table) partial class. See in above code , Red rectangle.
  3. WCF class is business class and contains Data members , methods and constructor.
  4. So WCF cannot expose this as Data Contract.

Service

Here we will create the DTO class and converter class.

  1. DTO class. Just right click and add a class. This class contains exactly the same number of property with exactly same data type of the business class got created by the Entity model.

WCFDTO.cs

using System;

using System.Collections.Generic;

using System.Linq;

using System.Web;

using System.ServiceModel ;

using System.Runtime.Serialization;

namespace DataContractSample

{

[DataContract]


public
class
WCFDTO

{

[DataMember]


public
string Name { get; set; }

[DataMember]


public
string EmpId { get; set; }

}

}

  1. Converter class. This class will convert WCFDTO class to WCF class and vice versa. This is a very simple static class, which is having two static methods. One to convert WCF to WCFDTO and one to convert WCFDTO to WCF.

Right click and add one more class. Give name of this class as Converter.

Converter.cs

using System;

using System.Collections.Generic;

using System.Linq;

using System.Web;

namespace DataContractSample

{


public
static
class
Converter

{


public
static
WCFDTO ConvertWCFtoWCFDTO(WCF obj)

{


WCFDTO objdto = new
WCFDTO();

objdto.EmpId = obj.EmpId ;

objdto .Name = obj.Name ;


return objdto;

}


public
static
WCF ConvertWCFDTOtoWCF(WCFDTO obj)

{


WCF objdto = new
WCF();

objdto.EmpId = obj.EmpId;

objdto.Name = obj.Name;


return objdto;

}

}

}

Service

Create the Contract. This contains operations for CRUD operation.

IService1.cs

using System;

using System.Collections.Generic;

using System.Linq;

using System.Runtime.Serialization;

using System.ServiceModel;

using System.Text;

namespace DataContractSample

{

[ServiceContract]


public
interface
IService1

{

[OperationContract]


WCFDTO Find(string empid);

[OperationContract]


List<WCFDTO> All();

[OperationContract]


void InsertData(WCFDTO obj);

[OperationContract]


void Updatedata(WCFDTO obj);

[OperationContract]


void DeleteData(WCFDTO obj);

}

}

  1. Implement the service

    This is the simple CRUD operation on ADO.Net Entity model. For complete description on how to perform CRUD operation on ADO.Net Entity model, read my other articles 

Service1.cs 

using System;

using System.Collections.Generic;

using System.Linq;

using System.Runtime.Serialization;

using System.ServiceModel;

using System.Text;

namespace DataContractSample

{


public
class
Service1 : IService1

{


kpmgdemoEntities _ent;


public
WCFDTO Find(string Empid)

{

_ent = new
kpmgdemoEntities();


WCF res = (from r in _ent.WCF where r.EmpId == Empid select r).First();


return
Converter.ConvertWCFtoWCFDTO(res);

}


public
void InsertData(WCFDTO obj)

{

_ent = new
kpmgdemoEntities();


WCF insertingobject = Converter.ConvertWCFDTOtoWCF(obj);

_ent.AddObject(“WCF”, insertingobject);

_ent.SaveChanges();

}


public
void Updatedata(WCFDTO obj)

{

_ent = new
kpmgdemoEntities();


WCF res = (from r in _ent.WCF where r.EmpId == obj.EmpId select r).First();


//WCF insertingobject = Converter.ConvertWCFDTOtoWCF(obj);

res.Name = obj.Name;

_ent.AcceptAllChanges();

}


public
void DeleteData(WCFDTO obj)

{

_ent = new
kpmgdemoEntities();


WCF res = (from r in _ent.WCF where r.EmpId == obj.EmpId select r).First();


//WCF insertingobject = Converter.ConvertWCFDTOtoWCF(obj);

_ent.DeleteObject(res);

_ent.SaveChanges();

}


public
List<WCFDTO> All()

{

_ent = new
kpmgdemoEntities();


var res = from r in _ent.WCF select r;


List<WCFDTO> abc= res.ToList().ConvertAll(new
Converter<WCF,WCFDTO>(Converter.ConvertWCFtoWCFDTO));


return abc;

}

}

Build and host the service. For my purpose, I am hosting the service in .Net Web server. You may choose any options.

 


 Client

Create a client and consume the service by adding the Service Reference.

For my purpose, I am creating a console application client in the same solution as of service.

After Console application creation, I added a Service Reference of the service. To do so, Right clicks in Service in solution explorer and add service reference.

 using System;

using System.Collections.Generic;

using System.Linq;

using System.Text;

using TestClient.ServiceReference1;

namespace TestClient

{


class
Program

{


static
void Main(string[] args)

{


Service1Client proxy = new
Service1Client();


WCFDTO result = proxy.Find(“U18949″);


Console.Read();


WCFDTO addindbobj = new
WCFDTO();

addindbobj.EmpId = “U00000000″;

addindbobj.Name = “WCF Traning”;

proxy.InsertData(addindbobj);

proxy.DeleteData(addindbobj);

proxy.Updatedata(addindbobj);


//Displaying all Result


List<WCFDTO> res = proxy.All().ToList();


foreach (WCFDTO r in res)

{


Console.WriteLine(r.Name);

}


Console.Read();

}

}

} 

This is very simple client. This is just creating a proxy and calling the operations from the service.

Conclusion

This article mainly explained how to perform CRUD operation on a table using ADO.Net Entity Data model and WCF Soap service.

Transport level Security in WCF

Objective

 This article will give a very brief introduction of transport level security in WCF

  1. When we say security at the transport layer, then the main concern is with the integrity, privacy and to certain extent authentication of the message as it travels along the wire. 
  2. In WCF, the secure transports available for use are HTTP, TCP, IP and MSMQ. 
  3. For a transport to be secured all the communication that takes place across the channel must be encrypted.

     

Advantage of using Transport security:

  • Less chances of sniffing network.
  • Less chances of Phishing network.
  • Less chances of message alteration.
  • Less chances of replay of message attack.

Regardless of the Binding used, Transport level security provides

  • Authentication of the sender.
  • Authentication of the service.
  • Message integrity
  • Message confidentiality.
  • Replay of message detection.

Different Binding and Transport Layer Security

Transport layer security is directly related to binding. The type of transport security that is available depends on binding used.

basicHttpBinding

  1. The basicHttpBinding is the only built in binding that is not secure when configured using the default value.
  2. Security could be enabled on basicHttpBinding.
  3. When security is enabled in basicHttpBinding, it is interoperate with IIS security mechanism.
  4. Security for basicHttpBinding could be configured either in declaratively in code or in configuration. 

Attributes of Transport channel

Values of attribute type

Conclusion

I discussed in very brief Transport level security in WCF

Data Contract Hierarchy in WCF

Objective 

This article will explain

  1. Data Contract hierarchy
  2. How base class and sub class are getting exposed in WCF?
  3. What is Known Type attribute
  4. Mixing of sterilization and Data Contract

Data Contract Hierarchy

 

  1. If any class in hierarchy is not attributed as [DataContract] or [serilizable] then InvalidDataContractException will occur at service run time 
  2. WCF allows mixing [DataContract] and [Serilizable] attribute. But [Serilizable] should be at the root of the DataContract hierarchy 

Examples

Mixing of DataContract and Serilizable

One problem in WCF

Follow the below code,

  1. There are two classes in hierarchy
  2. Base class is referring instance of derive class. This is perfectly valid.



Let us try to refer derive child class in base class,

Contract and classes

Error Service implantation

 


 

 


 

How to solve this problem?

KnownTypeAttribute

 

  1. The solution is to explicitly tell WCF about the sub class to the base class.
  2. This is done using KnownType Attribute class. 

    This class is defined as below in System.Runtime.Serilization namespace

  1. The KnownTypeAttribute allows designating the sub class. 

Example

 

  1. On the host side the KnownTypeAttribute affects all contracts and operations using the base class across all services and endpoints. This allows accepting subclass instead of base class.
  2. WCF includes sub class in metadata such that client can also pass the sub class instead of base class. 

ServiceKnownTypeAttribute


 

ServiceKnownTypeAttribute class

 

 

 

 

ServiceKnownType could be applied on a particular service operation or to entire service contract.