WCF分布式开发步步为赢(2)自定义托管宿主WCF解决方案开发配置过程详解

 

    上一节《WCF分布式框架基础概念》我们介绍了WCF服务的概念和通信框架模型,并给出了基于自定义托管服务的WCF程序的实现代码。考虑到WCF分布式开发项目中关于托管宿主服务配置和客户端添加引用。两个环节最容易出错。对于大部分想学习WCF分布式开发的人来说,成功开发、配置、部署第一个自己的WCF服务困难重重。很多资料都介绍了WCF的基本概念。但是对于实际的项目开发过程介绍粗略,给入门者带来诸多不便。今天我们就来补充一节WCF分布式开发一个完整解决方案的开发和配置过程。本节基本结构是:首先介绍【1】WCF服务解决方案的项目组成【2】WCF服务的开发和配置过程,【3】自定义宿主的开发和配置过程【4】客户端的服务引用和配置过程。【总结】算是为各位WCF分布式技术开发的爱好者,提供的一个开发参考。

【1】WCF服务解决方案的项目组成:

1.1】WCF服务:

    通常来说,WCF服务由三个部分构成:

  • 服务类:包含服务契约、操作契约和数据契约的定义和实现;

  • 宿主:一种应用程序域和进程,服务将在该环境中运行;

  • 终结点:由客户端用于访问服务。

我们这里的解决方案包括服务类项目、托管宿主、和简单的客户端程序,结构如图:

1.2】客户端应用程序:

     上一节我们介绍了WCF的基本概念,WCF基本通信机制是基于SOAP消息,SOAP消息基于XML语言,因此WCF应用程序可与运行于各种上下文环境的其他进程进行通信,当然也支持跨系统、跨平台的应用程序之间的数据交互。基于WCF构建的分布式应用程序可与下列所有程序进行交互:

  • 同一 Windows 计算机上不同进程中的WCF应用程序。

  • 另一 Windows 计算机上的WCF应用程序。

  • 基于其他技术构建的应用程序,如基于 Java 2 企业版 (J2EE) 构建的、支持标准 Web 服务的应用程序服务器。这些应用程序可以运行在 Windows 计算机上,也可以运行在其他操作系统(如 Sun Solaris、IBM 的 z/OS 或 Linux)上。

    因此可以作为客户端的应用程序,并不限制其类型,只要可以解析基于XML的SOAP消息,都可以与WCF的服务端进行通信。.NET平台上我们可以创建控制台应用程序、WinForm、Windows服务、ASP.NET应用程序等,来访问和调用WCF服务。下面我们就来具体介绍自定义托管服务,WCF解决方案的开发配置的详细过程。

【2】WCF服务类的开发过程:

    要创建WCF服务解决方案,首先应该定义服务类,并编写服务类的相关的代码。我们这里把服务类创建类单独的类库项目,托管宿主程序项目引用服务类的程序集。

2.0】创建WCF服务类库项目:

    WCF服务类库项目的创建非常简单,Visual Studio 2008为我们提供了便捷的方式,选择新建项目,选择--WCF服务类库项目项目,输入项目名称,选择保存位置就可以。如图:

     当然我们也可以建立空项目,但是程序集引用等操作要手动完整,过程相对复杂。这里我们选择的使用创建向导方式。

System.ServiceModel和System.Runtime.Serialization程序集对WCF服务至关重要,因为后续服务契约、操作契约和数据契约等特性定义都在这两个程序集中。我们在新建的项目引用中可以看到:

    使用WCF契约相关的属性,必须显示引用这两个命名空间.语句如下:

  using System.ServiceModel;
  using System.Runtime.Serialization;

   如果不添加命名空间引用程序集,编写的代码会出现错误,无法通过。

2.1】服务契约和操作契约:

    WCF服务类库创建完毕后,我们可以来进行代码的实际编写。我们知道,每个WCF服务类均需实现一些方法,以供其客户端使用。服务类的创建者通过将这些方法包含在某个服务契约中,来决定将哪些方法公开为客户可调用的操作。服务契约就是显示指定的服务必须实现的用户可以使用的操作。

   ServiceContract 属性以及 WCF使用的所有其他属性均在 System.ServiceModel 命名空间中定义,类声明使用 using 语句来引用该命名空间。服务类中可被客户端调用的每个方法都必须使用名为 OperationContract 的另一个属性加以标记。服务类中带有前置 OperationContract 属性的所有方法都将自动被WCF公开为 SOAP 可调用操作。

    WCF中最基本的属性是 ServiceContract。实际上,WCF服务类本身就是标记有 ServiceContract 属性的类或者是实现了标记有该属性的接口的类。我们使用的还是上次的代码:

    首先是服务契约IWCFService,定义了连个操作,添加[OperationContract]属性标记

 //1.服务契约
    [ServiceContract(Namespace = "http://www.cnblogs.com/frank_xl/")]
    
