WCF入門教程之Windows通訊接口
概述
WCF:Windows Communication Foundation ,Windows通信基礎(chǔ)。
SOP:Service Orientation Architechture,面向服務(wù)的架構(gòu)。
WebService是以BasicHttpBing方式運(yùn)行的WCF。
方案結(jié)構(gòu):
1、創(chuàng)建解決方案WCFService

依次添加四個(gè)項(xiàng)目,如上圖,Client和Hosting為控制臺(tái)應(yīng)用程序,Service和Service.Interface均為類庫(kù)。
2、引用關(guān)系
- Service.Interface:定義服務(wù)契約(Service Contract)接口,引用WCF核心庫(kù)System.ServiceModel.dll;
- Service:定義服務(wù)的項(xiàng)目,由于需要實(shí)現(xiàn)具體的服務(wù),而服務(wù)契約在Service.Interface中,所以要引用Service.Interface項(xiàng)目;
- Hosting:服務(wù)宿主的控制臺(tái)程序,需要引用Service.Interface和Service項(xiàng)目,同時(shí)還要引用System.ServiceModel.dll類庫(kù):
- Client:一個(gè)控制臺(tái)應(yīng)用程序的客戶端,需要引用Service.ServiceModel類庫(kù)。
一、Contracts協(xié)定
一個(gè)類庫(kù)項(xiàng)目,定義服務(wù)契約。
服務(wù)契約抽象了服務(wù)的所有操作,一般契約為接口形式存在。
//服務(wù)協(xié)定
[ServiceContract(Name = "ICalculator", Namespace = "http://SampleWcfTest")] //webservice描述文件用的portType命名空間
//CallbackContract =typeof(ICallBack),//雙工時(shí)的返回協(xié)定
//ConfigurationName = "Calculator",//配置文件重的服務(wù)名
//ProtectionLevel = System.Net.Security.ProtectionLevel.EncryptAndSign,//保護(hù)等級(jí)
//SessionMode = SessionMode.Allowed//設(shè)置會(huì)話的支持模式
public interface ICalculator
{
//操作協(xié)定
[OperationContract]
double Add(double n1, double n2);
}二、Services服務(wù)
一個(gè)類庫(kù)項(xiàng)目,提供對(duì)契約的實(shí)現(xiàn)。
public class Calculator : ICalculator
{
public double Add(double n1, double n2)
{
double result = n1 + n2;
Console.WriteLine("Received Add({0},{1})", n1, n2);
// Code added to write output to the console window.
Console.WriteLine("Return: {0}", result);
return result;
}
}VS的“WCF服務(wù)庫(kù)項(xiàng)目”自動(dòng)生成了svc文件和對(duì)應(yīng)的svc.cs文件以及App.config文件,運(yùn)行此項(xiàng)目,會(huì)自動(dòng)啟動(dòng)“WCF服務(wù)主機(jī)”和“WCF測(cè)試客戶端”窗口
三、ServiceHost自我服務(wù)宿主
一個(gè)控制臺(tái)項(xiàng)目,通過(guò)自我寄宿的方式作為Sevice項(xiàng)目服務(wù)的宿主。寄宿進(jìn)程為ServiceHost1.exe。
服務(wù)寄宿的目的是開(kāi)啟一個(gè)進(jìn)程,為WCF服務(wù)提供一個(gè)運(yùn)行環(huán)境,并為服務(wù)添加一個(gè)或者多個(gè)終結(jié)點(diǎn),然后暴漏給服務(wù)消費(fèi)者。
WCF服務(wù)需要一個(gè)運(yùn)行著的宿主進(jìn)程,服務(wù)寄宿就是給服務(wù)指定一個(gè)宿主的過(guò)程。、
終結(jié)點(diǎn)(EndPoint)
WCF采用基于終結(jié)點(diǎn)(EndPoint)的通信手段。終結(jié)點(diǎn)有地址(Address),綁定(Binding)和契約(Contract)三部分組成,三要素也可以記作:EndPoint=ABC。
一個(gè)終結(jié)點(diǎn)包含了通信所必須的所有信息,具體如下:
- Address:地址決定了服務(wù)的位置,解決了尋址的問(wèn)題;
- Binding:綁定實(shí)現(xiàn)了通信的所有細(xì)節(jié),包括網(wǎng)絡(luò)傳輸,消息編碼,以及其他為實(shí)現(xiàn)某種功能(比如傳輸安全,可靠消息傳輸,事務(wù)等)對(duì)消息進(jìn)行的相應(yīng)處理。
WCF中具有一系列的系統(tǒng)定義綁定,比如BasicHttpBinding,WSHttpBinding和NetTcpBinding,WSHttpBinding、NetMsmqBindiing等; - Contract:契約是對(duì)服務(wù)操作的抽象,也是對(duì)消息交換模式以及消息結(jié)構(gòu)的定義。
1、編碼方式
//承載服務(wù)的宿主
using (ServiceHost selfHost = new ServiceHost(typeof(Calculator)))
{
try
{ //添加服務(wù)終結(jié)點(diǎn)
selfHost.AddServiceEndpoint(typeof(ICalculator), new WSHttpBinding(), new Uri("http://localhost:8000/GettingStarted/"));
//添加服務(wù)元數(shù)據(jù)行為
if (selfHost.Description.Behaviors.Find() == null)
{
ServiceMetadataBehavior smb = new ServiceMetadataBehavior();
smb.HttpGetEnabled = true;
smb.HttpGetUrl = new Uri("http://localhost:8000/GettingStarted/metadata")
selfHost.Description.Behaviors.Add(smb);
}
selfHost.Open();
Console.WriteLine("The service is ready.");
Console.WriteLine("input to terminate service.");
Console.WriteLine();
while ("exit" == Console.ReadLine())
{
selfHost.Close();
}
}
catch (CommunicationException ex)
{
Console.WriteLine(ex.Message);
selfHost.Abort();
}
}2、配置文件方式
打開(kāi)Hosting項(xiàng)目中的app.config,添加以下代碼即可。
可直接右鍵點(diǎn)擊config文件選擇“編輯WCF配置”菜單,或通過(guò)VS的“工具”菜單,選擇“WCF Service配置編輯器”菜單編輯配置文件。
<configuration>
<startup>
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.5" />
</startup>
<system.serviceModel>
服務(wù)
<service name="Service.CalculatorService" behaviorConfiguration="metadataBehavior">
<endpoint address="http://127.0.0.1:1111/GettingStarted" binding="wsHttpBinding" contract="Service.Interface.ICalculator"></endpoint>
</service>
</services>
行為
<serviceBehaviors>
<behavior name="metadataBehavior">
<serviceMetadata httpGetEnabled="true" httpGetUrl="http://127.0.0.1:1111/GettingStarted/metadata"/>
</behavior>
</serviceBehaviors>
</behaviors>
</system.serviceModel>
</configuration>Hosting代碼修改如下:
using (ServiceHost host = new ServiceHost(typeof(CalculatorService)))
{
host.Opened += delegate
{
Console.Write("CalculatorService已經(jīng)啟動(dòng),按任意鍵終止服務(wù)");
};
host.Open();
Console.Read();
}四、IIS宿主
一個(gè)Web應(yīng)用程序,通過(guò)IIS寄宿的方式將服務(wù)寄宿于IIS中,
寄宿進(jìn)程為w3wp.exe。WAS激活服務(wù):Window Activation Services。
1、創(chuàng)建WCF服務(wù)文件:CalculatorService.svc:
<%@ ServiceHost Sevice=”GettingStarted.CalculatorService” %>
2、配置文件
與app.config相比,web.config無(wú)EndPointAddress?服務(wù)的地址為.svc所在的地址,默認(rèn)的元數(shù)據(jù)為…../CalculatorService.svc?ws…
<system.serviceModel>
<services>
<service name="GettingStarted.CalculatorService" behaviorConfiguration="metadataBehavior" >
<endpoint address="CalculatorService" binding="wsHttpBinding" contract="Calculator"/>
</service>
</services>
<behaviors>
<serviceBehaviors>
<behavior name="metadataBehavior" >
<serviceMetadata httpGetEnabled="true" />
</behavior>
</serviceBehaviors>
</behaviors>
</system.serviceModel>五、實(shí)現(xiàn)Rest 風(fēng)格的web服務(wù)
可以使用 WCF REST 編程模型。
默認(rèn)WebHttpBinding。
在協(xié)定的實(shí)現(xiàn)方式上添加 WebGet或者WebInvoke屬性
[OperationContract]
[WebInvoke(UriTemplate = "div?x={x}&y={y}")]
long Divide(long x, long y);
[OperationContract]
[WebGet(UriTemplate = "hello?name={name}")]
string SayHello(string name);舉例2:
[ServiceContract]
public interface ITestService
{
[OperationContract]
[WebInvoke(Method = "POST", UriTemplate = "Test1", RequestFormat = WebMessageFormat.Json, ResponseFormat = WebMessageFormat.Json, BodyStyle = WebMessageBodyStyle.Wrapped)]
string Test1(string userName, string password);
[OperationContract]
[WebGet(UriTemplate = "Test/{id}", RequestFormat = WebMessageFormat.Json, ResponseFormat = WebMessageFormat.Json, BodyStyle = WebMessageBodyStyle.Bare)]
string Test(string id);
}六、使用預(yù)配置的主機(jī)類WebServiceHost
使用WebServiceHost類
Uri baseAddress = new Uri("http://localhost:8000/");
WebServiceHost svcHost = new WebServiceHost(typeof(CalcService), baseAddress);
try
{
svcHost.Open();
Console.WriteLine("Service is running");
Console.WriteLine("Press enter to quit...");
Console.ReadLine();
svcHost.Close();
}
catch (CommunicationException cex)
{
Console.WriteLine("An exception occurred: {0}", cex.Message);
svcHost.Abort();
}3、調(diào)用:
http://…/div?x=1&y=2
七、client:一個(gè)客戶端
1、使用VS“添加服務(wù)引用”生成的CalculatorServiceClient
CalculatorServiceClient基類是System.ServiceModel.ClientBase,該基類封裝了ChannelFactory
using (CalculatorServiceClient proxy = new CalculatorServiceClient())
{
double result = proxy.Add(1, 2);
Console.WriteLine("Add({0},{1}) = {2}", value1, value2, result);
}2、不用添加服務(wù)引用,使用ChannelFactory方式
//using (ChannelFactory channelFactory = new ChannelFactory(new WSHttpBinding(), "<a rel="external nofollow" target="_blank">http://127.0.0.1</a>:1111/CalculatorService"))//構(gòu)造函數(shù)中指定了終結(jié)點(diǎn)的ABC三要素,
using (ChannelFactory channelFactory = new ChannelFactory("CalculatorService"))//通過(guò)配置文件來(lái)進(jìn)行,對(duì)應(yīng)的為config 文件中終結(jié)點(diǎn)的name
{
ICalculator proxy = channelFactory.CreateChannel();
using (proxy as IDisposale)
{
Console.WriteLine("x+y={2} when x={0} and y={1}", 1, 2, proxy.Add(1, 2));
}
}配置文件:
<configuration>
<system.serviceModel>
<client>
<endpoint name="CalculatorService" address="http://127.0.0.1:1111/CalculatorService" binding="wsHttpBinding" contract="Service.Interface.ICalculator" />
</client>
</system.serviceModel>
</configuration>八、綁定類型
WCF中常用的binding方式:
1. 基于HTTP的綁定
BasicHttpBinding、WSHttpBinding、WSDualHttpBinding和WSFederationHttpBinding選項(xiàng)適合于通過(guò)XML Web服務(wù)協(xié)議提供契約類型。顯然,如果需要使該服務(wù)可適用于更多場(chǎng)合(多種操作系統(tǒng)和多種編程語(yǔ)言),這些就是需要關(guān)注的綁定,因?yàn)樗羞@些綁定類型都基于XML表示編碼數(shù)據(jù)并且使用HTTP傳送數(shù)據(jù)。
在下面清單中,注意到可以在代碼中表示W(wǎng)CF綁定(通過(guò)System.ServiceModel名稱空間中的類類型),或者作為在*.config文件中定義的XML屬性表示W(wǎng)CF綁定。
- BasicHttpBinding:用于綁定符合WS-Basic Profile(WS-I Basic Profile 1.1)的WCF服務(wù)。該綁定使用HTTP作為傳送方式,并且使用Text/XML作為默認(rèn)消息編碼。用于兼容舊的Web ASMX 服務(wù)。
BasicHttpBinding是所有以Web服務(wù)為中心的協(xié)議中最簡(jiǎn)單的協(xié)議。特別是,該綁定將確保WCF服務(wù)符合由WS-I定義的名為WS-I Basic Profile 1.1的規(guī)范。 - WSHttpBinding:類似于BasicHttpBinding,但是提供了更多的Web服務(wù)特性。該綁定添加對(duì)事務(wù)、可靠消息發(fā)送和WS-Addressing的支持。
WSHttpBinding協(xié)議不僅集成了對(duì)WS-*規(guī)范(事務(wù)、安全性和可靠會(huì)話)子集的支持,而且支持使用消息傳輸優(yōu)化機(jī)制(Message Transmission Optimization Mechanism,MTOM)處理二進(jìn)制數(shù)據(jù)編碼的能力。 - WSDualHttpBinding:類似于WSHttpBinding,但是用于與雙向契約結(jié)合使用(例如,服務(wù)和客戶可以來(lái)回發(fā)送消息)。該綁定只支持SOAP安全性,并且需要可靠的消息發(fā)送。
WSDualHttpBinding的主要優(yōu)點(diǎn)是它添加了允許調(diào)用者和發(fā)送方使用雙向消息發(fā)送(duplex messaging)通信的能力,這是一種表示調(diào)用者和發(fā)送方可以參加雙向會(huì)談的流行方法。在選擇WSDualHttpBinding時(shí),可以與WCF發(fā)布/訂閱事件模型建立關(guān)聯(lián)。 - WSFederationHttpBinding:安全的和可互操作的綁定,該綁定支持WS-Federation協(xié)議,并且允許位于聯(lián)盟內(nèi)的組織有效地驗(yàn)證和授權(quán)用戶
WSFederationHttpBinding是基于Web服務(wù)的協(xié)議,在安全性最為重要時(shí)就需要使用該協(xié)議。該綁定支持WS-Trust、WS-Security和WS-SecureConversation規(guī)范,通過(guò)WCF CardSpace API表示這些規(guī)范。 - WebHttpBinding:用于通過(guò)HTTP(非SOAP)請(qǐng)求提供的服務(wù)隊(duì)腳本客戶端有用,如ASPNet AJAX。
2. 基于TCP的綁定
如果正在構(gòu)建一個(gè)分布式系統(tǒng),該系統(tǒng)涉及使用.NET 3.0/3.5庫(kù)配置的一組連網(wǎng)機(jī)器(換句話說(shuō),所有機(jī)器都運(yùn)行Windows XP、Windows Server 2003或Windows Vista),就可以通過(guò)繞開(kāi)Web服務(wù)綁定并選擇使用TCP綁定來(lái)增強(qiáng)性能,TCP綁定確保以緊湊二進(jìn)制格式(而不是XML)編碼所有數(shù)據(jù)。同樣,在使用下表的的綁定時(shí),客戶和主機(jī)必須是.NET應(yīng)用程序。
- NetNamedPipeBinding:用于相同機(jī)器上不同.NET應(yīng)用程序之間通信的安全的、可靠的、優(yōu)化的綁定。
NetNamedPipeBinding支持事務(wù)、可靠的會(huì)話和安全的通信,但是它不能夠執(zhí)行跨機(jī)器的調(diào)用。如果您正在尋找在相同機(jī)器上的WCF應(yīng)用程序之間推動(dòng)數(shù)據(jù)(例如,跨越應(yīng)用程序的域通信)的最快速方法,NetNamedPipeBinding綁定就是最佳的選擇。 - NetPeerTcpBinding:為對(duì)等(P2P)網(wǎng)絡(luò)應(yīng)用程序提供安全的綁定。
至于NetPeerTcpBinding,可查閱.NET Framework 3.5 SDK文檔以了解關(guān)于P2P連網(wǎng)的細(xì)節(jié)。 - NetTcpBinding:適合于不同機(jī)器上.NET應(yīng)用程序之間通信的安全的、優(yōu)化的綁定。
NetTcpBinding類使用TCP在客戶和WCF服務(wù)之間移動(dòng)二進(jìn)制數(shù)據(jù)。前面提及,這將導(dǎo)致比Web服務(wù)協(xié)議更佳的性能,但是只限于內(nèi)部應(yīng)用程序解決方案。此外,NetTcpBinding支持事務(wù)、可靠的會(huì)話和安全的通信。
3. 基于MSMQ的綁定
- MsmqIntegrationBinding:該綁定可用于允許WCF應(yīng)用程序向已有的MSMQ應(yīng)用程序發(fā)送消息以及從這種應(yīng)用程序接收消息,這種應(yīng)用程序使用COM、本地C++或定義在System.Messaging名稱空間中的類型
- NetMsmqBinding:這個(gè)排隊(duì)的綁定適合于不同機(jī)器上的.NET應(yīng)用程序之間的通信
注:二進(jìn)制編碼格式使用TCP、IPC、MSMQ可以獲取最佳性能,但是它是以犧牲互操作性為代價(jià),因?yàn)樗恢С諻CF到WCF的通信。
到此這篇關(guān)于WCF入門教程之Windows通訊接口的文章就介紹到這了。希望對(duì)大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。
相關(guān)文章
C#讀寫(xiě)EXCEL單元格的問(wèn)題實(shí)現(xiàn)
這篇文章主要介紹了C#讀寫(xiě)EXCEL單元格的問(wèn)題實(shí)現(xiàn),小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧2019-04-04
C# 全角和半角轉(zhuǎn)換以及判斷的簡(jiǎn)單代碼
這篇文章介紹了在C#中判斷和轉(zhuǎn)換全角半角的方法,有需要的朋友可以參考一下2013-07-07
C#使用DateTime獲取日期和時(shí)間的實(shí)現(xiàn)
在C#中,DateTime類是用來(lái)處理日期和時(shí)間的類,它具有許多屬性和方法,用于操作和獲取日期和時(shí)間的不同部分,本文就來(lái)介紹一下C#使用DateTime獲取,感興趣的可以了解一下2023-11-11
C# WinForm國(guó)際化實(shí)現(xiàn)的簡(jiǎn)單方法
這篇文章主要介紹了C# WinForm國(guó)際化實(shí)現(xiàn)的簡(jiǎn)單方法,有需要的朋友可以參考一下2014-01-01
C#實(shí)現(xiàn)簡(jiǎn)單播放mp3的方法
這篇文章主要介紹了C#實(shí)現(xiàn)簡(jiǎn)單播放mp3的方法,涉及C#播放多媒體文件的技巧,具有一定參考借鑒價(jià)值,需要的朋友可以參考下2015-03-03
C#通過(guò)yield實(shí)現(xiàn)數(shù)組全排列的方法
這篇文章主要介紹了C#通過(guò)yield實(shí)現(xiàn)數(shù)組全排列的方法,以實(shí)例形式較為詳細(xì)的分析了全排列的概念及C#的實(shí)現(xiàn)技巧,具有一定參考借鑒價(jià)值,需要的朋友可以參考下2015-03-03
c# 通過(guò)代碼開(kāi)啟或關(guān)閉防火墻
這篇文章主要介紹了c# 通過(guò)代碼開(kāi)啟或關(guān)閉防火墻的示例,幫助大家更好的理解和使用c#,感興趣的朋友可以了解下2020-10-10

