WCF學習——構建一個簡單的WCF應用(一)

来源:http://www.cnblogs.com/songjianhui/archive/2017/06/21/7060698.html
-Advertisement-
Play Games

本文的WCF服務應用功能很簡單,卻涵蓋了一個完整WCF應用的基本結構。希望本文能對那些準備開始學習WCF的初學者提供一些幫助。 在這個例子中,我們將實現一個簡單的計算器和傳統的分散式通信框架一樣,WCF本質上提供一個跨進程、跨機器、跨網路的服務調用。在本例中,客戶端和WCF應用服務通過運行在同一臺機 ...


本文的WCF服務應用功能很簡單,卻涵蓋了一個完整WCF應用的基本結構。希望本文能對那些準備開始學習WCF的初學者提供一些幫助。

在這個例子中,我們將實現一個簡單的計算器傳統的分散式通信框架一樣,WCF本質上提供一個跨進程、跨機器、跨網路的服務調用。在本例中,客戶端和WCF應用服務通過運行在同一臺機器上的不同進程模擬。

 

步驟一、構建整個解決方案

     1.創建一個空白的解決方案

      

 


          2.添加四個項目和引用及關係

      

 


              Service.Interface  用於定義服務契約的類庫項目,引用WCF核心程式集System.ServuceModel.dll
              Service           用於定義服務類型的類庫項目,由於服務類型需要實現定義在ervice.Interface中相應的介面,因此需要引用Service.Interface
              Hosting           作為服務寄主的控制台應用,該項目同時引用Service.Interface、System.ServuceModel.dll、Service
              Client           模擬服務的客服端控制台應用  該醒目引用System.ServuceModel.dll

       

 

     

 

 

 

步驟二、創建服務契約(一般將服務契約定義為介面)

     WCF採用基於介面(MSDN上翻譯為:服務協定)的交互方式實現了服務功能,以及客戶端和服務端之間的松耦合。WCF包含五種類型的協定:服務協定、操作協定、消息協定、錯誤協定和數據協定。

       從功能上講,服務協定將多個相關的操作聯繫在一起,組成單個功能單元。協定可以定義服務級設置,如服務的命名空間、對應的回調協定以及其他此類設置,以及各種操作。

      從消息交換的角度來講,服務協定則定義了基於服務調用的消息交換過程中, 請求消息和回覆消息的結構,以及採用的消息交換模式。

      從使用編程語言的角度來講,協定是通過所選的編程語言創建一個介面,然後將 ServiceContractAttribute 屬性應用於該介面。通過實現該介面,可生成實際的服務代碼。

 1 using System;
 2 using System.Collections.Generic;
 3 using System.Linq;
 4 using System.Text;
 5 using System.Threading.Tasks;
 6 using System.ServiceModel;
 7 
 8 namespace Service.Interface
 9 {
10     /// <summary>
11     /// 計算器
12     /// </summary>
13     [ServiceContract(Name = "CalculatorService",Namespace="http://www.artech.com/")]
14     public interface ICalculator
15     {
16         /// <summary>
17         ///18         /// </summary>
19         /// <param name="x"></param>
20         /// <param name="y"></param>
21         /// <returns></returns>
22         [OperationContract]
23         double Add(double x,double y);
24 
25         /// <summary>
26         ///27         /// </summary>
28         /// <param name="x"></param>
29         /// <param name="y"></param>
30         /// <returns></returns>
31         [OperationContract]
32         double Subtract(double x,double y);
33 
34         /// <summary>
35         ///36         /// </summary>
37         /// <param name="x"></param>
38         /// <param name="y"></param>
39         /// <returns></returns>
40         [OperationContract]
41         double Multiply(double x,double y);
42 
43         /// <summary>
44         ///45         /// </summary>
46         /// <param name="x"></param>
47         /// <param name="y"></param>
48         /// <returns></returns>
49         [OperationContract]
50         double Divide(double x,double y);
51     }
52 }

 

 

步驟三、實現WCF服務契約

  

 1 using System;
 2 using System.Collections.Generic;
 3 using System.Linq;
 4 using System.Text;
 5 using System.Threading.Tasks;
 6 using Service.Interface;
 7 
 8 namespace Service
 9 {
10     public class CalculatorService:ICalculator
11     {
12 
13  
14         public double Add(double x, double y)
15         {
16             return x + y;
17         }
18 
19         public double Subtract(double x, double y)
20         {
21             return x - y;
22         }
23 
24         public double Multiply(double x, double y)
25         {
26             return x * y;
27         }
28 
29         public double Divide(double x, double y)
30         {
31             return x / y;
32         }
33     }
34 }

 

步驟四、通過自我寄宿的方式寄宿服務

    WCF服務需要依存一個運行著的進程(宿主),服務寄宿就是為服務指定一個宿主的過程。WCF是一個基於消息的通信框架,採用基於終結點(Endpoint)的通信手段。

       終結點主要由地址(Address)、綁定(Binding)和協定(Contract)三要素組成,如圖所示。由於三要素應為首字母分別為ABC,所以就有了易於記憶的公式:Endpoint = ABC。一個終結包含了實現通信所必需的所有信息。如下圖。

