程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> JAVA編程 >> 關於JAVA >> Acegi(八):securityContextHolderAwareRequestFilter

Acegi(八):securityContextHolderAwareRequestFilter

編輯:關於JAVA

上篇 中我們說了下 LogoutFilter的配置, 這篇裡接著看另一個常見的配置SecurityContextHolderAwareRequestFilter. 下面先看怎麼把它配置到Acegi裡.

應該說對 securityContextHolderAwareRequestFilter 的配置要比LogoutFilter的更簡單些. 有以下兩步:

Step1: 定義一個名為securityContextHolderAwareRequestFilter的bean, 如下所示:

Xml代碼

<bean id="securityContextHolderAwareRequestFilter"
class="org.acegisecurity.wrapper.SecurityContextHolderAwareRequestFilter" />

呵呵, 簡單地我就有些不好意思往這寫了. 就這麼一個干巴巴的類, 別什麼屬性要配置的.

Step2: 把定義好的 securityContextHolderAwareRequestFilter放到 filterInvocationDefinitionSource裡, 如下所示:

/**=httpSessionContextIntegrationFilter,logoutFilter,authenticationProcessingFilter,securityContextHolderAwareRequestFilter ,exceptionTranslationFilter,filterInvocationInterceptor

上面是對它的配置, 這個配置有些干巴巴的, 那它究竟有什麼用呢? 我們接著往下看, 那將是一個豐富多彩的世界.

SecurityContextHolderAwareRequestFilter類名怎麼這麼長? 也看不出什麼有用的信息啊. 不過, 看文檔得知 SecurityContextHolderAwareRequestFilter的作用是:將傳來的 request用一個 HttpServletRequestWrapper封裝下再傳給 filterChain. 我們不禁要問? 為什麼要這麼做呢? 也就是說這麼做有什麼好處呢?

要弄通這個問題, 我們得看這個Filter對傳的 request做了些什麼手腳, 也就是說是以什麼樣的一個 HttpServletRequestWrapper來封裝了傳來的 request. 在Acegi中我們發現就有兩個 HttpServletRequestWrapper的子類: SecurityContextHolderAwareRequestWrapper和 SavedRequestAwareWrapper. 它們又有什麼樣的特質呢? 發現 SavedRequestAwareWrapper是 SecurityContextHolderAwareRequestWrapper的子類, 為了鑽研的方便, 我們先看父類 SecurityContextHolderAwareRequestWrapper , 所謂有其父必有其子嘛.

先解剖下這個類, 這個類只有一個屬性authenticationTrustResolver(其實它沒什麼多大的用處, 待會再細說), 覆蓋了 HttpServletRequestWrapper的三個方法: getRemoteUser, getUserPrincipal, isUserInRole.

(這裡先順便說下, 我以前一直沒注意到上面的這三個方法是接口裡定義的, 看來Servlet規范裡早就考慮到Security方面的問題了; 另一個沒注意到的是, 原來 Principal是Java標准類security包下的定義的接口, 而Acegi裡重要的接口 Authentication是繼承自 Principal )

於是問題就轉為為什麼要單獨再覆蓋這三個方法了.那得看這三個方法又都干了什麼. 看方法的實現, 發現它們實際上是做了同樣的事, 即通過 SecurityContextHolder.getContext().getAuthentication()拿到 Authentication後再get出String類型的 RemoteUser,或 Principal類型信息, 或看這個 Authentication是否有指定的權限. 也就是說它們把Acegi裡自身的驗證信息放到Servlet規范裡體現的對Security的支持!

那為什麼非要用Acegi的認證信息來替換或填充Servlet規范中 Security信息呢? 我想有這麼幾點好處:

1, 替換掉Web容器自身的認證信息. 拿Tomca為例, 我們知道在Tomcat中可以配置管理權限的, 若Tomcat自身配置了權限管理, 而Acegi不做什麼處理的話, 程序員從 HttpServletRequest裡通過調用上面三種方法得到的Security方面的信息就不是通過Acegi配置的了, 那樣豈不就亂套了? Acegi自身的Security作用也就給架空了, 這還得了? 於是Acegi就有果斷地通過 SecurityContextHolderAwareRequestWrapper把漏洞給補上了.

2, 還有一個可能的好處, 那就是通過這種覆蓋處理, 程序員可以在Action或JSP中方便地得到當前登錄用戶的信息, 而不必在系統中揉合進Acegi自己的API. 項目中這樣的反例太多了.

通過上面的分析,再看類的名字 SecurityContextHolderAwareRequestFilter, 這樣也就好理解了, 真是顧名思義! 這個名字表達的意思是說, 這個Filter是讓Request 來aware下SecurityContextHolder裡的信息, 這個讓它Aware正是通過覆蓋三個方法實現的.

好了, 這篇就寫到這裡, 下一篇中我們將看 SecurityContextHolderAwareRequestFilter子類 SavedRequestAwareWrapper又加了些什麼功能. Until the next.

  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved