日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程语言 > asp.net >内容正文

asp.net

WCF分布式开发必备知识(2):.Net Remoting

發(fā)布時間:2025/3/19 asp.net 30 豆豆
生活随笔 收集整理的這篇文章主要介紹了 WCF分布式开发必备知识(2):.Net Remoting 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.
上一節(jié)我們學習了網(wǎng)絡(luò)分布式編程中的MSMQ消息隊列技術(shù).本節(jié)我們將學習分布式編程的另外一個重要的技術(shù).Net Remoting,文章的結(jié)構(gòu)還是先討論基本概念,再來探討具體的技術(shù)實現(xiàn),希望能和大家一起交流學習. .Net Remoting技術(shù),我們可以將其看作是一種分布式處理方式。作為應(yīng)用程序之間通信的一種機制,.Net Remoting與MSMQ消息隊列不同,它不支持離線脫機消息,另外只適合.Net平臺間程序的通信.從微軟的產(chǎn)品角度來看,可以說Remoting就是分布式組件DCOM的一種升級,它改善了很多功能,并極好的融合到.Net平臺下。.NET Remoting 提供了一種允許對象通過應(yīng)用程序域與另一對象進行交互的框架。這也正是我們使用Remoting的原因。為什么呢?在Windows操作系統(tǒng)中,是將應(yīng)用程序分離為單獨的進程。這個進程形成了應(yīng)用程序代碼和數(shù)據(jù)周圍的一道邊界。如果不采用進程間通信IPC(Internet Process Connection)機制,則在一個進程中執(zhí)行的代碼就不能訪問另一進程。這是一種操作系統(tǒng)對應(yīng)用程序的保護機制。然而在某些情況下,我們需要跨過應(yīng)用程序域,與另外的應(yīng)用程序域進行通信,即穿越邊界(參考MSDN)。 .Net Remoting的通信架構(gòu)如下圖. 我們可以通過上圖簡單理解一下.Net Remoting的通信框架,而現(xiàn)在來介紹一下其中涉及到的幾個比較重要的概念: 1.通道(channel), 在.Net Remoting中是通過通道(channel)來實現(xiàn)兩個應(yīng)用程序域之間對象的通信的。首先,客戶端通過Remoting,訪問通道以獲得服務(wù)端對象,再通過代理解析為客戶端對象。這就提供一種可能性,即以服務(wù)的方式來發(fā)布服務(wù)器對象。遠程對象代碼可以運行在服務(wù)器上(如服務(wù)器激活的對象和客戶端激活的對象),然后客戶端再通過Remoting連接服務(wù)器,獲得該服務(wù)對象并通過序列化在客戶端運行。 通道(channel)有4種嚴格說,很多資料上說有2-3種.應(yīng)該有4種.HttpChanel和TcpChanel. (1)HttpChannel。在將遠程對象駐留在 ASP.NET 中時,可以使用此通道。此通道使用 HTTP 協(xié)議在客戶端和服務(wù)器之間發(fā)送消息??梢允褂肏TTP協(xié)議中的加密機制.需要主機名字和端口號.
(2)TcpChannel。在將遠程對象駐留在? 操作系統(tǒng)服務(wù)或其他可執(zhí)行文件中時,此通道使用 TCP 套接字在客戶端和服務(wù)器之間發(fā)送消息。同樣需要提供主機名字和端口號.不提供任何內(nèi)置的安全功能。 (3)IPCChanel,進程間通道,只使用同一個系統(tǒng)內(nèi),進程之見的通信.不需要需要主機名字和端口號.
(4)自定義通道 。自定義的傳輸通道可以使用任何基本的傳輸協(xié)議UDP\SMTP\IPX\消息排隊等機制進行通信.用戶可以根據(jù)需要自定義方式協(xié)議,因此.Net Remoting相對其他機制更加的靈活。不提供任何內(nèi)置的安全功能。 2.遠程對象(Obeject) 在Remoting中要傳遞的對象,設(shè)計者除了需要了解通道的類型和端口號之外,無需再了解數(shù)據(jù)包的格式。但必須注意的是,客戶端在獲取服務(wù)器端對象時,并不是獲得實際的服務(wù)端對象,而是通過代理獲得它的引用。遠程對象要繼承自MarshalByRefObject類,這個可以使遠程對象在remoting應(yīng)用通信中使用,支持對象的跨域邊界訪問. 3.激活方式 (1)服務(wù)器端激活,又叫做知名WellKnown方式,是因為服務(wù)器應(yīng)用程序在激活對象實例之前會在一個眾所周知的統(tǒng)一資源標識符(URI)上來發(fā)布這個類型。然后該服務(wù)器進程會為此類型配置一個WellKnown對象,并根據(jù)指定的端口或地址來發(fā)布對象。服務(wù)器端激活又分為SingleTon模式和SingleCall模式兩種。SingleTon模式:此為有狀態(tài)模式。如果設(shè)置為SingleTon激活方式,則Remoting將為所有客戶端建立同一個對象實例。SingleCall模式:SingleCall是一種無狀態(tài)模式。一旦設(shè)置為SingleCall模式,則當客戶端調(diào)用遠程對象的方法時, Remoting會為每一個客戶端建立一個遠程對象實例,至于對象實例的銷毀則是由GC自動管理的。 (2)客戶端激活。與WellKnown模式不同, Remoting在激活每個對象實例的時候,會給每個客戶端激活的類型指派一個URI。客戶端激活模式一旦獲得客戶端的請求,將為每一個客戶端都建立一個實例引用。SingleCall模式和客戶端激活模式是有區(qū)別的:首先,對象實例創(chuàng)建的時間不一樣??蛻舳思せ罘绞绞强蛻粢坏┌l(fā)出調(diào)用的請求,就實例化;而SingleCall則是要等到調(diào)用對象方法時再創(chuàng)建。其次,SingleCall模式激活的對象是無狀態(tài)的,對象生命期的管理是由GC管理的,而客戶端激活的對象則有狀態(tài),其生命周期可自定義。其三,兩種激活模式在服務(wù)器端和客戶端實現(xiàn)的方法不一樣。尤其是在客戶端,SingleCall模式是由 GetObject()來激活,它調(diào)用對象默認的構(gòu)造函數(shù)。而客戶端激活模式,則通過CreateInstance()來激活,它可以傳遞參數(shù),所以可以調(diào)用自定義的構(gòu)造函數(shù)來創(chuàng)建實例。(詳細參考MSDN)
?????(4)代理Proxy,客戶端訪問的不能直接訪問遠程對象,它是通過代理來訪問代理上的方法.代理對象又分為透明代理和真實代理,區(qū)別是,在透明代理上,客戶通過Invoke調(diào)用的是遠程對象上真實代理的方法.然后把消息再傳遞給通道. 好了,介紹到此我們也基本了解.Net Remoting相關(guān)的知識,下面我們來學習的是具體的編程實現(xiàn)部分.程序大體分為3個部分遠程對象\服務(wù)器\可戶端.現(xiàn)在我們來分別實現(xiàn).服務(wù)器端要添加引用System.Runtime.Remoting的程序集. 1.遠程對象(RemoteOject),也就是我們遠程要訪問的對象.首先定義一個Class,繼承MarshalByRefObject,可以使用在remoting應(yīng)用中,支持對象的跨域邊界訪問.具體代碼如下: ?1namespace RemoteObject?
?2{?
?3????????//創(chuàng)建遠程對象.繼承MarshalByRefObject,可以使用在remoting應(yīng)用中,支持對象的跨域邊界訪問?
?4????????public?class?MyRemoteObject : MarshalByRefObject//訪問遠程對象需要通過代理?
?5????????{?
?6????????????????//簡單的例子,實現(xiàn)加法功能的方法AddForTcpTest,這個遠程對象可以實現(xiàn)封裝業(yè)務(wù)邏輯或者數(shù)據(jù)訪問等操作。?
?7????????????????//?
?8????????????????public?int?AddForTcpTest(int?a,?int?b)?
?9????????????????{?
10????????????????????????return?a + b;?
11????????????????}?
12????????????????//實現(xiàn)減法功能的方法MinusForHttpTest,測試HTTP通道。?
13????????????????public?int?MinusForHttpTest(int?a,?int?b)?
14????????????????{?
15????????????????????????return?a - b;?
16????????????????}?
17????????????????//實現(xiàn)乘法功能的方法MultipleForIpcTest,測試Ipc通道?
18????????????????public?int?MultipleForIpcTest(int?a,?int?b)?
19????????????????{?
20????????????????????????return?a * b;?
21????????????????}?
22????????}????
23?
24} ?????對象分別定義了3種方法,目的是為了測試3種不同的通道方式的效果.?//簡單的例子,實現(xiàn)加法功能的方法AddForTcpTest,這個遠程對象可以實現(xiàn)封裝業(yè)務(wù)邏輯或者數(shù)據(jù)訪問等操作。實現(xiàn)減法功能的方法MinusForHttpTest,測試HTTP通道。實現(xiàn)乘法功能的方法MultipleForIpcTest,測試Ipc通道. 2服務(wù)器端,注冊通道,以便進程間通信,我們這里注冊了三種通道,分別是HttpChanel\TcpChanel\IPCChanel.具體代碼如下: //創(chuàng)建三種通道/
????????????
///創(chuàng)建Tcp通道,使用端口10001
????????????TcpChannel?chanTcp?=?new?TcpChannel(10001);
????????????
///創(chuàng)建Http通道,使用端口10002
????????????HttpChannel?chanHttp?=?new?HttpChannel(10002);
????????????
///創(chuàng)建IPC通道,使用端口10003,IPC只適合同系統(tǒng)內(nèi)進程的通信,所以不需要設(shè)置端口和主機名
????????????IpcChannel?chanIPC?=?new?IpcChannel("FrankTestIpc");
????????????
//注冊通道//

