zoukankan      html  css  js  c++  java
  • WCF扩展系列

    原文地址:http://www.cnblogs.com/Creator/archive/2011/05/21/2052687.html

    这个系列的第一部分将会重点关注WCF行为(behaviors),WCF提供了四种类型的行为:服务行为、终结点行为、契约行为和操作行为。这些行为的接口几乎是所有WCF的扩展入口。本篇文章只是对行为拓展讲述一些基础的铺设,具体到上面四个行为的扩展以及使用案例,将会在后续的文章中讲到.

    Behaviors

    上述这四个行为的所定义的接口分别是IServiceBehavior,IEndpointBehavior,IContractBehavior以及 IOperationBehavior。虽然是四个不同的接口,但它们的接口方法却基本相同,分别为 AddBindingParameters(),ApplyClientBehavior()以及ApplyDispatchBehavior()。注意,IServiceBehavior由于只能作用在服务端,因此并不包含ApplyClientBehavior()方法

    public interface I[Service/Endpoint/Contract/Operation]Behavior { 
                    void Validate(DescriptionObject); 
                    void AddBindingParameters(DescriptionObject, BindingParameterCollection); 
                    void ApplyDispatchBehavior(DescriptionObject, RuntimeObject); 
                    void ApplyClientBehavior(DescriptionObject, RuntimeObject); // not on IServiceBehavior 
    }

    其中的方法描述如下:

    • AddBindingParameters用于向绑定元素传递自定义数据,以支持协定实现。
    • Validate:用于检查服务宿主和服务说明,从而确定服务是否可成功运行。
    • Apply[Client/Dispatch]Behavior这是我们可以引用和修改WCF运行时对象的地方,也是用得最多的行为方法(大部分情况,上两个方法都会留空)。用于更改运行时属性值或插入自定义扩展对象(例如错误处理程序、消息或参数拦截器、安全扩展以及其他自定义扩展对象)。

    他们各自的作用范围如下图所示(引用自张逸):

    image

    增加一个行为(behaviors )

    向WCF中增加行为有三种不同的方法:

      • 代码:service / endpoint / contract / operation 的描述类有一个behaviors集合属性,我们可以通过他简单的增加一个行为,具体做法,先将自定义服务行为添加到 Behaviors 属性,然后对 System.ServiceModel.ServiceHost 对象调用 ICommunicationObject.Open 方法。

      • 配置文件:通过配置文件system.serviceModel/behaviors 节点,我们可以指定service behaviors 和 endpoint behaviors,已达到添加行为的目的

      • 特性: 添加行为的简单方法是使用特性 — — 除了终结点行为。通过创建特性类 (基类型 = = System.Attribute) 和实现其中一个行为接口,您可以将特性应用于适当的元素,并添加行为到元素的描述。下面的代码显示了一个简单的服务,基于特性的行为的添加以及输出它们的调用顺序 (以及通过代码添加终结点行为)。

      1 using System;
      2 using System.Collections.ObjectModel;
      3 using System.Reflection;
      4 using System.ServiceModel;
      5 using System.ServiceModel.Channels;
      6 using System.ServiceModel.Description;
      7 using System.ServiceModel.Dispatcher;
      8 
      9 namespace Behaviors
     10 {
     11     class MyServiceBehaviorAttribute : Attribute, IServiceBehavior
     12     {
     13         public void AddBindingParameters(ServiceDescription serviceDescription, ServiceHostBase serviceHostBase, Collection<ServiceEndpoint> endpoints, BindingParameterCollection bindingParameters)
     14         {
     15             Console.WriteLine("Inside {0}.{1}", this.GetType().Name, MethodBase.GetCurrentMethod().Name);
     16         }
     17 
     18         public void ApplyDispatchBehavior(ServiceDescription serviceDescription, ServiceHostBase serviceHostBase)
     19         {
     20             Console.WriteLine("Inside {0}.{1}", this.GetType().Name, MethodBase.GetCurrentMethod().Name);
     21         }
     22 
     23         public void Validate(ServiceDescription serviceDescription, ServiceHostBase serviceHostBase)
     24         {
     25             Console.WriteLine("Inside {0}.{1}", this.GetType().Name, MethodBase.GetCurrentMethod().Name);
     26         }
     27     }
     28 
     29     class MyEndpointBehavior : IEndpointBehavior
     30     {
     31         public void AddBindingParameters(ServiceEndpoint endpoint, BindingParameterCollection bindingParameters)
     32         {
     33             Console.WriteLine("Inside {0}.{1}, endpoint {2}", this.GetType().Name, MethodBase.GetCurrentMethod().Name, endpoint.Name);
     34         }
     35 
     36         public void ApplyClientBehavior(ServiceEndpoint endpoint, ClientRuntime clientRuntime)
     37         {
     38             Console.WriteLine("Inside {0}.{1}, endpoint {2}", this.GetType().Name, MethodBase.GetCurrentMethod().Name, endpoint.Name);
     39         }
     40 
     41         public void ApplyDispatchBehavior(ServiceEndpoint endpoint, EndpointDispatcher endpointDispatcher)
     42         {
     43             Console.WriteLine("Inside {0}.{1}, endpoint {2}", this.GetType().Name, MethodBase.GetCurrentMethod().Name, endpoint.Name);
     44         }
     45 
     46         public void Validate(ServiceEndpoint endpoint)
     47         {
     48             Console.WriteLine("Inside {0}.{1}, endpoint {2}", this.GetType().Name, MethodBase.GetCurrentMethod().Name, endpoint.Name);
     49         }
     50     }
     51 
     52     class MyContractBehaviorAttribute : Attribute, IContractBehavior
     53     {
     54         public void AddBindingParameters(ContractDescription contractDescription, ServiceEndpoint endpoint, BindingParameterCollection bindingParameters)
     55         {
     56             Console.WriteLine("Inside {0}.{1}, contract {2}", this.GetType().Name, MethodBase.GetCurrentMethod().Name, contractDescription.ContractType.Name);
     57         }
     58 
     59         public void ApplyClientBehavior(ContractDescription contractDescription, ServiceEndpoint endpoint, ClientRuntime clientRuntime)
     60         {
     61             Console.WriteLine("Inside {0}.{1}, contract {2}", this.GetType().Name, MethodBase.GetCurrentMethod().Name, contractDescription.ContractType.Name);
     62         }
     63 
     64         public void ApplyDispatchBehavior(ContractDescription contractDescription, ServiceEndpoint endpoint, DispatchRuntime dispatchRuntime)
     65         {
     66             Console.WriteLine("Inside {0}.{1}, contract {2}", this.GetType().Name, MethodBase.GetCurrentMethod().Name, contractDescription.ContractType.Name);
     67         }
     68 
     69         public void Validate(ContractDescription contractDescription, ServiceEndpoint endpoint)
     70         {
     71             Console.WriteLine("Inside {0}.{1}, contract {2}", this.GetType().Name, MethodBase.GetCurrentMethod().Name, contractDescription.ContractType.Name);
     72         }
     73     }
     74 
     75     class MyOperationBehaviorAttribute : Attribute, IOperationBehavior
     76     {
     77         public void AddBindingParameters(OperationDescription operationDescription, BindingParameterCollection bindingParameters)
     78         {
     79             Console.WriteLine("Inside {0}.{1}, operation {2}", this.GetType().Name, MethodBase.GetCurrentMethod().Name, operationDescription.Name);
     80         }
     81 
     82         public void ApplyClientBehavior(OperationDescription operationDescription, ClientOperation clientOperation)
     83         {
     84             Console.WriteLine("Inside {0}.{1}, operation {2}", this.GetType().Name, MethodBase.GetCurrentMethod().Name, operationDescription.Name);
     85         }
     86 
     87         public void ApplyDispatchBehavior(OperationDescription operationDescription, DispatchOperation dispatchOperation)
     88         {
     89             Console.WriteLine("Inside {0}.{1}, operation {2}", this.GetType().Name, MethodBase.GetCurrentMethod().Name, operationDescription.Name);
     90         }
     91 
     92         public void Validate(OperationDescription operationDescription)
     93         {
     94             Console.WriteLine("Inside {0}.{1}, operation {2}", this.GetType().Name, MethodBase.GetCurrentMethod().Name, operationDescription.Name);
     95         }
     96     }
     97 
     98     [ServiceContract]
     99     [MyContractBehavior]
    100     public interface ITest
    101     {
    102         [OperationContract]
    103         [MyOperationBehavior]
    104         int Add(int x, int y);
    105         [OperationContract]
    106         int Multiply(int x, int y);
    107     }
    108 
    109     [ServiceContract]
    110     [MyContractBehavior]
    111     public interface ITest2
    112     {
    113         [OperationContract]
    114         [MyOperationBehavior]
    115         string Echo(string text);
    116     }
    117 
    118     [MyServiceBehavior]
    119     public class Service : ITest, ITest2
    120     {
    121         public int Add(int x, int y) { return x + y; }
    122         public int Multiply(int x, int y) { return x * y; }
    123         public string Echo(string text) { return text; }
    124     }
    125 
    126     class Program
    127     {
    128         static void Main(string[] args)
    129         {
    130             string baseAddress = "http://" + Environment.MachineName + ":8000/Service";
    131             ServiceHost host = new ServiceHost(typeof(Service), new Uri(baseAddress));
    132             ServiceEndpoint ep1 = host.AddServiceEndpoint(typeof(ITest), new BasicHttpBinding(), "basic");
    133             ep1.Name = "Endpoint1-BasicHttp";
    134             ep1.Behaviors.Add(new MyEndpointBehavior());
    135             ServiceEndpoint ep2 = host.AddServiceEndpoint(typeof(ITest2), new WSHttpBinding(), "ws");
    136             ep2.Name = "Endpoint2-WSHttp";
    137             ep2.Behaviors.Add(new MyEndpointBehavior());
    138             Console.WriteLine("Opening the host...");
    139             host.Open();
    140             Console.WriteLine("Host opened");
    141         }
    142     }
    143 }

          我并不认为这就是“最优”的添加方法,他只是描述通过特性增加行为的一个特定的例子而已,具体什么是“最优”的添加行为的方法呢?其实这就像软件架构一样,永远没有最好的架构,只有最合适的架构。所以具体项目里面采用哪种方式去添加来得具体情况具体分析。个人比较喜欢用使用配置文件添加的方法….


     在后面的文章中将会讲诉到具体的行为扩展,敬请期待..

            1.1.1. IServiceBehavior 
            1.1.2. IContractBehavior 
            1.1.3. IEndpointBehavior 
            1.1.4. IOperationBehavior


    博客地址:Zealot Yin

    欢迎转载,转载请注明出处[http://creator.cnblogs.com/]

  • 相关阅读:
    四则运算 2
    《你的灯亮着吗》读后感 (前两篇)
    四则运算设计思路
    读书目标
    课堂总结
    人月神话感想
    软件工程概论11
    软件工程概论10
    bnu——GCD SUM (莫比乌斯反演)
    POJ1108_Split Windows 解题报告
  • 原文地址:https://www.cnblogs.com/niaowo/p/4727378.html
Copyright © 2011-2022 走看看