WCF开发实战

WCF开发实战

 

一、 服务器应用开发

()    创建“WCF服务库

文件(F)”->“新建项目(P)...”打开新建项目对话框。在左侧的项目类型中选择“WCF”,然后再在右侧的模板中选择“WCF服务库
在下面的名称文本框中,填写我们要创建的WCF服务库的项目名称“WcfEmployee”


点击确定,会创建出我们的WCF服务库项目,在解决方案中会自动为我们生成两个类文件“IService1.cs”“Service1.cs”


这两个类文件是两个WCF示例文件,对我们开发没有什么用处,现在我们删掉这两个文件。

创建Employee实体类
解决方案窗口中,我们右击Services项目名,选择添加,再单击

在弹出的添加新项窗口中,选择,并在名称文本框中写入项名称“Employee.cs”

为Employee实体类编写代码
 

using System.Runtime.Serialization;

namespace WcfEmployee

{

 [DataContract]

public class Employee

    {

[DataMember]

        public string EmployeeId;

[DataMember]

        public string EmployeeName;

[DataMember]

        public int EmployeeAge;

    }

}


为了保证此类在WCF调用中能够被序列化,我们在Employee类上面加入[DataContract]标签,在每个需要序列化的成员变量上加入[DataMember]标签。这两个标签在使用的进候需要导入using System.Runtime.Serialization命名空间。
到此为至,我们创建完了需要在服务中传输的复杂的数据类型Employee

创建服务接口
创建服务接口,声明对外发布的类和方法。
解决方案窗口中,我们右击WcfEmployee项目名,选择添加,再单击

在弹出的添加新项窗口中,选择,并在名称文本框中写入项名称“IEmployeeSrv.cs”


在此类文件中我们编写服务接口,代码如下:
using System.Collections.Generic;

using System.ServiceModel;

 

namespace WcfEmployee

{

  [ServiceContract]

public interface IEmployeeSrv

    {

  [OperationContract]

        void AddEmployees(Employee employee);

[OperationContract]

        List<Employee> GetAllEmployees();

 [OperationContract]

        void RemoveEmployee(string id);

 

    }

}

 


IEmployeeSrv接口上面,我们定义了[ServiceContract]标签,此标签代表此接口及实现此接口的类都是对外发布的Service类,在每个需要对外发布的方法上都加上[OperationContract]标签,以使外部可以访问到此方法。
[ServiceContract][OperationContract]这两个标签需要导入using System.ServiceModel命名空间。

创建实现服务接口的类
实现我们上面声明的服务接口,实现对Employee的添加、删除和检索的具体功能。
解决方案窗口中,我们右击WcfEmployee项目名,选择添加,再单击

在弹出的添加新项窗口中,选择,并在名称文本框中写入项名称“EmployeeSrv.cs”


在此类文件中编写代码实现IEmployeeSrv.cs服务接口。
 

 

using System.Collections.Generic;

using System.ServiceModel;

 

namespace WcfEmployee

{

 [ServiceBehavior(InstanceContextMode=InstanceContextMode.Single)]

 

public class EmployeeSrv:IEmployeeSrv

    {

        List<Employee> _Employee=new List<Employee>();

public void AddEmployees(Employee employee)

        {

            employee.EmployeeId=Guid.NewGuid().ToString();

            _Employee.Add(employee);

        }

 

public void RemoveEmployee(string id)

        {

            Employee employee=_Employee.Find(p=>p.EmployeeId==id);

            _Employee.Remove(employee);

        }

 

public List<Employee> GetAllEmployees()

        {

            return _Employee;

        }

    }

}


此类是对IEmployeeSrv接口的具体实现,在此类的上面我们声明了[ServiceBehavior(InstanceContextMode=InstanceContextMode.Single)]标签,此标签代表这个类采用SingleTone(单类模式)来生成对象。
使用[ServiceBehavior(InstanceContextMode=InstanceContextMode.Single)]接口需要导入using System.ServiceModel;命名空间。

 

app.configService1改为EmployeeSrv.

运行WCF进行测试。
    VS2008中为我们提供了测试WCF的工具,按F5启动WCF会出现两个东西
    一个是在右下角的托盘图标中会出现WCFSVCHost(WCF服务主机),它为我们在开发时候提供了一个运行WCF的服务器,用来为测试客户端提供WCF服务。


   
   
另一个是“WCF测试客户端

   
    “
测试客户端WcfSVCHost中取得WCF服务的元数据,解析为右侧的服务结构树,从这里面我们可以看到此WCF服务为我们提供了一个服务契约“IEmployeeSrv”,此服务契约中对外提供了三个可调用的方法。
    双击AddEmployees()方法,我们可以从右面输入相关的数据然后点击调用,就可以把数据送给WCF服务器,去调用对应的方法了。

()   使用IIS发布WCF服务
 上一篇中,我们创建了一个简单的WCF服务,在测试的时候,我们使用VS2008自带的WCFSVCHost(WCF服务主机)发布WCF服务,以便进行测试。这种VS2008内置的WCFSVCHost只适用于开发人员测试的使用,能进行WCF服务部署。这一篇文章中我们来看一下如何在IIS中部发布我们上一篇中做好的WCF服务。

第一步:打开我们上一篇文章中建立的WCF服务项目。

 

 


图《1

第二步:新建WCF服务站点。在解决方案上右击,选择添加”->“新建网站,打开新建网站对话框。在添加新网站对话框中,我们选择“WCF服务,并把网站的名子命名为“BookServiceHost”


图《2
建立起来的新的WCF服务站点的结果如下,其中在App_Code文件中自动为我们生成两个类文件:IService.csService.cs。这两个文件对我们来说没有用,我们删掉。

 


图《3

第三步:在刚刚创建的WCF服务站点上添加对WCF服务库项目--Services项目的引用。


图《4

第四步:配置Service.svc文件。
双击Service.svc文件,我们可以看到它的声明指示如下:
<%@ ServiceHost Language="C#" Debug="true" Service="Service" CodeBehind="~/App_Code/Service.cs" %>
由于在第二步中我们已经把IService.csService.cs两个文件已经删除了,所以这里的声明指示内容修改一下,让这个Service.svc文件的后台代码指向我们上次创建的WCF服务库项目--Services项目中的类,改后的代码如下:
<%@ServiceHostLanguage="C#"Debug="true"Service="WcfEmployee.EmployeeSrv"%>
我们把其中的Service属性指定为WcfEmployee命名空间下的EmployeeSrv类,并把CodeBehind属性删去了。

第五步:配置此WCF服务站点与WCF服务库项目之间的类的对应。
虽然在第三步中我们添加了对Services项目的引用,并且在第四步中修改了Service.svc的类的对应,但此时我们的WCF服务站点并不能把WCF服务库中的服务和终结点发布出来,还需要我们对web.config进行一系列的配置工作。
web.config上右击选择编辑WCF配置

 



在弹出的服务配置编辑器窗口中,单击新建服务...”

 

 

单击”浏览”.定位到本项目下的Bin目录,单击WcfEmployee.dll,再选打开.

 

选”WcfEmployee.EmployeeSrv”,单击”打开”

 

 

 

 

 

 

 


 

 


 


 


Service.svc上右击,选择在浏览器中查看,在IE中运行此服务。



由此我们看到我们可以在ASP.NET Development Server中发布我们的WCF服务了。

第八步:在IIS布署此WCF服务站点。
打开iis管理器,在其中找到一个正常的网站,如下图中的wa3,右击之,

 

别名任意,物理路径必须准确为项目所在的目录.

使浏览器指向”http://localhost:83/EmployeeService/service.svc”,注意”EmployeeService”为刚才指定的别名.

 

在外网其他电脑上使浏览器指向”http://221.213.51.74:83/EmployeeService/service.svc

也应该出现上图.

 

 

 

()   创建WCF服务宿主程序

1.    控制台应用程序作为宿主程序


 

建立控制台应用程序ConsSrvHostEmployee

 

 


《图1
ConsSrvHostEmployee程序中添加两个引用:一个是WCF服务库Services项目的引用,另一个是System.ServiceModel引用。

生成该项目。

 