????????????
///注冊TCP通道
????????????ChannelServices.RegisterChannel(chanTcp);
????????????
///注冊HTTP通道
????????????ChannelServices.RegisterChannel(chanHttp);
????????????
///注冊IPC通道
????????????ChannelServices.RegisterChannel(chanIPC);

????????????
////打印通道/
????????????//?打印TCP通道的名稱.
????????????Console.WriteLine("The?name?of?the?TCPChannel?is?{0}.",
????????????????chanTcp.ChannelName);
????????????
//?打印TCP通道的優(yōu)先級.
????????????Console.WriteLine("The?priority?of?the?TCPChannel?is?{0}.",
????????????????chanTcp.ChannelPriority);

????????????
//?打印Http通道的名稱.
????????????Console.WriteLine("The?name?of?the?HttpChannel?is?{0}.",
????????????????chanHttp.ChannelName);
????????????
//?打印Http通道的優(yōu)先級.
????????????Console.WriteLine("The?priority?of?the?HttpChannel?is?{0}.",
????????????????chanHttp.ChannelPriority);

????????????
//?打印IPC通道的名稱.
????????????Console.WriteLine("The?name?of?the?IpcChannel?is?{0}.",
????????????????chanIPC.ChannelName);
????????????
//?打印IPC通道的優(yōu)先級.
????????????Console.WriteLine("The?priority?of?the?IpcChannel?is?{0}.",
????????????????chanIPC.ChannelPriority);
????????????
///注冊對象/
????????????//注冊對象MyRemoteObject到Net?Remoting運行庫
????????????
//配置遠程通信基礎(chǔ)框架.第2個參數(shù)是對象的URI,“RemoteObject.MyRemoteObject”,客戶端URL一定要和這個匹配,不然會出現(xiàn)查找不到代理對象的異常
????????????RemotingConfiguration.RegisterWellKnownServiceType(typeof(RemoteObject.MyRemoteObject),?"RemoteObject.MyRemoteObject",?WellKnownObjectMode.Singleton);
????????????
//遠程對象激活方式是單件激活模式,每次調(diào)用共享一個對象,SingleCall激活模式會在每次調(diào)用的時候產(chǎn)生一個新對象

