文章详情

短信预约-IT技能 免费直播动态提醒

请输入下面的图形验证码

提交验证

短信预约提醒成功

WCF如何实现双向通信

2023-06-30 13:23

关注

这篇文章主要介绍“WCF如何实现双向通信”,在日常操作中,相信很多人在WCF如何实现双向通信问题上存在疑惑,小编查阅了各式资料,整理出简单好用的操作方法,希望对大家解答”WCF如何实现双向通信”的疑惑有所帮助!接下来,请跟着小编一起来学习吧!

请求过程中的回调

这是一种比较典型的双工消息交换模式的表现形式,客户端在进行服务调用的时候,附加上一个回调对象;服务在对处理该处理中,通过客户端附加的回调对象(实际上是调用回调服务的代理对象)回调客户端的操作(该操作在客户端执行)。整个消息交换的过程实际上由两个基本的消息交换构成,其一是客户端正常的服务请求,其二则是服务端对客户端的回调。两者可以采用请求-回复模式,也可以采用单向(One-way)的MEP进行消息交换。图1描述了这样的过程,服务调用和回调都采用请求-回复MEP。

WCF如何实现双向通信

图1

我们沿用计算服务的例子。在这之前,我们都是调用CalculuateService直接得到计算结果,并将计算结果通过控制台输出。在本例中我们将采用另外一种截然不同的方式调用服务并进行结果的输出:我们通过单向(One-way)的模式调用CalculuateService(也就是客户端不可能通过回复消息得到计算结果),服务端在完成运算结果后,通过回调(Callback)的方式在客户端将计算结果打印出来。

一:定义服务契约和回调契约

首先进行服务契约的定义,我们照例通过接口(ICalculator)的方式定义服务契约,作用于指定加法运算的Add操作,我们通过OperationContractAttribute特性的IsOneway属性将操作定义成单向的操作,这意味着客户端仅仅是向服务端发送一个运算的请求,并不会通过回复消息得到任何运算结果。

[ServiceContract(Namespace = "http://www.artech.com/", CallbackContract = typeof(ICallback))]//回调契约的类型通过ServiceContractAttribute特性的CallbackContract属性进行指定。public interface ICalculator{    [OperationContract(IsOneWay = true)]    void Add(double x, double y);}
//回调契约public interface ICallback //由于定义ICalculator的时候已经通过[ServiceContract(CallbackContract=typeof(ICallback))]指明ICallback是一个服务契约了,所以ICallback不再需要添加ServiceContractAttribute特性。{    [OperationContract(IsOneWay = true)]//服务端不需要回调的返回值,索性将回调操作也设为单向方法。    void DisplayResult(double x, double y, double result);}

二:实现服务

在实现了上面定义的服务契约ICalculator的服务CalculatorService中,实现了Add操作,完成运算和结果显示的工作。结果显示是通过回调的方式实现的,所以需要借助于客户端提供的回调对象(该对象在客户端调用CalculatorService的时候指定,在介绍客户端代码的实现的时候会讲到)。在WCF中,回调对象通过当前OperationContext的GetCallback<T>方法获得(T代表回调契约的类型)。

public class CalculatorService : ICalculator{    public void Add(double x, double y)    {        double result = x + y;        ICallback callback = OperationContext.Current.GetCallbackChannel<ICallback>();        callback.DisplayResult(x, y, result);    }}

注: OperationContext在WCF中是一个非常重要、也是一个十分有用的对象,它代表服务操作执行的上下文。我们可以通过静态属性Current(OperationContext.Current)得到当前的OperationContext。借助OperationContext,我们可以在服务端或者客户端获取或设置一些上下文,比如在客户端可以通过它为出栈消息(outgoing message)添加SOAP报头,以及HTTP报头(比如Cookie)等。在服务端,则可以通过OperationContex获取在客户端设置的SOAP报头和HTTP报头。关于OperationContext的详细信息,可以参阅MSDN在线文档。

三:服务寄宿

我们通过一个控制台应用程序完成对CalculatorService的寄宿工作,并将所有的服务寄宿的参数定义在配置文件中。由于双工通信依赖于一个双工的信道栈,即依赖于一个能够支持双工通信的绑定,在此我们选用了NetTcpBinding。

<system.serviceModel>       <behaviors>       <services>           <service name = "Artech.DuplexServices.Services.CalculatorService">                <endpoint address = "net.tcp://127.0.0.1:9999/CalculatorService"  binding = "netTcpBinding" contract = "Artech.DuplexServices.Contracts.ICalculator"/>             </service>         </services> </system.serviceModel>