ConsSrvHostEmployee 项目中的Program.cs中编写代码。
 

using System;

using System.Collections.Generic;

using System.Linq;

using System.Text;

using System.Threading.Tasks;

using WcfEmployee;

using System.ServiceModel;

 

namespace ConsSrvHostEmployee

{

    class Program

    {

        static void Main(string[] args)

        {

            ServiceHost host = new ServiceHost(typeof(EmployeeSrv));

            host.Credentials.ServiceCertificate.SetCertificate("CN=OujianpingServer");

            host.Open();

            Console.WriteLine("服务已启动......");

            Console.ReadLine();

            host.Close();

        }

    }

}

 

 

配置App.Config

 

App.Config上右击选择选择编辑WCF配置,弹出服务配置管理窗口

 

 

 

 

 

 

 

 



第六步:点击右边的新建服务...”弹出新建服务元素向导窗口,单击浏览按钮,选择Bin/Debug目录下Services.dll程序集中的Services.EmployeeSrv服务。

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

注意进行绑定配置,选择“NewBinding0 netTcpBinding”。

 

 

 

 

 

 

 

 

配置元数据终结点:

//如果没有这个过程,也可以正常启动服务,但客户端无法通过引用添加服务引用”.

 

 

 

 

 

 


System.ServiceModel

 

 

 

 

 

 

 

 

 

 

 

 

 

 

<?xml version="1.0" encoding="utf-8" ?>

<configuration>

<startup>

<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.5" />

</startup>

<system.serviceModel>

<services>

<service behaviorConfiguration="NewBehavior0" name="WcfEmployee.EmployeeSrv">

<clear />

<endpoint address="basic" binding="basicHttpBinding" contract="WcfEmployee.IEmployeeSrv"

                    listenUriMode="Explicit">

<identity>

<certificateReference storeName="My" storeLocation="LocalMachine"

                            x509FindType="FindBySubjectName" findValue="OujianpingServer" />

</identity>

</endpoint>

<endpoint address="net.tcp://localhost:8082/Service" binding="netTcpBinding"

                    bindingConfiguration="NewBinding0" contract="WcfEmployee.IEmployeeSrv"

                    listenUriMode="Explicit">

<identity>

<certificateReference storeName="My" storeLocation="LocalMachine"

                            x509FindType="FindBySubjectName" findValue="OujianpingServer" />

</identity>

</endpoint>

<endpoint address="mex" binding="mexHttpBinding" bindingConfiguration=""

                    contract="IMetadataExchange" />

<host>

<baseAddresses>

<add baseAddress="http://localhost/service" />

</baseAddresses>

</host>

</service>

</services>

<behaviors>

<serviceBehaviors>

<behavior name="NewBehavior0">

<serviceMetadata />

</behavior>

</serviceBehaviors>

</behaviors>

<bindings>

<netTcpBinding>

<binding name="NewBinding0">

<security>

<transport clientCredentialType="None" />

</security>

</binding>

</netTcpBinding>

</bindings>

</system.serviceModel>

</configuration>

 

注:今后可将以上文件当作一个模版来使用,比如新建了个了名为wcflibwcf服务库项目,在此项目中建立了一个名为wcfserver的服务,并使用名为myCert的证书,则可将文中的WcfEmployee替换为wcflibEmployeeSrv替换为wcfserverOujianpingServer替换为myCert即可,而不必进行上述繁琐的操作。

 

 

 

用以下命令创建证书

makecert.exe -sr LocalMachine -ss My -a sha1 -n CN=OuJianpingServer -sky exchange -pe

