WCF学习笔记(2)---消息交换模式

WCF是基于消息的开发框架。其中,消息交换的模式一共有三种,分别为:数据报、请求/应答和双工。

 

数据报交换模式:     用于单向的消息发送。即发即弃。

请求/应答交换模式: 也叫半双工。一方请求,另一方应答。 类似于对讲机。

双工交换模式:        也叫全双工,发送者和接收者可以互发消息。类似于电话。 

 

 示例代码:

 

契约:

 1     [ServiceContract(CallbackContract = typeof(IExampleCallbackClass))]
 2     public interface IExampleClass
 3     {
 4         [OperationContract(IsOneWay = true)]
 5         void SendMessage(string message);
 6 
 7         [OperationContract()]
 8         string RequestMessage();
 9 
10         [OperationContract(IsOneWay = true)]
11         void SendMessageAgain(string message);
12     }
13 
14     public interface IExampleCallbackClass
15     {
16         [OperationContract(IsOneWay= true)]
17         void CallBack(string message);
18     } 

 

 

 实现:

 1     [ServiceBehavior(ConcurrencyMode = ConcurrencyMode.Reentrant)]
 2     public class ExampleClass : IExampleClass
 3     {
 4         public void SendMessage(string message)
 5         {
 6             Console.WriteLine("Send Message: " + message);
 7         }
 8         public string RequestMessage()
 9         {
10             return "Request and Response!";
11         }
12         public void SendMessageAgain(string message)
13         {
14             Console.WriteLine("Send message again: " + message);
15             var callBack = OperationContext.Current.GetCallbackChannel<IExampleCallbackClass>();
16             callBack.CallBack("Send Callback: " + message);
17         }
18     }
19 
20     public class ExampleCallbackClass : IExampleCallbackClass
21     {
22         public void CallBack(string message)
23         {
24             Console.WriteLine("Print Callback :" + message);
25         }
26     } 

 

调用:

 1         static void Main(string[] args)
 2         {
 3             // 启动服务
 4             WSDualHttpBinding dualBinding = new WSDualHttpBinding(WSDualHttpSecurityMode.None);
 5             dualBinding.MessageEncoding = WSMessageEncoding.Text;
 6 
 7             Uri address = new Uri("http://localhost:8000/Datapram", UriKind.Absolute);
 8             ServiceHost svc = new ServiceHost(typeof(ExampleClass));
 9             svc.AddServiceEndpoint(typeof(IExampleClass), dualBinding, address);
10             svc.Open();
11 
12             Console.WriteLine("WCF服务已经启动!");
13 
14             // 调用服务
15             WSDualHttpBinding remoteBinding = new WSDualHttpBinding(WSDualHttpSecurityMode.None);
16             EndpointAddress remoteAddress = new EndpointAddress(
17                 new Uri("http://localhost:8000/Datapram", UriKind.Absolute));
18 
19             IExampleCallbackClass callBack = new ExampleCallbackClass();
20             IExampleClass proxy = DuplexChannelFactory<IExampleClass>.CreateChannel(callBack, remoteBinding, remoteAddress);
21 
22             //数据报交换模式
23             proxy.SendMessage("some message");
24 
25             // 请求应答模式
26             string responseString = proxy.RequestMessage();
27             Console.WriteLine("收到服务器的应答:" + responseString);
28 
29             // 双工
30             proxy.SendMessageAgain("message");
31 
32             Console.WriteLine("服务调用成功!");
33             Console.ReadLine();
34         }
35     } 

 

数据报和请求/调用的绑定,可以使用 WSHttpBinding 来做,因为,三种方式都写入到一个示例里,所以用了 WSDualHttpBinding。 

 

需要注意的部分:在IExampleClass 的实现中,需要声明特性:[ServiceBehavior(ConcurrencyMode = ConcurrencyMode.Reentrant)].如果不声明,运时的时候会报"操作将死锁..."的异常。出现这个异常的原因是:在默认的情况下,服务的执行按Single并发模式进行,也就是说在服务执行全程,服务对象只能被一个线程访问。WCF通过加锁机制保证服务对象的独占性使用,也就是说在服务执行开始会对服务对象加锁,该锁在服务操作结束之后释放。

 

posted @ 2012-04-26 16:48  Gene Li  阅读(232)  评论(0编辑  收藏  举报