代码改变世界

WCF学习笔记(1)-- 一个简单的wcf实例

2011-07-29 14:54  通心菜  阅读(1221)  评论(3编辑  收藏  举报

WCF的服务不能孤立地存在,需要寄宿于一个运行着的进程中,我们把承载WCF服务的进程称为宿主,为服务指定宿主的过程称为服务寄宿(Service Hosting)。

我们要用WCF来实现一个远程调用计算的方法

步骤一:构建整个解决方案

通过VS 2008创建一个空白的解决方案,添加如下四个项目。项目的类型、承载的功能和相互引用关系如下,整个项目在VS下的结构如图2所示。

  • Contracts一个类库项目,定义服务契约(Service Contract),添加引用System.ServiceMode程序集;
  • Services一个类库项目,提供对WCF服务的实现。定义在该项目中的所有WCF服务实现了定义在Contracts中相应的服务契约,所以Services具有对Contracts项目的引用;
  • Hosting一个控制台(Console)应用,实现对定义在Services项目中的服务的寄宿,该项目须要同时引用Contracts和Services两个项目和System.ServiceMode程序集;
  • Application一个控制台应用模拟服务的客户端,该项目引用System.ServiceMode程序集。

  • 步骤二:创建服务契约
    先在Contracts定义一个接口 IOperation
    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using System.ServiceModel;
    
    namespace WcfServices.Contracts
    {
    
    	[ServiceContract(Name = "OperationService")]
    	public interface IOperation
    	{
    		[OperationContract]
    		double Add(double x, double y);
    
    	}
    }
    
    步骤三:创建服务
    在Services层来实现这个接口
    当服务契约成功创建时,我们需要通过实现服务契约来创建具体的WCF服务。WCF服务OperationService定义在Services项目中,实现了服务契约接口IOperation,实现了所有的服务操作。OperationService定义如下:
    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using WcfServices.Contracts;
    
    namespace WcfServices.Services
    {
    	public class OperationService:IOperation
    	{
    
    		#region IOperation 成员
    
    		public double Add(double x, double y)
    		{
    			return x + y;
    		}
    
    		#endregion
    	}
    }
    

    步骤四:通过自我寄宿的方式寄宿服务

    WCF服务需要依存一个运行着的进程(宿主),服务寄宿就是为服务指定一个宿主的过程。WCF是一个基于消息的通信框架,采用基于终结点(Endpoint)的通信手段。终结点由地址(Address)、绑定(Binding)和契约(Contract)三要素组成,如图3所示。由于三要素应为首字母分别为ABC,所以就有了易于记忆的公式:Endpoint = ABC。一个终结包含了实现通信所必需的所有信息,我们可以这样认识终结点的ABC:

  • 地址(Address):地址决定了服务的位置,解决了服务寻址的问题,
  • 绑定(Binding):绑定实现了通信的所有细节,包括网络传输、消息编码,以及其他为实现某种功能(比如安全、可靠传输、事务等)对消息进行的相应处理。WCF中具有一系列的系统定义绑定,比如BasicHttpBinding、WsHttpBinding、NetTcpBinding等
  • 契约(Contract):契约是对服务操作的抽象,也是对消息交换模式以及消息结构的定义。
    服务寄宿的目的就是开启一个进程,为WCF服务提供一个运行的环境。通过为服务添加一个或多个终结点,使之暴露给潜给的服务消费者。服务消费者最终通过相 匹配的终结点对该服务进行调用。我们可以完全通过代码的方式完成所有的服务寄宿工作,下面的代码体现了通过一个控制台应用对 OperationService的寄宿
    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using WcfServices.Services;
    using WcfServices.Contracts;
    using System.ServiceModel;
    using System.ServiceModel.Description;
    
    namespace WcfServices.Hosting
    {
        class Program
        {
    		static void Main(string[] args)
    		{
    
    			using (ServiceHost host = new ServiceHost(typeof(OperationService)))
    			{
    
    				host.Opened += delegate
    				{
    
    					Console.WriteLine("OperationService已经启动,按任意键终止服务!");
    
    				};
    
    
    
    				host.Open();
    
    				Console.Read();
    
    			}
    
    		}
    
        }
    }
    

    然后我门要写一些配置信息 在Hosting下添加一个应用程序配置文件

    代码如下 也可以通过 工具--wcf服务配置工具来生成 (见这里 )

    <?xml version="1.0" encoding="utf-8"?>
    <configuration>
    <system.serviceModel>

    <behaviors>
    <serviceBehaviors>
    <behavior name="NewBehavior">
    <serviceMetadata httpGetEnabled="true" />

    </behavior>
    </serviceBehaviors>
    </behaviors>

    <services>
    <service behaviorConfiguration="NewBehavior" name="WcfServices.Services.OperationService">
    <endpoint address="" binding="basicHttpBinding" bindingConfiguration=""
    contract
    ="WcfServices.Contracts.IOperation" />
    <host>
    <baseAddresses>
    <add baseAddress="http://127.0.0.1:9999/OperationService" />
    </baseAddresses>
    </host>
    </service>
    </services>

    </system.serviceModel>
    </configuration>

    来测试下服务是否能启动 Hosting 里的Program.cs 加入如下代码
    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using WcfServices.Services;
    using WcfServices.Contracts;
    using System.ServiceModel;
    using System.ServiceModel.Description;

    namespace WcfServices.Hosting
    {
    class Program
    {
    static void Main(string[] args)
    {

    using (ServiceHost host = new ServiceHost(typeof(OperationService)))
    {

    host.Opened
    += delegate
    {

    Console.WriteLine(
    "OperationService已经启动,按任意键终止服务!");

    };



    host.Open();

    Console.Read();

    }

    }

    }
    }

    按F5启动测试


    服务启动了?我们来测试下 在浏览器中输入我们配置的

    baseAddress地址  http://127.0.0.1:9999/OperationService 
  • 出现下面的图示 则OK(有个配置节点决定是否显示元数据 后面在讲)


    步骤五:创建客户端调用服务

    同样
    在Application里添加配置文件
    <?xml version="1.0" encoding="utf-8" ?>
    <configuration>
        <system.serviceModel>

           
            <client>
                <endpoint address="http://127.0.0.1:9999/OperationService"
                          binding="basicHttpBinding"
                          contract="WcfServices.Contracts.IOperation"
                          name="OperationService"></endpoint>
            </client>
           
        </system.serviceModel>
       
    </configuration>


    Program.cs 代码

  • using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using System.ServiceModel;
    using WcfServices.Contracts;
    using System.IO;
    namespace WcfServices.Client
    {
    class Program
    {
    static void Main(string[] args)
    {
    using (ChannelFactory<IOperation> channelFactory = new ChannelFactory<IOperation>("OperationService"))
    {
    IOperation proxy
    = channelFactory.CreateChannel();

    using (proxy as IDisposable)
    {
    Console.WriteLine(
    "x + y = {2} when x = {0} and y = {1}", 1, 2, proxy.Add(1, 2));
    }
    }

    Console.Read();
    }
    }
    }


    OK 先开启服务端 对Hosting 点右键 在点调试 选启动新实例 然后在Application 也是一样操作

    调用成功! 附带源代码