(注:复制上述命令时须先整行显示,且只能不能复制行尾的多余空格,否则无法执行.

如下图

 

安装的证书可在控制台(cmd mmc)的本地计算机证书下看到

(文件-添加/删除管理单位-证书-计算机帐户-本地计算机)

 

 

 

 

 

 

 

 

 

 

 


测试一下。
选按Ctrl+F5运行打开浏览器,

 

 

 

 

 

 

 

 

 

 

2.    Windows服务作为宿主程序

建立Windows服务程序WinSrvEmployee

注意:必须选.Net Framework 4.5,与WCF服务库项目保持一致,否则引入WCF服务库会出现问题。
 


《图2

第二步:WinSrvEmployee程序中添加两个引用:一个是WCF服务库Services项目的引用,另一个是System.ServiceModel引用。

 

第三步:修改Service1的属性
Service1的设计界面中右击,选择属性,把其中的(Name)ServiceName都改为EmployeeSrv

 


《图3

第四步:在Service1中编写代码如下

 

 

 


《图4

ConsSrvHostEmployeev项目中的App.Config复制过来.为防止元数据泄漏,应将其中以下内容删除:

 

<endpointaddress="mex"binding="mexHttpBinding"bindingConfiguration=""

contract="IMetadataExchange" />

 


 

到这里我们已经作好一个可以发布EmployeeSrv服务的Windows Service宿主程序了。
下面我们要看一看如何把这个Windows Service运行起来。

第六步:为服务添加安装程序。
Service1设计界面中右击,选择添加安装程序


《图6
生成安装程序组件,出现界面如下


《图7
serviceProcessInstaller1:服务安装的信息

 


《图8
serviceInstaller1:服务本身的信息


《图9
生成项目

安装的服务

在计算机中搜索installutil.exe文件,找到版本最高的那个,将其路径写入环量变量path中。
打开VS2008命令窗口,进入当前项目的bin/Debug文件夹中,执行命令 installutil WinSrvEmployee.exe

(注:卸载时 InstallUtil.exe /u WinSrvEmployee.exe。)

启动EmployeeSrv服务
打开服务管理器,我们可以看到我们刚刚注册上的服务已经存在了,但还没有启动,右击启动


注意:上述通过windows server项目发布在.net 3.5 vs 2008windows server 2003的环境下无法通过,表现为启动服务会出错,会出现以下提示

,原因不明,但可以通过构建winform项目来代替,尤其是托盘型的winform应用。

 

 

二、 部署WCF服务器

 

 

 

三、 客户端程序开发

(一)  创建WCF客户端程序

(此步vs2008不必做)

 


using System;

using System.Collections.Generic;

using System.ComponentModel;

using System.Data;

using System.Drawing;

using System.Linq;

using System.Text;

using System.Threading.Tasks;

using System.Windows.Forms;

using System.ServiceModel;

using System.ServiceModel.Description;

 

 

namespace EmployeeIMS

{

publicpartialclassForm1 : Form

    {

        ServiceReference1.EmployeeSrvClient mClient = new ServiceReference1.EmployeeSrvClient("NetTcpBinding_IEmployeeSrv");

public Form1()

        {

            InitializeComponent();

        }

 

privatevoid Form1_Load(object sender, EventArgs e)

        {

            mClient.ClientCredentials.ServiceCertificate.Authentication.CertificateValidationMode = System.ServiceModel.Security.X509CertificateValidationMode.None;

            ServiceReference1.Employee employee = new ServiceReference1.Employee();

            employee.EmployeeName = "王芳";

            employee.EmployeeAge = 18;

            mClient.AddEmployees(employee);

            employee.EmployeeName = "李明";

            employee.EmployeeAge = 17;

            mClient.AddEmployees(employee);

 

string msg = "";

foreach(ServiceReference1.Employee em in mClient.GetAllEmployees())

            {

                msg += em.EmployeeName + "" + em.EmployeeAge + "\r";

            }

MessageBox.Show(msg);

 

        }

    }

}

 

 

(二)  修改app.config

Localhost

将app.config文件中的localhost替换为WCF服务器的实际ip地址,否则在其他计算机上运行时无法连接到服务器。

SendTimeout

如果客户端的请求需要服务花较长的时间才能回复,且这个过程会超过1分钟,则需要改变使用了进行数据传输的绑定(如netTcpBinding)的SendTimeout的值,并应该留有余量,否则超过1分钟后,客户端将抛出超时的错误。

maxBufferPoolSize和maxBufferSize

如果传输的数据过大,则需要改变使用了进行数据传输的绑定(如netTcpBinding)的maxBufferPoolSize和maxBufferSize的值,否则,客户端会抛出错误。

 

 

  • 1
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值