public interface IWCFService
    {
        
//操作契约
        [OperationContract]
        
string SayHello(string name);
        
//操作契约
        [OperationContract]
        
string SayHelloToUser(User user);

    }
【3】自定义宿主的开发和配置过程:

    我们这里使用的控制台程序为托管宿主,我们这里讲解托管宿主的代码编写和配置文件的设置过程。

3.1】托管宿主程序的创建:

   使用VS2008新建控制台应用程序,非常简单,选择新建项目-控制台程序,即可。

3.2】托管宿主代码编写:

   这里要添加对WCF服务类库项目的引用,另外要引用ServiceModel程序集。ServiceHost类位于ServiceModel命名空间下。这里比较重要的步骤就是,定义一个ServiceHost实例,定义地址,定义终结点使用ABC地址、契约、绑定。

代码如下:

 //反射方式创建服务实例,
            
//Using方式生命实例,可以在对象生命周期结束时候,释放非托管资源
            using (ServiceHost host = new ServiceHost(typeof(WCFService.WCFService)))
            {
                
//相同的服务注册多个基地址
                
//添加服务和URI,用户资源标识符
                Uri tcpAddress = new Uri("NET.tcp://localhost:8001/WCFService");
                Uri httpAddress 
= new Uri("http://localhost:8002/WCFService");
                Uri pipeAddress 
= new Uri("NET.pipe://localhost:8002/WCFService");
                host.AddServiceEndpoint(
typeof(WCFService.IWCFService), new NETTcpBinding() , tcpAddress);
                host.AddServiceEndpoint(
typeof(WCFService.IWCFService), new WSHttpBinding(), httpAddress);
                host.AddServiceEndpoint(
typeof(WCFService.IWCFService), new NETNamedPipeBinding(), pipeAddress);
                
//判断是否以及打开连接,如果尚未打开,就打开侦听端口
                if (host.State !=CommunicationState.Opening)
                host.Open();
                
//显示运行状态
                Console.WriteLine("Host is runing! and state is {0}",host.State);
                
//等待输入即停止服务
                Console.Read();
            
            
            }
【4】客户端的服务引用、配置和开发过程:

    服务类和服务宿主已经配置完毕,下面我们来讲述客户端添加WCF服务的引用、配置和服务调用过程。

    首先要运行宿主程序,这样才能在客户端添加服务引用,从元数据获取服务类的相关信息,生成本地类。

4.1】添加WCF服务引用:

  服务浏览器,单击客户端项目,添加Services Reference.在弹出的窗口地址里输入服务的基地址,首先查找TCP服务。

保持地址和配置文件里服务的基地址相同,:查找成功后的窗口如下:

  我们可以看到WCF服务类公布的操作,输入命名空间的名字为ServiceReferenceTcp。同样的方式添加对HTTP服务的引用。添加成功后我们可以查看所有文件,在客户端项目的服务引用的窗口看到所有的服务引用的文件信息如图:

证明我们添加WCF服务成功。客户端app.config文件里会生成相应的服务代理的相关信息,包括客户端终结点的信息:

<client>
            
<endpoint address="http://localhost:8001/WCFService" binding="wsHttpBinding"
                bindingConfiguration
="WSHttpBinding_IWCFService" contract="ServiceReferenceTcp.IWCFService"
                name
="WSHttpBinding_IWCFService">
                
<identity>
                    
<userPrincipalName value="FRANK/Administrator" />
                
identity>
            
endpoint>
            
<endpoint address="NET.tcp://localhost:8002/WCFService" binding="NETTcpBinding"
                bindingConfiguration
="NETTcpBinding_IWCFService" contract="ServiceReferenceTcp.IWCFService"
                name
="NETTcpBinding_IWCFService">
                
<identity>
                    
<userPrincipalName value="FRANK/Administrator" />
                
identity>
            
endpoint>
            
<endpoint address="http://localhost:8001/WCFService" binding="wsHttpBinding"
                bindingConfiguration
="WSHttpBinding_IWCFService1" contract="ServiceReferenceHttp.IWCFService"
                name
="WSHttpBinding_IWCFService1">
                
<identity>
                    
<userPrincipalName value="FRANK/Administrator" />
                
identity>
            
endpoint>
            
<endpoint address="NET.tcp://localhost:8002/WCFService" binding="NETTcpBinding"
                bindingConfiguration
="NETTcpBinding_IWCFService1" contract="ServiceReferenceHttp.IWCFService"
                name
="NETTcpBinding_IWCFService1">
                
<identity>
                    
<userPrincipalName value="FRANK/Administrator" />
                
identity>
            
endpoint>
        
client>

NET技术WCF分布式开发步步为赢(2)自定义托管宿主WCF解决方案开发配置过程详解,转载需保留来源!

郑重声明:本文版权归原作者所有,转载文章仅为传播更多信息之目的,如作者信息标记有误,请第一时间联系我们修改或删除,多谢。