注: 在WCF预定义绑定类型中,WSDualHttpBinding和NetTcpBinding均提供了对双工通信的支持,但是两者在对双工通信的实现机制上却有本质的区别。WSDualHttpBinding是基于HTTP传输协议的;而HTTP协议本身是基于请求-回复的传输协议,基于HTTP的通道本质上都是单向的。WSDualHttpBinding实际上创建了两个通道,一个用于客户端向服务端的通信,而另一个则用于服务端到客户端的通信,从而间接地提供了双工通信的实现。而NetTcpBinding完全基于支持双工通信的TCP协议。

using (ServiceHost host = new ServiceHost(typeof(CalculatorService))){    host.Open();    Console.Read();}

四:实现回调契约与服务调用

在客户端程序为回调契约提供实现,在下面的代码中CalculateCallback实现了回调契约ICallback,在DisplayResult方法中对运算结果进行输出。

class CalculateCallback : ICallback{    public void DisplayResult(double x, double y, double result)    {        Console.WriteLine("x + y = {2} when x = {0} and y = {1}", x, y, result);    }}

接下来实现对双工服务的调用,下面是相关的配置和托管程序。在服务调用程序中,通过DuplexChannelFactory<TChannel>创建服务代理对象,DuplexChannelFactory<TChannel>和ChannelFactory<TChannel>的功能都是一个服务代理对象的创建工厂,不过DuplexChannelFactory<TChannel>专门用于基于双工通信的服务代理的创建。在创建DuplexChannelFactory<TChannel>之前,先创建回调对象,并通过InstanceContext对回调对象进行包装。

<system.serviceModel>     <client>         <endpoint name = "CalculatorService" address = "net.tcp://127.0.0.1:9999/CalculatorService" binding = "netTcpBinding" contract = "Artech.DuplexServices.Contracts.ICalculator"/>     </client> </system.serviceModel>
InstanceContext instanceContext = new InstanceContext(new CalculateCallback());using (DuplexChannelFactory<ICalculator> channelFactory = new DuplexChannelFactory<ICalculator>(instanceContext, "CalculatorService")){    ICalculator proxy = channelFactory.CreateChannel();    using (proxy as IDisposable)    {        proxy.Add(1, 2);        Console.Read();    }}

注意:如果采用WsDualHttpBinding,由于回调的服务监听地址采用的默认端口是80,在IIS 5.x以及之前的版本中,80端口是IIS独占的监听端口。WsDualHttpBinding定义了一个ClientBaseAddress使你能很容易地改变回调服务的基地址。对于我们给出的案例,我们只要通过下面的配置将clientBaseAddress设为可用的地址(http://127.0.0.1:8888/ CalculatorService) 
< bindings >
     < wsDualHttpBinding >
         < binding name = "MyBinding" clientBaseAddress = "http://127.0.0.1:8888/calculatecallback" />
        </ wsDualHttpBinding >
  </ bindings >

到此,关于“WCF如何实现双向通信”的学习就结束了,希望能够解决大家的疑惑。理论与实践的搭配能更好的帮助大家学习,快去试试吧!若想继续学习更多相关知识,请继续关注编程网网站,小编会继续努力为大家带来更多实用的文章!

阅读原文内容投诉

免责声明:

① 本站未注明“稿件来源”的信息均来自网络整理。其文字、图片和音视频稿件的所属权归原作者所有。本站收集整理出于非商业性的教育和科研之目的,并不意味着本站赞同其观点或证实其内容的真实性。仅作为临时的测试数据,供内部测试之用。本站并未授权任何人以任何方式主动获取本站任何信息。

② 本站未注明“稿件来源”的临时测试数据将在测试完成后最终做删除处理。有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341

软考中级精品资料免费领

  • 历年真题答案解析
  • 备考技巧名师总结
  • 高频考点精准押题
  • 2024年上半年信息系统项目管理师第二批次真题及答案解析(完整版)

    难度     813人已做
    查看
  • 【考后总结】2024年5月26日信息系统项目管理师第2批次考情分析

    难度     354人已做
    查看
  • 【考后总结】2024年5月25日信息系统项目管理师第1批次考情分析

    难度     318人已做
    查看
  • 2024年上半年软考高项第一、二批次真题考点汇总(完整版)

    难度     435人已做
    查看
  • 2024年上半年系统架构设计师考试综合知识真题

    难度     224人已做
    查看

相关文章

发现更多好内容

猜你喜欢

AI推送时光机
位置:首页-资讯-后端开发
咦!没有更多了?去看看其它编程学习网 内容吧
首页课程
资料下载
问答资讯