終結點三要素  

  • 地址(Address):一個指示可以查找終結點的位置的地址。地址決定了服務的位置,解決了服務定址的問題
  • 綁定(Binding):一個指定客戶端如何與終結點進行通信的綁定。綁定實現了通信的所有細節,包括網路傳輸、消息編碼,以及其他為實現某種功能(比如安全、可靠傳輸、事務等)對消息進行的相應處理。WCF中具有一系列的系統定義綁定,比如BasicHttpBinding、WsHttpBinding、NetTcpBinding等,
  • 協定(Contract):一個標識可用操作的協定。協定是對服務操作的抽象,也是對消息交換模式以及消息結構的定義。
  • 行為(Behavior):一組指定終結點的本地實現細節的行為。

      服務寄宿的目的就是開啟一個進程,為WCF服務應用提供一個運行的環境。通過為服務添加一個或多個終結點,使之暴露給潛在的服務調用者。服務調用者最終通過相匹配的終結點對該服務進行調用。

一)代碼方式實現寄宿

 1        using Service;
 2             using Service.Interface;
 3             using System.ServiceModel;
 4             using System.ServiceModel.Description;
 5 
 6             namespace Hosting
 7             {
 8                 class Program
 9                 {
10                     static void Main(string[] args)
11                     {
12                         //在進行真正的開放時一般在配置文件裡面進行配置添加終結點和服務行為的定義
13                         using(ServiceHost host = new ServiceHost(typeof(CalculatorService)))
14                         {
15                             //指定綁定和總結點的地址
16                             host.AddServiceEndpoint(typeof(ICalculator), new WSHttpBinding(), "http://127.0.0.1:3721/calculatorservice");
17                             //數據的發佈
18                             if(host.Description.Behaviors.Find<ServiceMetadataBehavior>() == null)
19                             {
20                                 //創建服務行為
21                                 ServiceMetadataBehavior behavior = new ServiceMetadataBehavior();
22                                 //是否發佈元數據以便使用HTTPS/GET請求進行檢索
23                                 behavior.HttpGetEnabled = true;
24                                 //使用HTTPS/GET請求的元數據發佈的位置
25                                 behavior.HttpGetUrl = new Uri("http://127.0.0.1:3721/calculatorservice/metadata");
26                                 //添加到發佈上
27                                 host.Description.Behaviors.Add(behavior);
28                             }
29                             host.Opened += delegate
30                             {
31                                 Console.WriteLine("CalculatorService已經啟動,按任意鍵終止服務!");
32                             };
33                             //通訊狀態轉換到已打開
34                             host.Open();
35                             Console.ReadLine();
36                         }
37                     }
38                 }
39             }

   1) WCF服務寄宿通過一個特殊的對象完成:ServiceHost。在上面的代碼基本實現的功能說明,基於WCF服務應用的類型(typeof(CalculatorService))創建了ServieHost對象,並添加了一個終結點。具體的地址為http://127.0.0.1:3721/calculatorservice/metadata,採用了WSHttpBinding,並指定了服務協定的類型ICalculator

        2) 松耦合是SOA的一個基本的特征,WCF服務應用中客戶端和服務端的松耦合體現在客戶端只需要瞭解WCF服務基本的描述,而無需知道具體的實現細節,就可以實現正常的WCF服務調用。WCF服務的描述通過元數據(Metadata)的形式發佈出來。WCF中元數據的發佈通過一個特殊的服務行為ServiceMetadataBehavior實現。在上面提供的服務寄宿代碼中,我們為創建的ServiceHost添加了ServiceMetadataBehavior,並採用了基於HTTP-GET的元數據獲取方式,元數據的發佈地址通過ServiceMetadataBehavior的HttpGetUrl指定。在調用ServiceHost的Open方法對服務成功寄宿後,我們可以通過該地址獲取服務相關的元數據。

 

     3) 運行已經生成的hosting.exe,

 

  4)然後在瀏覽器地址欄上鍵入http://127.0.0.1:3721/calculatorservice/metadata,你將會得到以WSDL形式體現的服務元數據,如下圖所示。

 

二)配置文件方式實現寄宿

        在實際應用中,對於WCF應用服務的寄宿,一般不會直接通過編碼的方式進行終結點的添加和服務行為的定義,而是通過寫配置文件的方式實現,這樣可以方便修改。

       1)  現在我在Hosting項目中添加一個app.config配置文件,把下麵的配置信息添加到配置文件app.config中。

    

 1 <?xml version="1.0" encoding="utf-8" ?>
 2 <configuration>
 3     <startup> 
 4         <supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.5" />
 5     </startup>
 6   <system.serviceModel>
 7     
 8     <behaviors>
 9       <serviceBehaviors>
