利用Web Services開發分佈式應用

1、引言

  在前面文章中分別介紹了MSMQ和.NET Remoting技術,今天繼續分享.NET 平臺下另外一種分佈式技術——Web Servicesweb

2、Web Services 詳細介紹

2.1 Web Services 概述

   Web Services是支持客戶端與服務器經過網絡互操做的一種軟件系統,是一組能夠經過網絡調用的應用程序API。在Web Services中主要到SOAP/UDDI/WSDL這三個核心概念,下面分別介紹下這三個概念的定義。數據庫

  • SOAP:SOAP(Simple Object Access Protocol,簡單對象訪問協議)是在分散或分佈式的環境中交換信息的簡單協議,是一種基於XML的協議,須要綁定一個網絡傳輸協議來完成信息的傳輸,這個協議一般是Http或Https,但也可使其餘協議。

  它包括四個部分:安全

  SOAP封裝:它定義了一個框架,描述消息中的內容是描述,是誰發送的,誰又應當接收並處理;服務器

  SOAP編碼規則:定義了一種序列化的機制,用於表示應用程序須要使用的數據類型的實例;網絡

  SOAP RPC:表示一種協定,用於表示遠程過程調用和應答;框架

  SOAP綁定:它定義了SOAP使用哪一種協議來進行交換信息。使用Http/TCP/UDP均可以。與WCF中的綁定概念一致。分佈式

  換句話說,SOAP協議只是用來封裝消息用的,封裝後的消息你能夠經過各類已有的協議來傳輸,如Http、Https、Tcp、UDP、SMTP等,甚至你還能夠自定義協議。然而Web Service是採用基於Http協議來傳輸數據的。關於使用Https協議來訪問Web Services的方法能夠參考這個文章:如何利用 SSL 調用 Web 服務測試

  • UDDI:是統一描述、發現和集成(Universal Description, Discovery, and Integration)的縮寫,它是一個基於XML的跨平臺的描述規範,可使世界範圍內的企業在互聯網上發佈本身所提供的服務供其餘客戶查詢使用。
  • WSDL:是Web服務描述語言(Web Services Description Language),是爲描述Web服務發佈的XML格式。用於描述服務器端口訪問方式和使用協議的細節,一般用來輔助生產服務器和客戶端代碼及配置信息。

 

2.2 Web Services 實現過程

   調用Web Services的實現過程與進行常規方法調用過程相似。不一樣的在於,前者方法並不位於客戶端應用程序中,而是經過指定傳輸協議生成請求消息。由於Web Services可能位於不一樣的計算機上,所以必須將Web Services處理請求所需的信息經過網絡傳遞給含有Web Services的服務器,Web Services在處理信息後,會經過網絡將結果發送回客戶端應用程序。下圖顯示了客戶端與Web Services之間的通訊過程:網絡傳輸協議

XML Web services 生存期

  下面介紹下調用Web Services時事件發生順序:編碼

  1. 在客戶端上,建立了一個Web Services代理類的實例。該對象駐留在客戶端機器上。
  2. 客戶端調用代理類上的方法
  3. 客戶端機器將Web Services方法的參數序列化爲SOAP消息,而後經過傳送協議發送給Web Services。
  4. Web Services底層結構接收SOAP消息並進行反序列化。它會建立Web Services的類的實例,同時調用對應的Web Services方法。
  5. Web Services方法執行,並返回結果。
  6. Web Services底層結構會將返回結果序列化爲SOAP消息,而後經過網絡發送回客戶端。
  7. 客戶端將接收SOAP消息,而後將XML反序列爲返回值或任何輸出參數,並將它們傳遞給代理類的實例。
  8. 客戶端接收返回值和全部輸出參數。

2.3 Web Services 優缺點

   通過上面詳細的介紹後,Web Services很明顯具備如下優勢:

  • 跨平臺:Web Services徹底基於XML(可擴展標記語言)、XSD(XMLSchema)等與平臺無關的行業標準。
  • 自描述:Web Service使用WSDL進行自我描述,包括服務的方法、參數、類型和返回值等相關信息。
  • 跨防火牆:Web Service使用http協議進行通訊,能夠穿越防火牆。

  Web Services也具備如下缺點:

  • 效率低下,不適合作單應用系統的開發。
  • 安全問題:Web Services沒有自身的安全機制,必須藉助Http協議或IIS等宿主程序實現信息安全加密。

3、使用Web Services來開發分佈式應用程序

   使用Web Services來開發分佈式應用較MSMQ和.NET Remoting來講相對簡單不少,今天的示例程序分三步走:

  1. 建立一個實現用戶信息驗證的項目WebServiceUserValidation。具體的實現代碼以下所示:
 
 1 namespace WebServiceUserValidation
 2 {
 3     public class UserValidation
 4     {
 5         // 判斷用戶名和密碼是否有效
 6         public static bool IsUserLegal(string name, string psw)
 7         {
 8             // 用戶能夠訪問數據庫進行用戶和密碼驗證
 9             // 這裏僅僅做爲演示
10             string password = "LearningHard";
11             if (string.Equals(password, psw))
12             {
13                 return true;
14             }
15             else 
16             {
17                 return false;
18             }
19         }
20 
21         // 判斷用戶的憑證是否有效
22         public static bool IsUserLegal(string token)
23         {
24             // 用戶能夠訪問數據庫進行用戶憑證驗證
25             // 這裏只作演示
26             string password = "LearningHard";
27             if (string.Equals(password, token))
28             {
29                 return true;
30             }
31             else
32             {
33                 return false;
34             }
35         }
36     }
37 }
 

  2. 建立Web Services服務類,須要建立一個繼承自SoapHeader,來接收SOAP 頭裏的消息,並添加WebServiceUserValidation程序集。經過添加Asp.net 空Web應用程序來建立Web Services服務工程,再右鍵建立的Web 應用程序工程添加一個Web 服務文件來建立Web 服務。具體的實現代碼以下所示:

 
 1 // 用戶自定義的SoapHeader類必須繼承於SoapHeader
 2     public class MySoapHeader : SoapHeader
 3     {
 4         // 存儲用戶憑證
 5         public string Token { get; set; }
 6     }
 7  /// <summary>
 8     /// LearningHardWebService 的摘要說明
 9     /// </summary>
