朋友炒股兩個月賺了10萬,我幫他推廣一下公眾號,把錢用來投資總比放銀行連通貨膨脹都跑不過里強, 硬核離職,在家炒股 ,這是他每天的日志,有些經驗是花錢也買不到的。
一、WCF服務應用程序與WCF服務庫
我們在平時開發的過程中常用的項目類型有“WCF 服務應用程序”和“WCF服務庫”。
WCF服務應用程序,是一個可以執行的程序,它有獨立的進程,WCF服務類契約的定義,可以直接看到運行的效果。此項目模板基於IIS托管的程序,如本系列的第一節所示。在開發基於IIS托管的WCF服務程序時,比較多見,自學的時候也可以使用這種類型,簡單易懂。
WCF服務庫,可以認為是一個包含WCF服務以及契約定義的類庫。不能直接運行,你可以在其他項目里引用,在宿主里啟用托管這個庫,有點類似於我們在Web項目中應用的類庫。考慮WCF服務設計的時候,服務類的定義為單獨的庫,可以為其它項目使用。提高代碼的復用性。
當然你也可以修改這些代碼,比如把WCF服務程序里的類,移到一個單獨的類庫里,或是把類庫里的類移到WCF服務程序中。
二、概述
通過前面的介紹我們知道,WCF在運行時必寄宿在“宿主程序”之上,WCF本身不能夠獨自運行(每個WCF服務必須宿主在一個Windows進程中)。.net 提供了多種宿主供WCF運行,WCF還是非常靈活的。
WCF的宿主可以是 Windows 服務、COM+應用程序、WAS(Windows Activation Services,Windows進程激活服務)或IIS、Windows應用程序,或簡單的控制台應用程序及任何.net程序。
這節的示例我們重新建立WCF類庫項目為例做示例,名稱為:WCFLibrary,並刪除自動生成的兩個文件(IService1.cs、Service1.cs)。如下圖所示:
鼠標右鍵查看項目屬性。我們發現,其實“WCF類庫項目”與我們平時建立的“類庫項目”都是類庫,只不過多了WCF的類庫項目在新建時多了兩個dll的引用(System.ServiceModel.dll、System.Runtime.Serialization.dll)和一個自動生成的配置文件(該配置文件只用於調試時使用,在WCF寄宿以后會應用宿主的配置文件與其他應用程序通信)。這更說明了我們在做分式程序開發的時候與我們平時開發的應用程序沒有多大的區別,只要我們在應用程序間通信時“符合WCF的約定”即可。
服務端我們還和第一個教程一樣(IUser接口與User實現),只建立一個方法做為我們調用的示例代碼如下:
1 //添加引用
2 using System.ServiceModel; 3
4 namespace WCFLibrary 5 { 6 [ServiceContract] 7 interface IUser 8 { 9 [OperationContract] 10 string ShowName(string name); 11 } 12 } 13
14 namespace WCFLibrary 15 { 16 class User : IUser 17 { 18 public string ShowName(string name) 19 { 20 string wcfName = string.Format("WCF服務,顯示姓名:{0}", name); 21 return wcfName; 22 } 23 } 24 }
由於原來的契約為IService,現在的為IUser,所以配置文件有兩處要修改為:
<service name="WCFLibrary.User">
<endpoint address="" binding="wsHttpBinding" contract="WCFLibrary.IUser">
點擊“F5“運行效果如下圖所示說明成功:
二、IIS宿主
我們在第一節中,把WCF寄宿在IIS之上,在IIS中宿主一個服務的主要優點是在發生客戶端請求時宿主進程會被自動啟動,並且你可以依靠IIS來管理宿主進程的生命周期。在開發和使用的過程與Web Service非常相似。
具體請參見本系列的第一節課程。
三、控制台應用程序宿主
建立宿主
(1)在解決方案下新建控制台輸出項目 WCFHost_Console。
(2)添加 System.ServiceModel.dll 的引用。
(3)添加 WCF 服務類庫(WCFLibrary)的項目引用。
(4)創建宿主程序,代碼如下:
1 using System; 2 using WCFLibrary; 3 using System.ServiceModel; 4 using System.ServiceModel.Description; 5
6 namespace WCFHost_Console 7 { 8 class Program 9 { 10 static void Main(string[] args) 11 { 12 //創建宿主的基地址
13 Uri baseAddress = new Uri("http://localhost:8080/User"); 14 //創建宿主
15 using (ServiceHost host = new ServiceHost(typeof(User), baseAddress)) 16 { 17 //向宿主中添加終結點
18 host.AddServiceEndpoint(typeof(IUser), new WSHttpBinding(), ""); 19 //將HttpGetEnabled屬性設置為true
20 ServiceMetadataBehavior smb = new ServiceMetadataBehavior(); 21 smb.HttpGetEnabled = true; 22 //將行為添加到Behaviors中
23 host.Description.Behaviors.Add(smb); 24 //打開宿主
25 host.Open(); 26 Console.WriteLine("WCF中的HTTP監聽已啟動...."); 27 Console.ReadLine(); 28 host.Close(); 29 } 30 } 31 } 32 }
(5)運行宿主程序[在客戶端調用時要先運行宿主程序],如下圖所示:
說明宿主建立成功。在上例中用到"ServiceHost"類,這里只是簡單的應用,具體請查看"MSDN ServiceHost"。
建立客戶端
(1)重新建立解決方案-->Web應用程序項目。
(2)添加對服務的引用(在引用上右鍵-->輸入我們定義的服務宿主的基地址(此處為:http://localhost:8080/User)-->前往-->確定),具體請看第一節。
(3)測試程序如下圖所示說明成功(注意:一定要先運行我們的宿主程序才行,如果宿主沒有打開的話會報錯:由於目標計算機積極拒絕,無法連接。)。
在這個示例中我們把Endpoint中的ABC,基地址,Behaviors等都直接寫在了代碼里,但實際應用過程中都是去依賴配置文件,為了對比說明我們下面的例子中會使用配置文件。
四、Windows應用程序宿主
建立宿主
(1)在解決方案下新建Windows窗體應用程序項目 WCFHost_Form。
(2)添加 System.ServiceModel.dll 的引用。
(3)添加 WCF 服務類庫(WCFLibrary)的項目引用。
(4)添加應用程序配置文件App.config。
(5)創建宿主程序MainForm窗體,並修改App.config,代碼如下:
1 <?xml version="1.0" encoding="utf-8" ?>
2 <configuration>
3 <system.serviceModel>
4 <services>
5 <service name="WCFLibrary.User">
6 <host>
7 <baseAddresses>
8 <add baseAddress="http://localhost:8081/User"/>
9 </baseAddresses>
10 </host>
11 <endpoint address="" binding="wsHttpBinding" contract="WCFLibrary.IUser"></endpoint>
12 </service>
13 </services>
14 <behaviors>
15 <serviceBehaviors>
16 <behavior>
17 <serviceMetadata httpGetEnabled="True"/>
18 <serviceDebug includeExceptionDetailInFaults="False"/>
19 </behavior>
20 </serviceBehaviors>
21 </behaviors>
22 </system.serviceModel>
23 </configuration>
24
25
26 using System; 27 using WCFLibrary; 28 using System.ServiceModel; 29 using System.Windows.Forms; 30 using System.Configuration; 31
32 namespace WCFHost_Form 33 { 34 public partial class MainForm : Form 35 { 36 ServiceHost host; 37
38 public MainForm() 39 { 40 InitializeComponent(); 41 } 42
43 //應用程序加載
44 private void MainForm_Load(object sender, EventArgs e) 45 { 46 host = new ServiceHost(typeof(User)); 47 //打開宿主
48 host.Open(); 49 this.lblState.Text = "WCF中的HTTP監聽已啟動...."; 50 } 51
52 //應用程序關閉
53 private void MainForm_FormClosed(object sender, FormClosedEventArgs e) 54 { 55 host.Close(); 56 } 57 } 58 }
運行程序如下圖所示:
建立客戶端
同上邊的Console程序一樣,這里要引用的地址為:<add baseAddress="http://localhost:8081/User"/>
在這個例子中與Console應用程序不同的是,我們在Console配置是直接寫在程序中的,而在本例中我們應用的是配置文件,區別在於如果寫在配置文件中程序運行時直接到配置文件里取出相關的配置節去創建ServiceHost類。
五、WAS宿主
IIS7允許通過HTTP外的協議進行激活和網絡通信。此環境適合開發可通過WCF支持的任何網絡協議(包括http、net.tcp、net.pipe、net.msmq)進行通信的WCF服務。部署簡單、管理方便,這些網絡協議在部署時可像Http一樣,直接丟到IIS7上即可,我們在下面的例子中以net.tcp為協議為例。IIS7以下的版本只能支持Http的通信。
1、確保已安裝IIS7的激活組件
在應用WAS宿主時,必須確保IIS7的激活組件安裝好。打開“控制面板”-->“打開或關閉Windows功能”-->“功能”,我的機器上已經安裝過,如下圖所示(WCF激活與非WCF激活):
如果沒有安裝,點擊“添加新功能”,然后勾選“WCF激活”,如下圖所示:
安裝成功后我們打開IIS,點擊“默認網站(任一個網站即可)”-->“綁定”-->“添加”,在類型中會出現非IIS支持的其他類型。如下圖所示
說明安裝成功。
2、添加net.tcp的網站綁定
在上圖中,我們選擇類型net.tcp,然后在綁定信息中填寫“808:*”,點擊確定。
3、開通net.tcp的協議
在安裝成功並且在指定的網站上綁定了net.tcp以后,我們還要開通.net.tcp協議,點擊我們要部署WCF的網站,在IIS管理器的操作功能區有一項“高級設置”點擊后出現如下圖所示高級配置的窗體
在啟用的協議中添加net.tcp協議(原來只對http協議支持,現在把tcp協議追加上去),中間用逗號隔離開,如上圖所示。
注意:這幾個步驟一個也不能少,否則會出現:“找不到具有綁定 NetTcpBinding 的終結點的與方案 net.tcp 匹配的基址。注冊的基址方案是 [http]”的錯誤信息。
4、建立服務程序
(1)在解決方案下新建WCF服務應用程序項目 WCFHost_WAS。
(2)建立IUser與User,代碼同例二一樣。
(3)修改配置文件代碼如下:
1 <?xml version="1.0" encoding="utf-8"?>
2 <configuration>
3 <system.serviceModel>
4 <bindings>
5 <netTcpBinding>
6 <binding name="netTcpBindConfig">
7 <security mode="None">
8 <transport clientCredentialType="Windows" protectionLevel="EncryptAndSign" />
9 <message clientCredentialType="Windows" />
10 </security>
11 </binding>
12 </netTcpBinding>
13 </bindings>
14 <services>
15 <service behaviorConfiguration="MyBehavior" name="WCFHost_WAS.User">
16 <endpoint address="" binding="netTcpBinding" contract="WCFHost_WAS.IUser" bindingConfiguration="netTcpBindConfig"></endpoint>
17 <!--元數據交換的終結點-->
18 <endpoint address="mex" binding="mexTcpBinding" contract="IMetadataExchange" ></endpoint>
19 </service>
20 </services>
21 <behaviors>
22 <serviceBehaviors>
23 <behavior name="MyBehavior" >
24 <serviceMetadata/>
25 <serviceDebug includeExceptionDetailInFaults="true" />
26 <dataContractSerializer maxItemsInObjectGraph="6553600"/>
27 </behavior>
28 </serviceBehaviors>
29 </behaviors>
30 </system.serviceModel>
31
32 </configuration>
(5)部署服務
像其他的Web應用程序一樣,把相關的文件丟到服務器端指定目錄即可。
鼠標右鍵瀏覽User.svc,如現如下所示:
說明部署成功,如上所示的服務地址為:net.tcp://服務器名/User.svc/mex
(6)建立客戶端
建立客戶端也與其他的一樣,如下圖所示:
我們此時看客戶端的配置文件:
<client>
<endpoint address="http://localhost:8080/User" binding="wsHttpBinding" contract="WCFHost_Console.IUser" />
<endpoint address="http://localhost:8081/User" binding="wsHttpBinding" bindingConfiguration="WSHttpBinding_IUser" contract="WCFHost_Form.IUser" name="WSHttpBinding_IUser">
<identity>
<userPrincipalName value="WIN-EOUTAA4CP4O\Administrator" />
</identity>
</endpoint>
<endpoint address="net.tcp://win-eoutaa4cp4o/User.svc" binding="netTcpBinding" bindingConfiguration="NetTcpBinding_IUser" contract="WCFHost_WAS.IUser" name="NetTcpBinding_IUser" />
</client>
我們在一個Web應用程序中調用了三種不同宿主的服務。
七、總結
通過上面的幾個例子,我們實現了控制台宿主、Form宿主、WAS宿主(基於TCP協議)的實現。在實際的開發過程中,有時候我們還會用到基於Windows服務的宿主,但大部份都使用IIS做宿主,方便、快捷。
八、代碼下載
九、版權