Hello WCF

WCF对我来讲既熟悉又陌生,说它熟悉,是因为看过几本关于它的书籍和一些博客,对他有一些基本的了解(用熟悉可能是有点过了!);又因为在项目中还没有用到过,所以缺乏相应的项目经验,所以看起来又陌生。
因为公司要涉及到WCF的相关内容,所以再留意一下这个技术。整个WCF当然不是几篇博文就能学习的透,讲的清楚的,整个认识,只有经过一定项目的锻炼才能达到认识层次的提升。

说到书籍,园子里的牛人Artech写过关于WCF的书籍,这里写下自己的读后的2点感觉,虽然我只看了上册:

1.有些内容从英文翻译过来后,Artech翻译的有点照本宣科,句子的组织让我很难受,很难理解!查阅英文的相关文章进行比较,很难看出写得是同一个东西。

2.有些简单的东西搞得很复杂,觉得作者好像在刻意影藏什么或是把简单的东西写得复杂点来凸显自己技术的牛x;有些复杂的东西,又简单带过,好比前面是一堵墙,作者以为给我们读者打了一个洞,刻意洞悉其中的奥秘,可事实是:我这个没有WCF实际项目经验的WCF Beginner 很难抓住作者的“良苦用心”。

当然我没有否定作者的技术厉害,因为与生俱来的对于强者的尊重。只是个人觉得作者技术强大的同时,能认真组织下语句,做好英文-汉语语言的组织,以更贴近本意的分享MS技术。毕竟你写的书是给程序员看的,不是中央的红头文件或是政府报告什么的。

以上发点牢骚,青年请跳过,也没有攻击作者技术的意思,只是一个读者用朴实的语言提出的一点点诚恳的建议,真希望市面上能出现一本像刘铁锰那样把WPF讲的深入浅出的入门书籍!

-----

今天这个程序是这样的:实现一个WCF服务(ClassLibrary),建立一个宿主寄宿这个服务(Winform),建立一个客户端调用这个服务(Console)。

这里不采用VS提供的WCF模板,也不适用VS自带的WCF宿主寄宿WCF,因为这个你打开VS NEW一个就来了。

下面Step by step:

1.在新建一个WcfCalculatorSecvice类库。

在项目中添加一个实现WCF服务契约的接口IAddCalculator.cs,注意项目需要添加System.ServiceModel.dll的引用,并引入相应的名称空间。如下:

using System.ServiceModel;//需要添加System.ServiceModel引用

namespace WcfCalculatorService
{
    [ServiceContract]
    public interface IAddCalculator
    {
        [OperationContract]
        int Add(int a,int b);
    }
}

再添加一个实现这个接口的类AddCalculator.cs,如下:

namespace WcfCalculatorService
{
    public class AddCalculator:IAddCalculator 
    {

        #region IAddCalculator 成员

        public int Add(int a, int b)
        {
            return a + b;
        }

        #endregion
    }
}

OK,服务就算建好了。

2.在解决方案中添加一个名为Host的Winform程序。设计如下:

点击按钮启动服务,按钮的Click事件处理如下,因为使用了ServiceHost,所以也要添加System.ServiceModel.dll的引用,并引入相应的名称空间。

using System.ServiceModel;//同样添加这个引用
private void button1_Click(object sender, EventArgs e)
{
    //把这个服务公开出去
    ServiceHost host = new ServiceHost(typeof(WcfCalculatorService.AddCalculator ));

    try
    {
       host.Open();
       listBox1.Items.Add("服务已经启动!");
    }
    catch(Exception ex)
    {
       listBox1.Items.Add("出现异常!"+ex.Message );
    }
}

 为了使WCF服务能够成功的开启,我们需要在Host中添加一个配置文件。

 App.config配置如下:

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
  <system.serviceModel>
    <services>
      <service name="WcfCalculatorService.AddCalculator"  behaviorConfiguration="AddCalculatorBehavior">
        <host>
          <baseAddresses>
            <add baseAddress ="http://192.168.1.64:2012/MyAddCalculatorService"/>
          </baseAddresses>
        </host>

        <endpoint address="" binding="wsHttpBinding" contract="WcfCalculatorService.IAddCalculator" bindingConfiguration="noSecurity"/>
      </service>
    </services>

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

    <bindings>
      <wsHttpBinding>
        <binding name="noSecurity">
          <security mode="None"/>
        </binding>
      </wsHttpBinding>
    </bindings>
    
  </system.serviceModel>
</configuration>

OK,到这里我们就建立了一个WCF服务,并通过一个Winform寄宿这个服务。
程序运行如下:

 为了证明服务确实已经开启,这时,我们在另外一台计算机上通过基地址http://192.168.1.64:2012/MyAddCalculatorService 访问这个服务:

 通过点击http://192.168.1.64:2012/MyAddCalculatorService?wsdl,获得其服务描述如下:

View Code
  <?xml version="1.0" encoding="utf-8" ?> 
- <wsdl:definitions name="AddCalculator" targetNamespace="http://tempuri.org/" xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/" xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/" xmlns:soapenc="http://schemas.xmlsoap.org/soap/encoding/" xmlns:wsu="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soap12="http://schemas.xmlsoap.org/wsdl/soap12/" xmlns:tns="http://tempuri.org/" xmlns:wsa="http://schemas.xmlsoap.org/ws/2004/08/addressing" xmlns:wsp="http://schemas.xmlsoap.org/ws/2004/09/policy" xmlns:wsap="http://schemas.xmlsoap.org/ws/2004/08/addressing/policy" xmlns:wsaw="http://www.w3.org/2006/05/addressing/wsdl" xmlns:msc="http://schemas.microsoft.com/ws/2005/12/wsdl/contract" xmlns:wsa10="http://www.w3.org/2005/08/addressing" xmlns:wsx="http://schemas.xmlsoap.org/ws/2004/09/mex" xmlns:wsam="http://www.w3.org/2007/05/addressing/metadata">
- <wsp:Policy wsu:Id="WSHttpBinding_IAddCalculator_policy">
- <wsp:ExactlyOne>
- <wsp:All>
  <wsaw:UsingAddressing /> 
  </wsp:All>
  </wsp:ExactlyOne>
  </wsp:Policy>
- <wsdl:types>
- <xsd:schema targetNamespace="http://tempuri.org/Imports">
  <xsd:import schemaLocation="http://192.168.1.64:2012/MyAddCalculatorService?xsd=xsd0" namespace="http://tempuri.org/" /> 
  <xsd:import schemaLocation="http://192.168.1.64:2012/MyAddCalculatorService?xsd=xsd1" namespace="http://schemas.microsoft.com/2003/10/Serialization/" /> 
  </xsd:schema>
  </wsdl:types>
- <wsdl:message name="IAddCalculator_Add_InputMessage">
  <wsdl:part name="parameters" element="tns:Add" /> 
  </wsdl:message>
- <wsdl:message name="IAddCalculator_Add_OutputMessage">
  <wsdl:part name="parameters" element="tns:AddResponse" /> 
  </wsdl:message>
- <wsdl:portType name="IAddCalculator">
- <wsdl:operation name="Add">
  <wsdl:input wsaw:Action="http://tempuri.org/IAddCalculator/Add" message="tns:IAddCalculator_Add_InputMessage" /> 
  <wsdl:output wsaw:Action="http://tempuri.org/IAddCalculator/AddResponse" message="tns:IAddCalculator_Add_OutputMessage" /> 
  </wsdl:operation>
  </wsdl:portType>
- <wsdl:binding name="WSHttpBinding_IAddCalculator" type="tns:IAddCalculator">
  <wsp:PolicyReference URI="#WSHttpBinding_IAddCalculator_policy" /> 
  <soap12:binding transport="http://schemas.xmlsoap.org/soap/http" /> 
- <wsdl:operation name="Add">
  <soap12:operation soapAction="http://tempuri.org/IAddCalculator/Add" style="document" /> 
- <wsdl:input>
  <soap12:body use="literal" /> 
  </wsdl:input>
- <wsdl:output>
  <soap12:body use="literal" /> 
  </wsdl:output>
  </wsdl:operation>
  </wsdl:binding>
- <wsdl:service name="AddCalculator">
- <wsdl:port name="WSHttpBinding_IAddCalculator" binding="tns:WSHttpBinding_IAddCalculator">
  <soap12:address location="http://192.168.1.64:2012/MyAddCalculatorService" /> 
- <wsa10:EndpointReference>
  <wsa10:Address>http://192.168.1.64:2012/MyAddCalculatorService</wsa10:Address> 
  </wsa10:EndpointReference>
  </wsdl:port>
  </wsdl:service>
  </wsdl:definitions>

3.建立一个名为Client的客户端,调用WCF服务。新建一个Client的Console程序,通过基地址http://192.168.1.64:2012/MyAddCalculatorService添加服务引用:

Console程序的源码如下:

using System;

namespace Client
{
    class Program
    {
        static void Main(string[] args)
        {
            //
            ServiceReferenceCalculator.AddCalculatorClient client = new ServiceReferenceCalculator.AddCalculatorClient();
            int result = client.Add(30, 40);
            Console.WriteLine("The Result is "+result );

            Console.ReadKey();
        }
    }
}

为了显示WCF的分布式效果,在另一台主机上运行这个Client。

结果如下:

 希望对你有帮助~

posted @ 2012-12-25 13:48  DebugLZQ  阅读(737)  评论(5编辑  收藏  举报