????????????
//向信道暴露一個IPC遠程對象.
????????????
//RemotingConfiguration.RegisterWellKnownService(Type(typeof(RemoteObject),?"RemoteObject.rem",?System.Runtime.Remoting.WellKnownObjectMode.Singleton);

????????????
///For?Debug/
????????????Console.WriteLine("Press?any?key?to?exit!");
????????????System.Console.ReadLine();
????????????創(chuàng)建Tcp通道,使用端口10001,?創(chuàng)建Http通道,使用端口10002,創(chuàng)建IPC通道,使用端口10003,IPC只適合同系統(tǒng)內(nèi)進程的通信,所以不需要設(shè)置端口和主機名.然后調(diào)用ChannelServices類的靜態(tài)方法RegisterChannel進行注冊.最后一步注冊對象MyRemoteObject到Net Remoting運行庫,同時要先配置遠程通信基礎(chǔ)框架.第2個參數(shù)是對象的URI,“RemoteObject.MyRemoteObject”,客戶端URL一定要和這個匹配,不然會出現(xiàn)查找不到代理對象的異常.WellKnownObjectMode.Singleton);遠程對象激活方式是單件激活模式,每次調(diào)用共享一個對象,SingleCall激活模式會在每次調(diào)用的時候產(chǎn)生一個新對象. 3客戶端是控制臺程序(實際項目類型可以替換,這里只是為了作為例子選擇控制臺類型).配置文件進行的設(shè)置如下: ?1<configuration>?
?2????????<appSettings>?
?3????????????????<add key="ServiceURLTcp"?value="tcp://localhost:10001/RemoteObject.MyRemoteObject"/>?
?4????????????????<add key="ServiceURLHttp"?value="http://localhost:10002/RemoteObject.MyRemoteObject"/>?
?5????????????????<add key="ServiceURLIpc"?value="ipc://FrankTestIpc/RemoteObject.MyRemoteObject"/>?
?6????????</appSettings>?
?7????????<system.runtime.remoting>?
?8????????????????????????
?9???????????? </system.runtime.remoting>?
10</configuration>
配置文件設(shè)置的是具體通道的URL信息.具體c#實現(xiàn)代碼如下: 1?
?2namespace RemoteClient?
?3{?
?4????????class?MyClient//客戶端?
?5????????{?
?6????????????????[STAThread]//主線程,建立客戶端程序:注冊通道,根據(jù)URL得到對象代理,使用代理調(diào)用遠程對象
?7?
?8????????????????static?void?Main(string[] args)?
?9????????????????{?
10????????????????????????//為遠程對象創(chuàng)建代理?
11????????????????????????//代理的優(yōu)勢在于不僅可以跨域訪問對象還可以跨進程,和系統(tǒng),使用TCP通道?
12????????????????????????try?
13????????????????????????{?
14????????????????????????????????/**/?
15????????????????????????????????RemoteObject.MyRemoteObject proxyObjectTcp = (RemoteObject.MyRemoteObject)Activator.GetObject(typeof(RemoteObject.MyRemoteObject), System.Configuration.ConfigurationSettings.AppSettings["ServiceURLTcp"]);?
16????????????????????????????????//通過代理訪問對象的方法,輸出結(jié)果?
17????????????????????????????????Console.WriteLine("This call object by TcpChannel,100+200 = {0}", proxyObjectTcp.AddForTcpTest(100, 200));?
18?????????????????????????????????
19????????????????????????????????/**///?
20????????????????????????????????RemoteObject.MyRemoteObject proxyObjectHttp = (RemoteObject.MyRemoteObject)Activator.GetObject(typeof(RemoteObject.MyRemoteObject), System.Configuration.ConfigurationSettings.AppSettings["ServiceURLHttp"]);?
21????????????????????????????????//通過代理訪問對象的方法,輸出結(jié)果?
22????????????????????????????????Console.WriteLine("This call object by HttpChannel,100-200 = {0}", proxyObjectHttp.MinusForHttpTest(100, 200));?
23?????????????????????????????????
24????????????????????????????????/**/ 注冊一個遠程對象的客戶端代理.?
25????????????????????????????????//System.Runtime.Remoting.WellKnownClientTypeEntry remoteType = new System.Runtime.Remoting.WellKnownClientTypeEntry(typeof(RemoteObject.MyRemoteObject), "ipc://FrankTestIpc/RemoteObject.MyRemoteObject");?
26????????????????????????????????//System.Runtime.Remoting.RemotingConfiguration.RegisterWellKnownClientType(remoteType);//如果需要客戶端和住進程通訊,要在客戶端注冊代理,方式和服務(wù)器端注冊注冊遠程對象的代理相同?
27?
28????????????????????????????????RemoteObject.MyRemoteObject proxyObjectIpc = (RemoteObject.MyRemoteObject)Activator.GetObject(typeof(RemoteObject.MyRemoteObject), System.Configuration.ConfigurationSettings.AppSettings["ServiceURLIpc"]);?
29????????????????????????????????//通過代理訪問對象的方法,輸出結(jié)果?
30????????????????????????????????Console.WriteLine("This call object by IpcChannel,100*200 = {0}", proxyObjectIpc.MultipleForIpcTest(100, 200));?
31????????????????????????}?
32????????????????????????catch?(Exception e)?
33????????????????????????{?
34????????????????????????????????throw?e;?
35????????????????????????}?
36????????????????????????finally????
37????????????????????????{?
38?
39????????????????????????}?
40????????????????????????//For Debug?
41????????????????????????Console.WriteLine("Press any key to exit!");?
42????????????????????????Console.ReadLine();?
43????????????????}?
44?
45????????}?
46} 主進程通過配置獲取遠程對象的信息,為遠程對象創(chuàng)建代理,代理的優(yōu)勢在于不僅可以跨域訪問對象還可以跨進程,和系統(tǒng),使用TCP通道,降低系統(tǒng)耦合性.最后客戶端通過代理訪問遠程對象的方法,輸出結(jié)果.首先要運行服務(wù)器端,其次是客戶端,IDE使用的是Visual Studio 2005/2008.其次注意項目引用.運行后的結(jié)果顯示如下. 服務(wù)器: 顯示3個通道都注冊成功. 客戶端:
??客戶端分別通過3種方式調(diào)用遠程對象,進行運算.測試成功! 本文代碼下載./Files/frank_xl/NetRemoting.rar 小結(jié):以上就是全部的.Net Remoting的實現(xiàn)過程.當然.Net Remoting知識范圍很廣,還有異步調(diào)用,安全等.以后再做深入的學習.接下來一節(jié)我打算寫關(guān)于Enterprise Services的文章,其中會涉及到COM+的知識,如COM+中事務(wù)機制.我們有必要好好學習一下.希望本文的能給大家在WCF學習上對.Net Remoting技術(shù)的理解有所幫助.大家有問題可以一起交流~


本文轉(zhuǎn)自 frankxulei 51CTO博客,原文鏈接:http://blog.51cto.com/frankxulei/320394,如需轉(zhuǎn)載請自行聯(lián)系原作者


總結(jié)

以上是生活随笔為你收集整理的WCF分布式开发必备知识(2):.Net Remoting的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。