刚刚学习WCF,自己的理解还比较少,比较书面化,希望以后可以更加了解和熟悉它。
首先了解客户端和服务器端的通信:ABC:地址(address)、绑定(binding)、契约(contract)
A——地址:定义网络消息送达之处,即端点接受消息处,客户端必须将消息送到此处。
B——绑定:绑定定义的是与端点通信的信道(或通道)(channel),即信息的传输方式。
(1、最底层的绑定元素是传输(transport),他负责在网络上传递信息。
(2、内置的传输包括HTTP、TCP、命名管道(Named Pipes)、PeerChannel和MSMQ。
(3、在此之上的绑定元素规定安全(security)和事务(transactions)
C——契约,即内容。定义端点提供的功能和功能的集合。契约定义了端点对外发布的操作以及这些操作所要求的消息格式。
首先创建一个简单的WCF程序及调用,先看一下程序的结构。
1、创建一个服务契约
WCF采用基于契约的交互方式实现了服务的自治,以及客户端和服务端之间的松耦合。WCF包含四种类型的契约:服务契约、数据契约、消息契约和错误契约,这里着重于服务契约。从功能上讲,服务契约抽象了服务提供的所有操作;而站在消息交换的角度来看,服务契约则定义了基于服务调用的消息交换过程中,请求消息和回复消息的结构,以及采用的消息交换模式。一般地,我们通过接口的形式定义服务契约。代码如下
1 using System;
2 using System.Collections.Generic;
3 using System.Linq;
4 using System.Runtime.Serialization;
5 using System.ServiceModel;
6 using System.ServiceModel.Web;
7 using System.Text;
8
9 namespace WcfDemo
10 {
11 // 注意: 使用“重构”菜单上的“重命名”命令,可以同时更改代码和配置文件中的接口名“IService1”。
12 [ServiceContract]
13 public interface IService1
14 {
15
16 [OperationContract]
17 string GetData(int value);
18
19 [OperationContract]
20 string GetDataUsingDataContract(string composite);
21
22 // TODO: 在此添加您的服务操作
23 }
24 }
WCF广泛采用基于自定义特性(Custom Attribtue)的声明式编程模式,我们通过在接口上应用System.ServiceModel.ServiceContractAttribute特性将一个接口定义成服务契约。
以上是定义了一个IService1的服务契约。
2、创建服务
当服务契约成功创建时,我们需要通过实现服务契约来创建具体的WCF服务。WCF服务Service1实现了契约接口IService1。
// 注意: 使用“重构”菜单上的“重命名”命令,可以同时更改代码、svc 和配置文件中的类名“Service1”。 public class Service1 : IService1 { public string GetData(int value) { return string.Format("{0}", value); } public string GetDataUsingDataContract(string composite) { if (composite == null) { throw new ArgumentNullException("composite"); } if (composite!="") { composite += "姓名"; } return composite; } }
3、配置WCF服务
WCF服务寄宿通过一个特殊的对象完成:ServiceHost。在上面的例子中,基于WCF服务的类型(typeof(CalculatorService))创建了ServieHost对象,并添加了一个终结点。具体的地址为http://localhost:8000/WCFDemo,采用了WSHttpBinding,并指定了服务契约的类型IService1。代码如下:
public class service { public static void Main() { ServiceHost serviceHost = new ServiceHost(typeof(Service1), new Uri("http://localhost:8000/WCFDemo")); serviceHost.AddServiceEndpoint( typeof(IService1), new BasicHttpBinding(), ""); ServiceMetadataBehavior behavior = new ServiceMetadataBehavior(); behavior.HttpGetEnabled = true; serviceHost.Description.Behaviors.Add(behavior); serviceHost.AddServiceEndpoint(typeof(IMetadataExchange), MetadataExchangeBindings.CreateMexHttpBinding(), "mex"); serviceHost.Open(); Console.WriteLine("Pree <ENTER> to terminate.\n\n"); Console.ReadLine(); serviceHost.Close(); } }
在进行真正的WCF应用开发时,一般不会直接通过编码的方式进行终结点的添加和服务行为的定义,而是通过配置的方式进行。一般是对Web.config或App.config文件进行配置,或者可以用VS的工具菜单栏中的WCF服务配置编辑器来配置WCF。
4、WCF服务的寄宿
WCF服务有两种寄宿的方式,一种是通过IIS托管,另一种是WCF自我寄宿。在这里我通过IIS托管的方式来展示。寄宿IIS的服务包含两个步骤:一是为WCF服务创建.svc文件,二是创建IIS虚拟目录。之后创建一个控制台应用程序来调用寄宿的WCF服务。代码如下:
[ServiceContract] public interface IService1 { [OperationContract] string GetData(int value); [OperationContract] string GetDataUsingDataContract(string composite); // TODO: 在此添加您的服务操作 } static void Main(string[] args) { ChannelFactory<IService1> my = new ChannelFactory<IService1>( new BasicHttpBinding(), new EndpointAddress("http://localhost:8000/Service1.svc")); IService1 wcf = my.CreateChannel(); string s = wcf.GetData(51); string name = "我是谁?"; name = wcf.GetDataUsingDataContract("名字:" + name + "数字:" + s); Console.WriteLine(name); //Console.WriteLine("运行了,结果是" + s); Console.ReadLine(); } }
在这里我是通过ChannelFactory<T>来调用WCF的服务,ChannelFactory<T>本质上是通过指定的终结点创建用于进行服务调用的服务代理。在上面的代码中,在创建ChannelFactory<T>的时候再在构造函数中指定终结点的相关要素(契约通过范型类型表示,地址和绑定则通过参数指定)。在真正的WCF应用中,大都采用配置的方式进行终结点的定义。