zoukankan      html  css  js  c++  java
  • 初学WCF之消息模式3——双工模式

      昨天终于下定决心计划这个月要把WCF学完,之所以安排一个月的时间,我不要只是学些表面的东西,我要比较深入的去学习下它。如果只学些表面的东西,我想一般的人花个一周的时间就够了。最近一段时间想要学的东西感觉太多了,想学习下Silverlight、WPF、WCF、MVC等,但总感觉好像很忙似的,我也不知道我在忙些什么,就这样稀里糊涂的一天就过去,一事无成。昨天晚上终于想起了5月份写的一个计划规则,还是按照这个计划规则去写每天的计划、日记、月计划。这样每天做了些什么,每天应该做些什么,目标很明确,再也不会像以前那样,想学Silverlight、WPF、WCF、MVC等,一会儿想看下Silverlight,一会儿想看下WPF,一会儿想等找到份工作再去学习它们。像这样下去这些东西的皮毛都没有学到,而且这样又把自己累得要死。 人们总喜欢说计划赶不变化,我觉得这没有什么道理,我觉得只要你计划的合理的话,这个计划肯定不会难产的。这是我最近的状况总结。费话说的有点多了,还大家见谅。。。呵呵!下面主要是和大家分享下我今天所学的双工模式。

      这个其实不难,但让我花比较长的时间,咱天生有点愚笨,没办法,所以特意记录下,以免下次又忘记了。

      双工模式的特点是:无论使用单向消息发送还是请求/答复消息发送方式,服务和客户端均能够独立地向对方发送消息。对于必须直接与客户端通信或向消息交换的任意一方提供异步体验(包括类似于事件的行为)的服务来说,这种双向通信形式非常有用。

      由于存在与客户端通信的附加机制,双工模式比请求/答复或单向模式要略为复杂。

      若要设计为双工协定,还必须设计回调协定,并将该回调协定的类型分配给标记服务协定的ServiceContractAttribute属性(attribute)的CallbackContract属性(protery)。

      若要实现双工模式,您必须创建第二个接口,该接口包含在客户端调用的方法声明。(以上四段话摘自:MSDN Webcasts 徐长龙讲的《跟我一起从零开始学WCF系列课程》的第二章,希望大家能充分理解这四段的意思,我今花了比较长的时间来学这个双工模式,就是因为没有注意看这四段话,没有理解好。)。

      下面我们就来创建一个WCF项目吧!

      点击确定,就这样创建了一个WCF项目了。简单吧。。。

    目录如下:

    你把IService1.cs和Serivce1.cs删除了也可以,没事的,咱就懒得删除了。咱把IService1.cs和Serivce1.cs里面的内容全部删除了。以下是IService1.cs文件里的内容:

    namespace WcfServiceLibrary4
    {
        [ServiceContract(Namespace = "http://Microsoft.ServiceMode.Samples", SessionMode = SessionMode.Required, CallbackContract = typeof(IB))]
        //定义一个服务接口
        public interface IA
        {
            [OperationContract(IsOneWay=true)]
            void Clear();
        }
        //这个是服务端调用客户端里方法的一个接口,在客户端里写一个类继承这个接口时,你是找到不IB这个接口的名字的,上面的CallbackContract = typeof(IB)这句话指定的回调的接口是IB,但它是以IACallback的形式出现的
        public interface IB
        {
            [OperationContract(IsOneWay=true)]
            void E(double e);
        }
    }

    以下是Serivce1.cs里面的代码:

    namespace WcfServiceLibrary4
    {
        [ServiceBehavior(InstanceContextMode=InstanceContextMode.PerSession)]
        public class A : IA
        {
            double result;
            //声明一个IB接口的对象
            IB ib = null;
            //A类的构造方法
            public A()
            {
                result = 0.0D;
                //实例化一个IB
                ib = OperationContext.Current.GetCallbackChannel<IB>();
            }
            public void Clear()
            {
                //服务端调用客户端的E方法
                ib.E(result + 9);
            }
        }
    }

      然后把App.config配置文件修改下就可以了。

      本来是这样的:

     <service name="WcfServiceLibrary4.Service1" behaviorConfiguration="WcfServiceLibrary4.Service1Behavior">
            <host>
              <baseAddresses>
                <add baseAddress = "http://localhost:8731/Design_Time_Addresses/WcfServiceLibrary4/Service1/" />
              </baseAddresses>
            </host>
            <!-- Service Endpoints -->
            <!-- 除非完全限定,否则地址将与上面提供的基址相关 -->
            <endpoint address ="" binding="wsHttpBinding" contract="WcfServiceLibrary4.IService1">

      修改后:

    <service name="WcfServiceLibrary4.A" behaviorConfiguration="WcfServiceLibrary4.Service1Behavior">
            <host>
              <baseAddresses>
                <add baseAddress = "http://localhost:8731/Design_Time_Addresses/WcfServiceLibrary4/A/" />
              </baseAddresses>
            </host>
            <!-- Service Endpoints -->
            <!-- 除非完全限定,否则地址将与上面提供的基址相关 -->
            <endpoint address ="" binding="wsDualHttpBinding" contract="WcfServiceLibrary3.IA">

      一定要把wsHttpBinding改成wsDualHttpBinding,请大家仔细对照下。

      下面实现客户端的调用吧,不过端还得实现服务端IB的接口。

      我在这个项目里添加了个命令项目,你添加个WebFrom项目或者Windows项目也可以的。

      哦,差点忘了应该先生成下服务,然后再在命令项目里右击“引用”选择“添加服务引用",不要点错了哦。

      然后我们开始在Program.cs里添加如下代码:

    //请记得添加以下两个命名空间
    using System.ServiceModel;
    using ConsoleApplication1.ServiceReference1;
    
    namespace ConsoleApplication1
    {
        /// <summary>
        /// 我今天主要是在B继承一个接口这个花了很长的时间,我总以为能找到服务端里的IB接口,谁知道服务端的接口IB是IACallback的形式出现在客户端
        /// </summary>
        public class B:IACallback
        {
            #region IACallback 成员
         //实现了IB接口的E方法
            public void E(double e1)
            {
                Console.WriteLine("E:" + e1);
            }#endregion
        }
        class Program
        {
            static void Main(string[] args)
            {
                InstanceContext instanceContext = new InstanceContext(new B());
                ServiceReference1.AClient client = new AClient(instanceContext);
                client.Clear();
                Console.ReadKey();
            }
        }
    }

      Demo下载

      欢迎大家拍砖,咱家正在建房......,如果你是烧砖厂的,欢迎你一车砖一车砖的拍,咱高兴的很呐,时间也不早了,明天早上还要去面试,该洗洗睡了,晚安各位基友。。。

    欢迎访问草根帮【https://www.caogenbang.top】 草根帮带你走向人生巅峰,迎娶白富美!!!
  • 相关阅读:
    String、StringBuffer、StringBuilder
    动态规划引入—矩阵乘法
    flask中间件
    有状态服务,无状态服务
    python 工厂模式
    python 单例模式
    python 工厂模式
    python timedelta() 和relativedelta()的区别
    mongo 查看(集合)表结构
    logstash 实现数据源分流
  • 原文地址:https://www.cnblogs.com/koeltp/p/2583807.html
Copyright © 2011-2022 走看看