一、WCF 中的绑定和绑定模型
作为终结点的三要素之一的绑定,它创建信道层的信道栈。WCF 是基于消息的通信方式,在信道层中,若干信道首尾相连组成了信道栈,它提供一个消息传输和处理的通道。通过信道、信道监听器、信道工厂等元素共同构成WCF 绑定模型,在整个绑定模型中,信道和信道栈位于最底层。
WCF 绑定模型图
二、信道、信道监听器、信道工厂
通信对象(CommunicationObject )
在WCF 中每种信道都是直接或间接实现了 System.ServiceModel.Channels.IChannel 接口,而IChannel 类型又实现了 System.ServiceModel.ICommunicationObject 接口。
ICommunicationObject 类型提供了统一的管理通信对象的状态机, 他的属性成员 State 是 System.ServiceModel.CommunicationState 类型表示通信对象的当前状态,这些状态体现为:被创建(Created)、正在开启(Opening)、已经开启(Opened)、正在关闭(Closing)、已经关闭(Closed)、出错(Faulted),他们分别能对应到 ICommunicationObject 类型中的Opening/Opened 、Closing/Closed 和 Faulted 事件。通过ICommunicationObject 类型中的Open、Close 和 Abort 方法分别能对通信进行开启、关闭和中止。
在开启一个通信时可以设置一个超时时限,WCF 为所有需要超时设置的通信对象,定义了一个默认超时接口 System.ServiceModel.IDefaultCommunicationTimeouts。在改接口中定义了分别代表开启(OpenTimeout)、关闭(CloseTimeout)、发送(SendTimeout)和接收(ReceiveTimeout)4中操作的默认超时时限。
信道(IChannel和ChannelBase)
在IChannel 接口中定义了一个很重要的的方法 GetProperty<T> ,它能探测信道是否具有某种能力会特性的一种有效方法。WCF还定义了一个实现了该几口的抽象类 ChannelBase,它还继承 CommunicationObject 类型 和 IDefaultCommunicationTimeouts 类型。
在System.ServiceModel.Channels 命名空间下定义了IOutputChannel/IInputChannel、IRequsetChannel/IReplyChannel 和IDuplexChannel 等信道接口,他们分别基于数据报模式、请求-回复模式和双工模式3中消息交换模式在发送端和接收端组成信道栈。
信道层的可扩展性主要体现在可以通过自定义信道的方式实现针对消息的某种处理,比如:压缩消息。信道存在于由多个信道组成的信道栈中,一个不处于栈尾的信道,在处理消息后一般会把处理后的消息传递给后一个信道(执行本信道的方法以后,获得下一个信道并执行同名的方法)。在信道栈中按照功能可将信道分成:
(1)传输信道(TransportChannel,实现基于某种网络协议的消息传输,如:Http,Https,Tcp,MSMQ和Named Pipes等);
(2)消息编码信道(Message Encoding Channel,实现对消息的编码,常见消息编码方式Text/XML、Binary和MTOM);
(3)协议信道(Protocol Channel,实现WCF对若干WS-*协议的支持)
信道监听器(IChannelListener 和 ChannelListenerBaase )
服务启动的时候,对应信道监听器被开启并绑定到某个URI 进行请求的监听。信道监听器实现了接口 System.ServiceModel.Channels.IChannelListener ,它的GetProperty<T> 成员用于返回基于指定类型的属性,Uri 成员返回真正的监听地址。在WCF 中还定义了泛型接口 System.ServiceModel.Channels.IChannelListener<TChannel> ,泛型参数实现了IChannel 接口,代表信道监听器创建的基于某种信道形状的信道。WCF 中还定义 System.ServiceModel.Channels.ChannelListenerBaase 和 System.ServiceModel.Channels.ChannelListenerBase<TChannel>俩个抽象类,作为信道监听器的基类。
信道工厂(IChannelFactory 和 ChannelFactoryBase )
信道工厂是信道管理器在客户端的别名,信道工厂起到创建用于发送请求和接收回复的信道的作用。WCF 为信道工厂定义了 System.ServiceModel.Channels.IChannelFactory 和 System.ServiceModel.Channels.IChannelFactory<TChannel> 两个接口,他们都继承 ICommunicationObject 接口。WCF 还为信道工厂定义 System.ServiceModel.Channels.ChannelFactoryBase 和 System.ServiceModel.Channels.ChannelFactory<TChannel> 两个抽象基类,作为所有信道工厂的基类。
三、绑定
绑定元素(BindingElement)
绑定元素的作用是实现对信道监听器和信道工厂的创建,WCF 中定义了一个绑定元素的基类 System.ServiceModel.Channels.BindingElement。它有两个核心方法 BuildChannelListener<TChannel> 和 BuildChannelFactory<TChannel> 分别用于创建信道监听器和信道工厂,参数都是代表绑定上下文的 BindingContext 对象。
绑定(Binding)
WCF 中所有的绑定都直接或间接的继承自 System.ServiceModel.Channels.Binding 类型。Binding 通过抽象方法 CreateBindingElement 创建组成该绑定对象的每一个绑定元素,这些绑定元素构成的有序集合就是一个绑定。绑定中一系列 BuildChannelListener<TChannel> 和 BuildChannelFactory<TChannel> 方法用于创建基于指定信道类型的信道监听器管道和信道工厂管道。Binding 中的只读属性 BindingContext 代表创建绑定上下文的绑定对象,BindingContext 有两个重要的 BuildChannelListener<TChannel> 和 BuildChannelFactory<TChannel> 方法,通过绑定创建的信道监听器管道和信道工厂管道就是通过调用这两个方法实现的。
WCF 中定义了很多的系统绑定,比如:BasicHttpBinding、WSHttpBinding、WS2007HttpBinding、WSDualHttpBinding、 NetMsmqBinding 、NetTcpBinding、NetNamedPipeBinding,这些绑定类型用于WCF 客户端和服务端直接进行通信。我们还可以通过 System.ServiceModel.Channels.CustomBinding 类型创建自定义绑定,从而重组绑定元素的顺序。
服务在寄宿的时候都需要为服务定义一个或多个终结点,每个终结点都具有一个banding的属性。终结点绑定既可以通过编程声明的方式指定,也可以通过配置指定绑定和绑定元素及属性。在 <system.serviceModel> 配置节点中具有一个 <bindings> 子节点,所有的系统绑定(如:<wsHttpBinding> 和 <netTcpBinding> 等)和自定义绑定(<CustomBinding>)节点都定义在<Bindings> 节点中,这些绑定配置节点中能够定义一组有具体名称的绑定,每个具体绑定对应一个<binding> 元素。在终结点配置中有一个bindingConfiguration 属性,通过他的值匹配具有相同名称的具体绑定。
绑定配置片段:
1: <configuration>
2: <system.serviceModel>
3: <bindings>
4: <customBinding>
5: <binding name="MyCustomBinding">
6: <lifeCycleTracking />
7: <tcpTransport />
8: <textMessageEncoding />
9: </binding>
10: </customBinding>
11: <wsHttpBinding>
12: <binding name="MyWSHttpBanding">
13: <security mode="TransportWithMessageCredential"></security>
14: </binding>
15: </wsHttpBinding>
16: </bindings>
17: <!--自定义绑定元素配置-->
18: <extensions>
19: <bindingElementExtensions>
20: <add name="lifeCycleTracking" type="Stone.SimpleSessionBindingElementExtensions"/>
21: </bindingElementExtensions>
22: </extensions>
23: <services>
24: <service name="MyService">
25: <endpoint binding="customBanding"
26: bindingConfiguration="MyCustomBinding"
27: contract="MyContract" address="net.tcp://127.0.0.1:98/MyService" ></endpoint>
28: <endpoint binding="wsHttpBanding"
29: bindingConfiguration="MyWSHttpBanding"
30: contract="MyContract" address="http://127.0.0.1:98/MyService"></endpoint>
31: </service>
32: </services>
33: </system.serviceModel>
34: </configuration>
绑定通过在对信道层的信道、信道监听器、信道工厂和绑定元素及绑定进行自定义实现扩展,因此绑定的核心还是信道层的信道、信道监听器和信道工厂。
本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。