管道過濾器模式

模式定義

管道過濾器模式將執行復雜處理的任務分解爲可重複使用的一系列離散元素,這種模式能夠提升性能,可擴展性和可重用性,容許執行部署和縮放獨立處理的任務元素。java

特定場景

整個應用的處理能夠被分解成一系列離散的,獨立的步驟的狀況下,能夠考慮使用管道過濾器模式。web

當應用處理的不一樣的步驟,有不一樣的擴展性需求的狀況下,能夠考慮實現管道過濾器模式。服務器

若是須要較強的靈活性的時候,能夠考慮使用管道過濾器模式。管道過濾器模式令應用能夠靈活的配置不一樣的執行步驟和執行序列,並且應用還能夠按需來增長或者減小對應的處理單元。網絡

當須要最大化服務器利用率的時候,能夠選擇管道過濾器模式。架構

若是解決方案須要保證的可靠,須要儘可能下降每個單獨的處理單元中執行的失敗的可能性的時候,能夠考慮使用管道過濾器模式。app

管道過濾器模式將執行復雜處理的任務分解爲可重複使用的一系列離散元素,這種模式能夠提升性能,可擴展性和可重用性,容許執行部署和縮放獨立處理的任務元素。分佈式

問題

一個應用程序可能根據其處理的不一樣的信息須要執行各類複雜的任務。一個簡單的,但不靈活的方法就是能夠將應用的處理做爲一個單獨的模塊。可是,若是部分相同的處理須要在應用程序的其餘地方,這種方法可能會減小代碼重構,重用,優化的機會。性能

不少獨立模塊執行的一些任務在功能上很是類似,可是由於這些模塊是分開設計的,實現任務的代碼都是緊密耦合在一個模塊中,其中的重複部分沒法獲得重用來提升擴展性和重用性。優化

然而,每一個模塊執行的處理任務,或每一個任務的部署要求,可能都會隨着業務需求的修改而改變。有些任務多是計算密集型的,可能會受益於運行在強大的硬件,而其餘任務可能不須要這樣昂貴的資源。此外,在將來可能須要執行一些額外的處理,或命令執行的任務可能會改變。因此須要一個技能解決這些問題,同時也能增長代碼重用的解決方案。加密

解決方案

將每一個數據流所需的處理分解成一組離散的組件(或過濾器),而後由每一個組件來執行一個任務是一種不錯的解決方案。經過標準化每一個組件接收和發出的數據的格式,這些組件(過濾器)能夠組合成一個管道。這種解決方案有助於避免重複代碼,而且在需求發生變化的時候,能夠很容易地刪除,替換或集成額外的組件來實現功能。

處理單個請求的時間取決於管道中最慢的過濾器的速度。尤爲在大量請求發送到組件的時候,某個或者某些組件就可能成爲系統的性能瓶頸。管道結構的一個主要優勢就在於,它爲運行緩慢的過濾器提供了使用並行實例的機會,這樣使系統可以均衡負載,以提升吞吐量。

組成管道的過濾器徹底能夠運行在不一樣的機器上,而且它們能夠利用許多雲環境提供的彈性可以來實現獨立擴展。一個計算密集型的過濾器能夠運行在高性能硬件上,而其餘要求較低的過濾器能夠運行在稍差的硬件上。過濾器甚至沒必要在相同的數據中心或不在同一個地點,管道解決方案容許管道中的每一個元素能夠在接近其所需資源的環境中運行。

若是一個過濾器的輸入和輸出被結構化爲一個流,它就有可能對多個過濾器進行並行處理。管道中的第一個過濾器能夠開始它的工做,並開始分發它的處理結果,這是直接傳遞到下一個過濾器的序列以前,第一個過濾器已完成其工做。

另外一個好處是管道過濾器模式能夠提供很好的跳轉。若是過濾器失敗或正在運行的機器再也不可用,則管道能夠從新安排過濾器正在執行的工做,並將此工做直接指向組件的另外一實例。一個過濾器的故障並不會致使整個管道的故障。

使用管道和過濾器模式與事務補償模式相結合,能夠提供一種替代的方法來實現分佈式事務。分佈式事務能夠分解成獨立的有償任務,每個均可以經過使用一個過濾器,還實現了事務補償模式。管道中的過濾器能夠做爲獨立的託管任務來執行,這些任務還能夠在物理位置上接近他們所維護的數據,以下降網絡代價。

實例

Servlet Filter

凡是開發過J2EE的web application的人員都知道,常常須要處理如下幾種狀況:

  1. 訪問特定資源(Web 頁、JSP 頁、servlet)時的身份認證
  2. 應用程序級的訪問資源的審覈和記錄
  3. 應用程序範圍內對資源的加密訪問,它創建在定製的加密方案基礎上
  4. 對被訪問資源的及時轉換, 包括從 servlet 和 JSP 的動態輸出

在servlet2.3以前這些功能處理是很難實現的,可是Java Servlet 2.3 規範新增了很多激動人心的功能,其中之一即是過濾器(Filter),其實這就是咱們所說的管道和過濾器體系架構在J2EE中的應用實踐. 經過使用該模式使得Web Application開發者可以在請求到達Web資源以前截取請求,在處理請求以後修改應答。

一個執行過濾器的Java 類必須實現javax.servlet.Filter 接口。這一接口含有三個方法:

  1. init(FilterConfig):這是容器所調用的初始化方法。它保證了在第一次 doFilter() 調用前由容器調用。它能獲取在 web.xml 文件中指定的filter初始化參數。
  2. doFilter(ServletRequest, ServletResponse, FilterChain):這是一個完成過濾行爲的方法。它一樣是上一個過濾器調用的方法。引入的 FilterChain 對象提供了後續過濾器所要調用的信息。
  3. destroy():容器在銷燬過濾器實例前,doFilter()中的全部活動都被該實例終止後,調用該方法。
相關文章
相關標籤/搜索