10         <behavior name="metadataBehavior">
11           <serviceMetadata httpGetEnabled="true" httpGetUrl="http://127.0.0.1:3721/calculatorservice/metadata" />
12         </behavior>
13       </serviceBehaviors>
14     </behaviors> 
15     
16     <services>
17       <service  behaviorConfiguration="metadataBehavior" name="Service.CalculatorService">
18         <endpoint address="http://127.0.0.1:3721/calculatorservice"
19             binding="wsHttpBinding" bindingConfiguration="" contract="Service.Interface.ICalculator" />
20       </service>
21     </services>
22     
23   </system.serviceModel>
24 </configuration>

 

 

 

   2)  增加app.config配置文件與配置信息之後,我們原來寫的寄宿代碼就不能使用了,需要進行服務寄宿代碼的修改,而且代碼會變的更簡潔,只需幾行代碼就可以了。代碼如下。

   

 1 using System;
 2 using System.Collections.Generic;
 3 using System.Linq;
 4 using System.Text;
 5 using System.Threading.Tasks;
 6 using Service;
 7 using Service.Interface;
 8 using System.ServiceModel;
 9 using System.ServiceModel.Description;
10 
11 namespace Hosting
12 {
13     class Program
14     {
15         static void Main(string[] args)
16         {
17             using(ServiceHost host = new ServiceHost(typeof(CalculatorService)))
18             {
19                 ////指定綁定和終結點的地址
20                 //host.AddServiceEndpoint(typeof(ICalculator), new WSHttpBinding(), "http://127.0.0.1:3721/calculatorService");
21                 ////數據的發佈
22                 //if(host.Description.Behaviors.Find<ServiceMetadataBehavior>() == null)
23                 //{
24                 //    //創建服務行為
25                 //    ServiceMetadataBehavior behavior = new ServiceMetadataBehavior();
26                 //    //是否發佈元數據以便使用HTTPS/GET請求進行檢索
27                 //    behavior.HttpGetEnabled = true;
28                 //    //使用HTTPS/GET請求的元數據發佈的位置
29                 //    behavior.HttpGetUrl = new Uri("http://127.0.0.1:3721/calculatorService/metadata");
30                 //    //添加到發佈上
31                 //    host.Description.Behaviors.Add(behavior);
32                 //}
33                 host.Opened += delegate
34                 {
35                     Console.WriteLine("CalculatorService已經啟動,按任意鍵終止服務!");
36                 };
37                 //通訊狀態轉換到已打開
38                 host.Open();
39                 Console.ReadLine();
40             }
41         }
42     }
43 }

 

    3) 執行hosting.exe應用程式,結果如下圖。

  

 

 

 下一章節講怎麼通過客戶端去調用我們成功寄宿後的服務 (歡迎關註)

 


您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • centos源更換為,163或者阿裡的。 1、首先備份 mv /etc/yum.repos.d/Centos Base.repo /etc/yum.repos.d/Centos Base.repo.backup 2、下載repo文件到目錄下 cd /etc/yum.repos.d wget http ...
  • 編譯windows下chromium,時間:20170619, 官方地址:https://chromium.googlesource.com/chromium/src/+/master/docs/windows_build_instructions.md 一. 系統要求: 1. 64位機器,至少8G ...
  • 自助命令:ls --help man ls info ls 文件屬性:ls -al 顯示當前目錄下文件/目錄擁有者,所屬組,其他人的寫讀執行許可權 文件或目錄下屬文件數 擁有者 群組 內容大小(byte) 最後修改日期 文件/目錄名 註意:對於目錄,如何沒有x許可權,則進不去目錄 【顯示別的目錄下的文件 ...
  • 輸入:top PID 進程的ID USER 進程所有者 PR 進程的優先順序別,越小越優先被執行 Ninice 值 VIRT 進程占用的虛擬記憶體 RES 進程占用的物理記憶體 SHR 進程使用的共用記憶體 S 進程的狀態。S表示休眠,R表示正在運行,Z表示僵死狀態,N表示該進程優先值為負數 %CPU 進程 ...
  • 不想用實體機,想不想弄個快速的Android虛擬環境,今天我們就來說說把Android模擬器(RemixOS)安到Hyper-v上的辦法。 1. 下載RemixOs 或者直接去 論壇獲得下載地址 2. 在Hyper-v中創建第1代的虛擬機,50G硬碟,2G記憶體。別急著開機。 3. 在電腦管理中打開 ...
  • 沒什麼新的內容,自己的練習代碼,供大家點評。 ...
  • 問題原因可能是: 1. 非空列未插入值錯誤 2. 多個表間外鍵列長度不一樣 3. ef上下文對象db為空 4. ef上下文設置屬性為 db.Configuration.ValidateOnSaveEnabled = false; 5. 內容長度超過列最大長度 6.解決方案里後來新增了類庫但未更新 7 ...
  • 現在驗證碼的形式越來越豐富,今天要實現的是在點擊圖片中的文字來進行校驗的驗證碼,如圖 這種驗證碼驗證是驗證滑鼠是否選中了圖片中文字的位置,以及選擇的順序,產生驗證碼的時候可以提供一組底圖,然後隨機獲取一張圖片,隨機選取幾個字,然後把文字的順序打亂,分別隨機放到圖片的一個位置上,然後記錄文字的位置和順 ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...