好得很程序员自学网

<tfoot draggable='sEl'></tfoot>

HTTP与Tcp协议下双工通信的差异

HTTP与Tcp协议下双工通信的差异

WCF中经常会使用HTTP协议与Tcp协议来实现双工通讯,对应使用的协议分别为WsDualHttpBinding、NetTcpBinding。

HTTP是基于应用层的协议,而Tcp是基于传输层的协议。Tcp经过三次握手建立起客户端到服务端的可靠连接,发起请求的客户端与回调客户端的服务端都使用一个连接就能完成。使用HTTP协议时,从客户端到服务端发起请求到服务端返回给客户端回复完成后,连接就关闭。

由于HTTP的这种无连接性,基于WsDualHttpBinding的双工在进行通讯时实际上服务端在回调客户端时,会与NetTcpBinding在使用上有些差异。

 

1、NetTcpBinding实现双工

1.1契约部分:

1.1.1 契约接口定义:

    [ServiceContract(CallbackContract =  typeof (ICallback))]
     public   interface  ICalculator
    {
        [OperationContract]
         void  Add( double  x,  double  y);
    }

 

1.1.2 回调接口定义:

     public   interface  ICallback
    {
        [OperationContract]
         void  Display( double  x,  double  y ,  double  result);
    }

 

1.2服务实现:

 

         public   void  Add( double  x,  double  y) 

        {
            Console.WriteLine( " 开始Add计算 " );
            ICallback callback = OperationContext.Current.GetCallbackChannel<ICallback>();
            callback.Display(x, y, x + y);
            Console.WriteLine( string .Format( " {0},{1} " , x, y));
        }

服务通过OperationContext.Current.GetCallbackChannel<T>泛型方法获取对客户端回调代理类,对客户端进行回调

  

    public  T GetCallbackChannel<T>() 

    {
         if  (( this .channel !=  null ) && ! this .IsUserContext)
        {
             return  (T)  this .channel.Proxy;
        }
         return   default (T);
    }

 

 

1.3 服务端配置:

 

<system.serviceModel>

 <services>
            <service name= " Services.CalculatorServices " >
                <endpoint address= " Calaulator "  binding= " netTcpBinding "  contract= " Contract.ICalculator " ></endpoint>
                <host>
                    <baseAddresses>
                        <add baseAddress= " net.tcp://127.0.0.1:6688 " />
                    </baseAddresses>
                </host>
            </service>        
        </services>
</system.serviceModel>

 

1.4 客户端部分:

 

回调接口的实现:

 

      public   void  Display( double  x,  double  y,  double  result) 

    {
            Console.WriteLine( string .Format( " {0}+{1}={2} " , x, y, result));
    }

客户端配置:

 

<system.serviceModel>        

<client>
            <endpoint address= " net.tcp://127.0.0.1:6688/Calaulator "  binding= " netTcpBinding "  contract= " Contract.ICalculator "  name= " calculatorTcp " ></endpoint>
        </client>
</system.serviceModel>

 

接口调用:

            InstanceContext context =  new  InstanceContext( new  CallBack());
             using  ( var  channelFactory =  new  DuplexChannelFactory<ICalculator>(context,  " calculatorTcp " ))
            {
                ICalculator proxy = channelFactory.CreateChannel();
                proxy.Add( 1.0 ,  2.0 );
                Console.ReadLine();
            }

结果如下图:

服务端:

 

客户端:

 

 

 

2、WsDualHttpBinding实现双工。

同样以上面的契约为例.在数据包、或者请求-响应模式中,如果更换协议一般只需更改所使用的绑定即可。我们将客户端配置改为如下:

 

<system.serviceModel>       
 <client>
            <endpoint address= " http://127.0.0.1:8866/Calaulator/ws "  binding= " wsDualHttpBinding "  contract= " Contract.ICalculator "  name= " calculatorWsDual "  ></endpoint>
        </client>
</system.serviceModel>

 

然后使用calculatorWsDual重新生成ChannelFactory:

using  ( var  channelFactory =  new  DuplexChannelFactory<ICalculator>(context,  " calculatorWsDual " ))

运行调试:有如下异常:

解决办法为Endpoint配置绑定行为,如下:

<system.serviceModel>       
     <bindings>
            <wsDualHttpBinding>
                <binding name = " myWsDualBinding "  clientBaseAddress= " http://127.0.0.1:3636/Service/CallbackService " ></binding>
            </wsDualHttpBinding>
        </bindings>
        <client>
            <endpoint address= " http://127.0.0.1:8888/Service/Calculator "   binding= " wsDualHttpBinding "  contract= " Contracts.ICalculator "   name= " calculatorService "  bindingConfiguration= " myWsDualBinding " />
        </client>

</system.serviceModel>  

 

 这样,问题就得以解决

 

分类:  WCF基础

作者: Leo_wl

    

出处: http://www.cnblogs.com/Leo_wl/

    

本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。

版权信息

查看更多关于HTTP与Tcp协议下双工通信的差异的详细内容...

  阅读:38次