代理模式簡(jiǎn)要介紹(doc 13頁).doc_第1頁
代理模式簡(jiǎn)要介紹(doc 13頁).doc_第2頁
代理模式簡(jiǎn)要介紹(doc 13頁).doc_第3頁
代理模式簡(jiǎn)要介紹(doc 13頁).doc_第4頁
代理模式簡(jiǎn)要介紹(doc 13頁).doc_第5頁
已閱讀5頁,還剩8頁未讀, 繼續(xù)免費(fèi)閱讀

下載本文檔

版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請(qǐng)進(jìn)行舉報(bào)或認(rèn)領(lǐng)

文檔簡(jiǎn)介

描述:讓我們思考一下下面的代碼:/Client1. classCustomer 2. publicvoidsomeMethod() 3. /CreatetheServiceProviderInstance 4. FileUtilfutilObj=newFileUtil(); 5. /AccesstheService 6. futilObj.writeToFile(“SomeData”); 7. 8. 作為它實(shí)現(xiàn)的一部分,Customer類創(chuàng)建了一個(gè)FileUtil類的一個(gè)實(shí)例并且直接訪問它的服務(wù)。換句話說,對(duì)于客戶對(duì)象,訪問FileUtil對(duì)象的方式是很直接的。它的實(shí)現(xiàn)可能是客戶對(duì)象訪問服務(wù)提供者對(duì)象最為普通的方式了。相比較,有些時(shí)候客戶對(duì)象可能不直接訪問服務(wù)提供者(也就是指目標(biāo)對(duì)象),這種情況是由于下面的原因?qū)е碌模海?)目標(biāo)對(duì)象的位置?目標(biāo)對(duì)象可能存在于同一臺(tái)或者不同機(jī)器的不同地址空間。(2)目標(biāo)對(duì)象的存在形式?目標(biāo)對(duì)象可能直到他被請(qǐng)求服務(wù)的時(shí)候還不存在,或者對(duì)象被壓縮。(3)特殊的行為?目標(biāo)對(duì)象可以根據(jù)客戶對(duì)象的訪問權(quán)限接受或拒絕服務(wù)。在多線程環(huán)境,一些服務(wù)提供者對(duì)象需要特殊的考慮。在這些情況下,代理模式(ProxyPattern)建議不要使有特殊需求的客戶對(duì)象直接訪問目標(biāo)對(duì)象,而是使用一個(gè)單獨(dú)的(分離的)對(duì)象(也就是指代理對(duì)象)為不同的客戶提供通常的、直接的訪問目標(biāo)對(duì)象的方式。代理對(duì)象提供和目標(biāo)對(duì)象一樣的接口。代理對(duì)象負(fù)責(zé)與目標(biāo)對(duì)象交互的細(xì)節(jié),代表客戶對(duì)象與目標(biāo)對(duì)象交互。所以客戶對(duì)象不再需要處理訪問目標(biāo)對(duì)象的服務(wù)時(shí)的特殊需求??蛻魧?duì)象通過它的接口調(diào)用代理對(duì)象,代理對(duì)象直接把這些調(diào)用依次地傳遞給目標(biāo)對(duì)象??蛻魧?duì)象不需要知道代理的原對(duì)象(目標(biāo)對(duì)象)。代理對(duì)象隱藏了與客戶對(duì)象進(jìn)行交互的對(duì)象細(xì)節(jié),如:對(duì)象是否是遠(yuǎn)程的、是否初始化、是否需要特殊的權(quán)限等。換句話說,代理對(duì)象作為客戶和不可訪問的遠(yuǎn)程對(duì)象或推遲初始化對(duì)象之間的透明橋梁。代理對(duì)象因使用的場(chǎng)景不同,代理的種類也不同。讓我們來快速的瀏覽一下一些代理和它們的目標(biāo)。注意:表23.1列出了不同種類的代理對(duì)象,在一章中,僅討論遠(yuǎn)程代理,其他的一些代理會(huì)在本書后面的模式中討論。Table23.1:ListofDifferentProxyTypes代理類型目的遠(yuǎn)程代理提供對(duì)在不同地址空間的遠(yuǎn)程對(duì)象的訪問緩存代理/服務(wù)代理為了提供能夠保存目標(biāo)操作經(jīng)常用到的結(jié)果,代理對(duì)象以存儲(chǔ)方式保存這些結(jié)果。當(dāng)客戶對(duì)象請(qǐng)求同一個(gè)操作時(shí),代理不需要直接訪問目標(biāo)對(duì)象,而是從存貯介質(zhì)返回操作結(jié)果。防火墻代理使用防火墻代理主要是為了保護(hù)目標(biāo)對(duì)象以防止有害客戶的訪問。同時(shí)也可以防止客戶訪問有害的目標(biāo)對(duì)象。保護(hù)代理提供了不同客戶訪問不同層次的目標(biāo)對(duì)象的功能。在創(chuàng)建代理時(shí),定義了一個(gè)權(quán)限的集合。雖后,這些權(quán)限用來限制訪問代理的特定部分,如果沒有執(zhí)行方法的權(quán)限,客戶對(duì)象不允許訪問特定的方法。同步代理提供了允許不同的客戶對(duì)象安全的同步訪問目標(biāo)對(duì)象的功能。計(jì)數(shù)代理在執(zhí)行目標(biāo)對(duì)象的方法前,提供了一些審計(jì)機(jī)制。代理模式和其他模式從討論不同的代理對(duì)象中可以看出:代理對(duì)象有兩個(gè)主要的特征:(1)它介于客戶對(duì)象和目標(biāo)對(duì)象之間。(2)它接受客戶對(duì)象的調(diào)用,然后轉(zhuǎn)發(fā)調(diào)用給目標(biāo)對(duì)象。在這種情形下,看上去和本書中前面討論的其他模式有些相似。讓我們討論一下代理模式和一些與它相似的模式之間的相同點(diǎn)和不同點(diǎn)。代理模式和裝飾模式:代理模式:(1)客戶對(duì)象不能直接訪問目標(biāo)對(duì)象(2)代理對(duì)象提供了對(duì)目標(biāo)對(duì)象的訪問控制(在保護(hù)代理中)(3)代理對(duì)象不能再增加其他的功能。裝飾模式:(1)如果需要,客戶對(duì)象不能直接訪問目標(biāo)對(duì)象。(2)裝飾對(duì)象不能控制對(duì)目標(biāo)對(duì)象的訪問。(3)裝飾對(duì)象可以增加額外的功能。代理模式和外觀模式:代理模式:(1)代理對(duì)象代表一個(gè)單一對(duì)象。(2)客戶對(duì)象不能直接訪問目標(biāo)對(duì)象。(3)代理對(duì)象提供了對(duì)于單一目標(biāo)對(duì)象的訪問控制。外觀模式:(1)外觀對(duì)象代表了對(duì)象的一個(gè)子系統(tǒng)。(2)如果必要,客戶對(duì)象可以直接訪問子系統(tǒng)中的對(duì)象。(3)一個(gè)外觀對(duì)象提供了一個(gè)對(duì)子系統(tǒng)組件的簡(jiǎn)單的、高層次的接口.代理模式和責(zé)任鏈模式:代理模式:(1)代理對(duì)象代表了一個(gè)單一的對(duì)象。(2)克輝請(qǐng)求首先被代理對(duì)象所接受,但是不直接被代理對(duì)象處理。(3)客戶請(qǐng)求總是被傳遞給目標(biāo)對(duì)象。(4)假設(shè)客戶與服務(wù)器正常工作,可以保證請(qǐng)求會(huì)得到響應(yīng),責(zé)任鏈模式:(1)責(zé)任鏈包括很多對(duì)象。(2)接受客戶請(qǐng)求的對(duì)象首先處理請(qǐng)求。(3)近當(dāng)現(xiàn)在的接收者不能處理請(qǐng)求時(shí),客戶請(qǐng)求才被傳遞給下一個(gè)對(duì)象。(4)不能保證請(qǐng)求會(huì)得到響應(yīng)。也就是請(qǐng)求已經(jīng)到達(dá)責(zé)任鏈尾,擔(dān)仍然沒有被處理。在Java中,遠(yuǎn)程方法調(diào)用(RMI)充分的利用了遠(yuǎn)程代理模式,讓我們快速的瀏覽一下遠(yuǎn)程方法調(diào)用(RMI)的概念和遠(yuǎn)程方法調(diào)用(RMI)通信過程應(yīng)用的組件。RMI:快速瀏覽RMI使客戶對(duì)象像訪問本地對(duì)象一樣訪問遠(yuǎn)程對(duì)象并調(diào)用其方法成為可能。(如圖23.1)Figure23.1:ClientsViewofItsCommunicationwithaRemoteObjectUsingRMI下面是為實(shí)現(xiàn)RMI功能而一起協(xié)作的不同組件。(1)遠(yuǎn)程接口(RemoteInterface)?一個(gè)遠(yuǎn)程對(duì)象必須實(shí)現(xiàn)一個(gè)遠(yuǎn)程接口(這個(gè)接口擴(kuò)展java.rmi.Remote)。遠(yuǎn)程接口聲明可以被客戶訪問的遠(yuǎn)程對(duì)象的方法。換句話說,遠(yuǎn)程接口可以看成遠(yuǎn)程對(duì)象對(duì)客戶的視圖。需求(要求):1)擴(kuò)展java.rmi.Remote2)在遠(yuǎn)程接口中定義的所有方法必須聲明拋出java.rmi.RemoteException異常。(2)遠(yuǎn)程對(duì)象(RemoteObject)?遠(yuǎn)程對(duì)象負(fù)責(zé)實(shí)現(xiàn)在遠(yuǎn)程接口中定義的方法。需求(要求):1)必須提供遠(yuǎn)程接口的實(shí)現(xiàn)。2)必須擴(kuò)展java.rmi.server.UnicastRemoteObject類。3)必須有一個(gè)沒有參數(shù)的構(gòu)造函數(shù)。4)必須與一個(gè)服務(wù)器相關(guān)聯(lián)。通過調(diào)用零參數(shù)的構(gòu)造函數(shù),服務(wù)器創(chuàng)建遠(yuǎn)程對(duì)象的一個(gè)實(shí)例。(3)RMI注冊(cè)表(RMIRegistry)?RMI注冊(cè)表提供了保持不同遠(yuǎn)程對(duì)象的地址空間。1)遠(yuǎn)程對(duì)象需要存儲(chǔ)在一個(gè)客戶可以通過命名引用(Namereference)來訪問它的RMI注冊(cè)表中。2)一個(gè)給定的命名引用僅可以存儲(chǔ)一個(gè)對(duì)象。(4)客戶(Client)?客戶是一個(gè)試圖訪問遠(yuǎn)程對(duì)象的應(yīng)用程序。1)必須可以感知被遠(yuǎn)程對(duì)象實(shí)現(xiàn)的接口。2)通過命名引用(Namereference)在RMI注冊(cè)表中可以查到遠(yuǎn)程對(duì)象。一旦查到遠(yuǎn)程對(duì)象的引用,調(diào)用這個(gè)引用上的方法。(5)RMIC(JavaRMI樁編譯器)JavaRMIstubcompiler?一旦遠(yuǎn)程對(duì)象編譯成功,RMIC(JavaRMI樁編譯器)可以生成遠(yuǎn)程對(duì)象的樁類文件(stub)和框架類文件(skeleton)。樁類文件(stub)和框架類文件(skeleton)從編譯的遠(yuǎn)程對(duì)象類中產(chǎn)生。這些樁類文件(stub)和框架類文件(skeleton)使客戶對(duì)象以無縫的方式訪問遠(yuǎn)程對(duì)象成為可能。下面這部分描述客戶對(duì)象和遠(yuǎn)程對(duì)象如何通信。RMI通信機(jī)制:一般地,客戶對(duì)象不能按通常方式直接訪問遠(yuǎn)程對(duì)象。為了使客戶對(duì)象像訪問本地對(duì)象一樣訪問遠(yuǎn)程對(duì)象的服務(wù),RMIC(JavaRMI樁編譯器)生成的遠(yuǎn)程對(duì)象的樁文件(stub)和遠(yuǎn)程接口需要拷貝到客戶機(jī)器上。樁文件(stub)負(fù)責(zé)扮演著遠(yuǎn)程對(duì)象的(遠(yuǎn)程)代理的角色,負(fù)責(zé)把方法的調(diào)用傳遞給真實(shí)的遠(yuǎn)程對(duì)象實(shí)現(xiàn)所在的遠(yuǎn)程服務(wù)器上。任何時(shí)候,客戶對(duì)象引用遠(yuǎn)程對(duì)象,這個(gè)引用實(shí)際上是遠(yuǎn)程對(duì)象的本地樁文件。也就是,當(dāng)客戶調(diào)用遠(yuǎn)程對(duì)象上的方法時(shí),調(diào)用首先被本地樁實(shí)例所接受,樁再將這個(gè)調(diào)用傳遞到遠(yuǎn)程服務(wù)器上。在服務(wù)器端,RMIC產(chǎn)生的遠(yuǎn)程對(duì)象的框架文件(skeleton)接受這個(gè)調(diào)用。框架文件(skeleton)在服務(wù)器端,不需要拷貝到客戶機(jī)器上??蚣芪募?skeleton)負(fù)責(zé)將這些調(diào)用轉(zhuǎn)發(fā)到真正的遠(yuǎn)程對(duì)象的實(shí)現(xiàn)上。一旦遠(yuǎn)程對(duì)象執(zhí)行了方法,方法返回的結(jié)果將按照反方向返回給客戶。圖23.2說明了RMI通信的過程Figure23.2:TheActualRMICommunicationProcess了解更多的關(guān)于JavaRMI的知識(shí),推薦閱讀RMItutorialRMI和遠(yuǎn)程代理模式:從RMI通信的討論中,可以看到樁類文件扮演著遠(yuǎn)程對(duì)象的遠(yuǎn)程代理的角色。它使得客戶訪問遠(yuǎn)程對(duì)象就像訪問本地對(duì)象一樣成為可能。因此,一些使用了RMI技術(shù)的應(yīng)用就已經(jīng)暗含著代理模式的實(shí)現(xiàn)。例子:在討論外觀模式時(shí),我們建立了一個(gè)簡(jiǎn)單的客戶數(shù)據(jù)管理應(yīng)用來驗(yàn)證和保存輸入的客戶數(shù)據(jù)。我們的設(shè)計(jì)由分別代表不同客戶數(shù)據(jù)的三個(gè)類組成。在應(yīng)用外觀模式以前,客戶AccountManager可以直接與子系統(tǒng)的三個(gè)用來驗(yàn)證、保存客戶數(shù)據(jù)的類交互。應(yīng)用外觀模式,我們定義了一個(gè)CustomFacade外觀對(duì)象代表客戶與三個(gè)子系統(tǒng)類交互(如圖23.3)。Figure23.3:CustomerDataManagementApplicationfortheLocalModeofOperation?ClassAssociation在這個(gè)應(yīng)用中,子系統(tǒng)組件和外觀對(duì)象對(duì)于客戶對(duì)象AccountManager都是本地的?,F(xiàn)在,讓我們建立這個(gè)應(yīng)用的不同版本,這個(gè)版本已遠(yuǎn)程的方式運(yùn)行。在遠(yuǎn)程方式下,這個(gè)應(yīng)用通過運(yùn)用JAVARMI技術(shù),訪問遠(yuǎn)程對(duì)象。在使應(yīng)用運(yùn)行在遠(yuǎn)程操作模式下的設(shè)計(jì)中,我們要把子系統(tǒng)組件(Account、Address和CreditCard)和外觀(CustomerFacade)移到遠(yuǎn)程服務(wù)器上。這樣會(huì)帶來以下好處:1)在服務(wù)器上的對(duì)象可以被不同的客戶應(yīng)用所共享。客戶不再需要維護(hù)這些類的本地版本,因此,成為輕型客戶端(light-weighted)。2)可以對(duì)變化、性能和監(jiān)控進(jìn)行統(tǒng)一的集中控制。Figure23.4:CustomerDataManagementApplicationfortheRemoteModeofOperation?ClassAssociation讓我們開始運(yùn)用RMI技術(shù)設(shè)計(jì)遠(yuǎn)程操作模式下的客戶數(shù)據(jù)管理應(yīng)用。第一步,先定義遠(yuǎn)程接口CustomerIntr:這個(gè)借口要滿足:1)聲明外觀實(shí)現(xiàn)的方法。2)所有的方法聲明拋出RemoteException異常。3)擴(kuò)展java.rmi.Remote接口。1. publicinterfaceCustomerIntrextendsjava.rmi. 2. voidsetAddress(inAddress)throwsRemoteException; 3. voidsetCity(inCity)throwsRemoteException; 4. voidsetState(inState)throwsRemoteException; 5. voidsetFName(inFName)throwsRemoteException; 6. voidsetLName(inLName)throwsRemoteException; 7. voidsetCardType(inCardType)throwsRemoteException; 8. voidsetCardNumber(inCardNumber) 9. throwsRemoteException; 10. voidsetCardExpDate(inCardExpDate) 11. throwsRemoteException; 12. booleansaveCustomerData()throwsRemoteException; 13. 讓我們重新定義CustomerFacade外觀類,因?yàn)樗獙?shí)現(xiàn)CustomerIntr遠(yuǎn)程接口。不同的客戶對(duì)象通過CustomerIntr接口在具體類CustomerFacade上的實(shí)現(xiàn)與子系統(tǒng)對(duì)象進(jìn)行交互。圖23.5展示了CustomerFacade和它實(shí)現(xiàn)的遠(yuǎn)程接口CustomerIntr之間的結(jié)構(gòu)和關(guān)聯(lián)。Listing23.1:CustomerFacadeClass?Revised1. publicclassCustomerFacadeextendsUnicastRemoteObject 2. implementsCustomerIntr 3. privateaddress; 4. privatecity; 5. privatestate; 6. privatecardType; 7. privatecardNumber; 8. privatecardExpDate; 9. privatefname; 10. privatelname; 11. publicCustomerFacade()throwsRemoteException 12. super(); 13. .out.println(Serverobjectcreated); 14. 15. publicstaticvoidmain( args)throws 16. port=1099; 17. host=localhost; 18. /Checkforhostnameargument 19. if(args.length=1) 20. host=args0; 21. 22. if(args.length=2) 23. port=args1; 24. 25. if(.getSecurityManager()=null) 26. .setSecurityManager(newRMISecurityManager(); 27. 28. /Createaninstanceoftheserver 29. CustomerFacadefacade=newCustomerFacade(); 30. /BinditwiththeRMIRegistry 31. Naming.bind(/+host+:+port+/CustomerFacade”, 32. facade); 33. .out.println(ServiceBound); 34. 35. publicvoidsetAddress(inAddress) 36. throwsRemoteException 37. address=inAddress; 38. 39. publicvoidsetCity(inCity) 40. throwsRemoteExceptioncity=inCity; 41. 42. publicvoidsetState(inState) 43. throwsRemoteExceptionstate=inState; 44. 45. publicvoidsetFName(inFName) 46. throwsRemoteExceptionfname=inFName; 47. 48. publicvoidsetLName(inLName) 49. throwsRemoteExceptionlname=inLName; 50. 51. publicvoidsetCardType(inCardType) 52. throwsRemoteException 53. cardType=inCardType; 54. 55. publicvoidsetCardNumber(inCardNumber) 56. throwsRemoteException 57. cardNumber=inCardNumber; 58. 59. publicvoidsetCardExpDate(inCardExpDate) 60. throwsRemoteException 61. cardExpDate=inCardExpDate; 62. 63. publicbooleansaveCustomerData()throwsRemoteException 64. AddressobjAddress; 65. AccountobjAccount; 66. CreditCardobjCreditCard; 67. /* 68. clientistransparentfromthefollowing 69. setofsubsystemrelatedoperations. 70. */ 71. booleanvalidData=true; 72. errorMessage=; 73. objAccount=newAccount(fname,lname); 74. if(objAccount.isValid()=false) 75. validData=false; 76. errorMessage=InvalidFirstName/LastName; 77. 78. objAddress=newAddress(address,city,state); 79. if(objAddress.isValid()=false) 80. validData=false; 81. errorMessage=InvalidAddress/City/State; 82. 83. objCreditCard=newCreditCard(cardType,cardNumber, 84. cardExpDate); 85. if(objCreditCard.isValid()=false) 86. validData=false; 87. errorMessage=InvalidCreditCardInfo; 88. 89. if(!validData) 90. .out.println(errorMessage); 91. returnfalse; 92. 93. if(objAddress.save()&objAccount.save()& 94. objCreditCard.save() 95. returntrue; 96. else 97. returnfalse; 98. 99. 100. Figure23.5:FaadeDesign?RemoteModeofOperation因?yàn)樽酉到y(tǒng)組件對(duì)于CustomerFacade類是本地的,子系統(tǒng)組件初始化、方法調(diào)用的方式上沒有任何變化,子系統(tǒng)組件對(duì)于CustomerFacade類仍然是本地對(duì)象。當(dāng)執(zhí)行的時(shí)候,CustomerFacade自己創(chuàng)建一個(gè)實(shí)例并把引用名稱(referencename)保存在RMI注冊(cè)表中。客戶對(duì)象通過引用名稱能取得遠(yuǎn)程對(duì)象的一個(gè)拷貝。因?yàn)榭蛻舨恍枰苯釉L問任何的子系統(tǒng)組件。所以在遠(yuǎn)程操作模式下的設(shè)計(jì)中,不需要對(duì)子系統(tǒng)的任何組件進(jìn)行任何的修改。讓我們重新設(shè)計(jì)客戶類AccountManager:Listing23.2:AccountManagerClass?Revised 1. 2. 3. publicvoidactionPerformed(ActionEvente) 4. 5. 6. if(e.getActionCommand().equals( 7. AccountManager.VALIDATE_SAVE) 8. /getinputvalues 9. firstName=objAccountManager.getFirstName(); 10. lastName=objAccountManager.getLastName(); 11. address=objAccountManager.getAddress(); 12. 13. 14. try 15. /CallregistryforAddOperation 16. facade=(CustomerIntr)Naming.lookup(rmi:/+ 17. objAccountManager.getRMIHost()+:+ 18. objAccountManager.getRMIPort()+ 19. /CustomerFacade); 20. facade.setFName(firstName); 21. facade.setLName(lastName); 22. facade.setAddress(address); 23. 24. 25. /Clientisnotrequiredtoaccesssubsystemcomponents. 26. booleanresult=facade.saveCustomerData(); 27. if(result) 28. validateCheckResult= 29. ValidCustomerData:DataSavedSuccessfully; 30. else 31. validateCheckResult= 32. InvalidCustomerData:DataCouldNotBeSaved; 33. 34. catch(ex) 35. .out.println( 36. Error:Pleasechecktoensurethe+ 37. remoteserverisrunning+ 38. ex.getMes

溫馨提示

  • 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請(qǐng)下載最新的WinRAR軟件解壓。
  • 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請(qǐng)聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
  • 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會(huì)有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
  • 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
  • 5. 人人文庫(kù)網(wǎng)僅提供信息存儲(chǔ)空間,僅對(duì)用戶上傳內(nèi)容的表現(xiàn)方式做保護(hù)處理,對(duì)用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對(duì)任何下載內(nèi)容負(fù)責(zé)。
  • 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請(qǐng)與我們聯(lián)系,我們立即糾正。
  • 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時(shí)也不承擔(dān)用戶因使用這些下載資源對(duì)自己和他人造成任何形式的傷害或損失。

最新文檔

評(píng)論

0/150

提交評(píng)論