10     [WebService(Namespace = "http://www.cnblogs.com/zhili/")]
11     [WebServiceBinding(ConformsTo = WsiProfiles.BasicProfile1_1)]
12     [System.ComponentModel.ToolboxItem(false)]
13     // 若要容許使用 ASP.NET AJAX 從腳本中調用此 Web 服務,請取消註釋如下行。 
14     // [System.Web.Script.Services.ScriptService]
15     public class LearningHardWebService : System.Web.Services.WebService
16     {
17         // 存儲用戶憑證的Soap Header信息
18         // 必須保證是public和字段名必須與SoapHeader("memberName")中memberName同樣
19         // 不然會出現「頭屬性/字段 LearningHardWebService.authenticationToken 缺失或者不是公共的。」的異常
20         public MySoapHeader authenticationToken; 
21         private const string TOKEN = "LearningHard"; // 存儲服務器端憑證
22         
23 
24         // 定義SoapHeader傳遞的方向
25         //SoapHeaderDirection.In;只發送SoapHeader到服務端,該值是默認值
26         //SoapHeaderDirection.Out;只發送SoapHeader到客戶端
27         //SoapHeaderDirection.InOut;發送SoapHeader到服務端和客戶端
28         //SoapHeaderDirection.Fault;服務端方法異常的話,會發送異常信息到客戶端
29         [SoapHeader("authenticationToken", Direction = SoapHeaderDirection.InOut)]
30         [WebMethod(EnableSession = false)]
31         public string HelloLearningHard()
32         {
33             if (authenticationToken != null && UserValidation.IsUserLegal(authenticationToken.Token))
34             {
35                 return "LearningHard 你好,調用服務方法成功!";
36             }
37             else
38             {
39                 throw new SoapException("身份驗證失敗", SoapException.ServerFaultCode);
40             }
41         }
42     }
 

  在上面代碼中須要注意的是,Web Servies中的Web方法須要拋出SoapExcetion異常才能被客戶端捕獲到,若是在Debug模式下調試運行的話,還須要在異常設置裏把這個異常勾選掉,即編譯器不對該異常進行捕獲。

  3. 建立控制檯客戶端,經過添加服務引用的方式來添加Web Services,添加成功後,會在客戶端程序中建立一個代理類,客戶端能夠經過該代理類來調用Web Services的方法,具體的實現代碼以下所示:

 
 1 namespace WebServiceClient
 2 {
 3     class Program
 4     {
 5         static void Main(string[] args)
 6         {
 7             // 實例化一個Soap協議的頭
 8             MySoapHeader mySoapHeader = new MySoapHeader() { Token = "LearningHard"};
 9             string sResult = string.Empty;
10             LearningHardWebServiceSoapClient learningHardWebSer = null;
11             try
12             {
13                 // 實例化Web服務的客戶端代理類
14                 learningHardWebSer = new LearningHardWebServiceSoapClient();
15                 // 調用Web服務上的方法
16                 sResult= learningHardWebSer.HelloLearningHard(ref mySoapHeader);
17                 // 輸出結果
18                 Console.WriteLine(sResult);
19             }
20             catch
21             {
22                 Console.WriteLine("調用Web服務失敗!");
23             }
24             finally
25             {
26                 // 釋放託管資源
27                 if (learningHardWebSer != null)
28                 {
29                     learningHardWebSer.Close();
30                 }
31             }
32 
33             Console.WriteLine("請按任意鍵結束...");
34             Console.ReadLine();
35         }
36     }
37 }
 

  關於Web Services異常捕獲的更多信息能夠參考MSDN:在 XML Web services 中處理和引起異常。然而在這個MSDN上的示例代碼好像運行不成功,後面發現,該文章中的客戶端對異常的處理只處理了SoapException 異常,而此時客戶端觸發的異常時FaultException異常,因此異常處理代碼應像下面代碼同樣處理,固然也能夠直接只處理Exception異常,我上面代碼就只處理這個大範圍的異常。

 
catch (SoapException ex)
    {
        // Do sth with SoapException 
    }
    catch (Exception ex)
    {
        // Do sth with Exception
    }
 

  通過上面的步驟,咱們就已經完成了全部的開發工做,下面運行來測試下該程序的運行效果。把WebServiceClient做爲啓動項目,直接按F5或Ctrl+F5來運行客戶端程序,你將看到以下所示的結果:

  注:像通常分佈式應用程序,都應用先運行服務器端,再運行客戶端來訪問服務方法。而這裏咱們運行卻直接運行客戶端就能夠訪問Web Services中的Web方法了。這是由於在運行Web Services客戶端程序以前,會先把Web Services部署到IIS Express 中,你將會看到任務欄右下角有,右鍵該圖標就能夠看到運行的Web Services。

4、總結

   到這裏,Web Services技術的分享就結束,從下一篇文章開始,將正式進入WCF的世界。而Web Services的內容和WCF內容同樣也有不少,只是微軟官方推薦採用WCF來建立Web服務程序,若是你想更多地瞭解Web Services的內容,能夠參考MSDN:使用 ASP.NET 建立的 XML Web Services 以及 XML Web Services 客戶端

相關文章
相關標籤/搜索