摘要:分析了基于Web服務的Acegi安全框架的構架和實現原理,以Web服務中的HTTPForm為例,詳細闡述了Acegi提供的認證和授權機制,并進一步探討了Acegi安全框架的權限管理,以滿足復雜的企業安全需求,從而提高了Web系統的安全性和穩定性。
關鍵詞:Web服務;認證;授權;權限管理
中圖分類號:TP311文獻標識碼:A文章編號:1009-3044(2008)23-897-03
Research and Application of Acegi Security Framework on Web Service
LIU Zhen-hai, YIN Zhao-lin, GENG Wei
(China University of Mining and Technology, Xuzhou 221008, China)
Abstract: Acegi security framework on Web service is analysed. As an example of HTTPForm on Web service, authentication and authorization mechanisms is explicated elaborately. Moreover, this paper discusses purview management of Acegi framework to meet the complex security needs of enterprises and improve the Web system of security and stability.
Key words: Web service; authentication; authorization; purview management
1 引言
隨著Web服務技術的發展,安全性往往是企業信息化開發中最為重要的問題之一,如何更好地實現Web應用系統安全成為開發人員所面臨的棘手問題。在企業的Web應用系統中,完善、靈活、高效的認證和授權機制是非常必要的,而且由于Web 業務需求面臨著不斷的變化,這些權限的認證和授權系統應該實現與已有的業務邏輯代碼松耦合,傳統的Java安全組件都不能很好地融入Web應用系統中,本文采用Spring Framework的Acegi安全框架來實現Web應用系統安全,它的架構和設計目標更符合企業級應用的需求。
2 Acegi框架的安全管理對象
Acegi是一個基于Spring Framework的安全框架,能夠和目前流行的Web容器無縫集成。它使用Spring的方式提供安全和認證服務,包括使用Bean Context,攔截器和面向接口的編程方式。通過精心配置Acegi安全系統,能夠輕松地適用于復雜的安全需求。Acegi安全系統目前支持3類安全管理對象。
1)MethodInvocation:開發人員可以用它來保護Spring容器中的業務對象。為了使Spring的管理Bean可以作為MethodInvocation使用,Bean可以通過ProxyFactoryBean和BeanNameAutoProxy-Creator來管理,就像在Spring的事務管理中一樣使用。
2)FilterInvocation:它通過過濾器(Filter)創建,并簡單地包裝了HTTP的ServletRequest、ServletResponse和FilterChain。FilterInvocation可以用來保護HTTP資源。通常,開發人員并不需要了解它的工作機制,因為他們只需要將Filter加入web.xml,Acegi安全系統就可以工作了。
3)AspecctJ joinPoint:AspectJ是一個基于Java語言擴展的AOP實現,它提供了強大的AOP功能,在領域對象保護方面特別有用,這些領域對象絕大部分是在Spring容器之外被管理。通過使用AspectJ,一個標準的構造函數,例如:new Person(),能夠在正常使用的同時,全面的被Acegi系統保護起來。AspectJSecurityInterceptor是由Spring進行管理的,Spring創建關于方面(aspect)的單實例對象,并且將它與相應的認證管理、存取管理等有效地編織在一起。
每個安全管理對象都可以描述數量不限的各種安全認證請求。例如,FilterInvocation可以描述任意的HTTP URL,而MethodInvocation可以描述帶有任意參數的任意方法的調用。
3 Acegi安全框架的分析
為實現對Web服務和POJO對象中方法的保護,Acegi提供了七項重要組件,分別是:
1)Authentication,包含了Principal(用戶),Credential(密碼)和Principal的授權信息。同時,還可以包含關于發起認證請求的客戶的其它信息,如IP地址;
2)ContextHolder,使用ThreadLocal儲存Authentication對象的地方;
3)AuthenticationManager(認證管理器),用于認證ContextHolder中的Authentication對象;
4)AccessDecissionManager(訪問決定管理器),用于授權一個特定的操作;
5)RunAsManager,當執行特定的操作時,用于選擇性地替換Authentication對象;
6)Secure Object攔截器,用于對用戶進行認證、授權,或給它賦予不同的角色(RunAsManager);
7)ObjectDefinitionSource,包含特定操作的授權定義。
這7個關鍵的功能組件的關系如圖1所示。
4 Acegi安全框架的實現原理
Acegi安全系統需要記錄應用于每個認證請求的安全配置參數。為了保存不同的認證請求的安全配置,需要使用配置參數。從實現的視角來看,配置參數使用ConfigAttribute接口來表示Acegi安全系統提供了ConfigAttribute接口的一個實現SecurityConfig,它把配置參數保存為一個字符串。ConfigAttributeDefinition類是ConfigAttribute對象的一個簡單的容器,它保存了和特定請求相關的ConfigAttribute的集合。
在采用了Acegi框架的Web系統中,如果用戶請求訪問受保護的資源,Acegi就會對請求進行攔截,然后進行認證、授權;如果審查通過,則用戶訪問成功,否則失敗。首先安全攔截器把獲得的Authentication對象存在SecurityContextHolder中的ThreadLocal對象中;然后認證管理器從SecurityContextHolder取出用戶信息,認證管理器的具體實現者DaoAuthenticationProvider從數據庫取出用戶信息,它通過比較從數據庫獲取的用戶信息、密碼以及從ThreadLocal里取出的Authentication對象中傳入的主體、憑證完成身體驗證。如果用戶名、密碼與主體、憑證分別匹配,則用戶通過身份驗證,同時返回給認證管理器一個已完全填充的Authentication對象,否則會拋出一個異常,表明驗證失敗;最后,如果認證成功,Acegi框架調用訪問決策管理器來實現用戶的授權。訪問決策管理器的投票者根據用戶具有的權限來對用戶是否用權訪問資源進行投票,Acegi框架根據投票結果進行判斷用戶是否有權訪問資源,如圖2所示。
5 Web服務中Acegi框架的實現及權限管理
5.1 Web服務中Acegi框架的實現
這里以Web服務中的HTTPForm認證為例,說明Acegi認證和授權原理:
1)首先通過HttpSessionContextIntegrationFilter初始化ContextHolder中的內容。如果session中已經存在Context,則直接初始化到ContextHolder中,否則創建一個新的Context,此時url為/j_secuirty_check。
2)進入用戶登錄系統,Acegi從AuthenticationProcessingFilter中得到用戶的登錄信息(包括Principal和Credentia1),然后,調用AuthenticationManager進行認證。若認證通過,返回帶有Principal授權信息的Authentication對象,此時ContextHolder中Authentication對象已擁有Principal的詳細信息;若認證失敗,則轉到“authenticationFailureUrl”。用戶從AuthenticationProcessingFilter中得到用戶的登錄信息,其配置如下:
<bean id=\"authenticationProcessingFilter\"
class=\"net.sf.acegisecurity.ui.webapp.AuthenticationProcessingFilter\">
<property name=\"authenticationManager><ref local=\"authenticationManager\"/></property>
<propertyname=\"authenticationFailureUrl\"><value>/login.jsp?error=true</value></property>
<property name=\"defaultTargetUrl\"><value>/</value></property>
<property name=\"filterProcessesUrl\"><value>/j_security_check</value></property>
</bean>
3)用戶登錄成功后,繼續進行業務操作。
4)安全攔截器(filterInvocationInterceptor)收到客戶端操作請求后,將操作請求的數據包裝成安全管理對象(FilterInvocation對象)。然后,從配置文件(ObjectDefinitionSource)中讀出相關的安全配置參數ConfigAttributeDefinition:
<bean id=\"filterInvocationInterceptor\"
class=\"net.sf.acegisecurity.intercept.web.FilterSecuirtyInterceptor\">
<property name=\"authenticationManager\"><ref local=\"authenticationManager\"/></property>
<property name=\"accessDecisionManager\"><ref local=\"accessDecisionManager\"/></property>
<propertyname=\"objectDefintionSource\">
<value>CONVERT_URL_TO_LOW ERCASE_BEFLRE_CONPARISON
PATTERN_TYPE_APACHE_ANT
/signup.html*ROLE_ANONYM OUS,admin,tomcat
/passwordhint.html*=ROLE_ANONYM OUS,admin,tomcat
/**/*.html*=admin.tomcat
/clickstreams.jsp*admin</value></property></bean>
5)接著,安全攔截器取出ContextHolder中的Authentication對象,把它傳遞給AuthenticationManager進行身份認證,并用返回值更新ContextHolder的Authentication對象:
6)將Authentication對象、ConfigAttributeDeifnition對象和安全管理對象交給AccessDecisionManager,檢查Principal的操作授權;
7)如果授權檢查通過,則執行客戶端請求的動作,否則拒絕。
5.2 Acegi安全框架的權限管理
企業級系統中,資源的權限配置一般將其存儲在數據庫中來管理。通過自定義的類urlDefinitionSource來實現權限配置信息向數據庫的移植,它擴展了PathBasedFilterInvationDefinitionMap類,用作從數據庫結構中讀取權限配置信息并存儲在內存中,其配置為:
<bean id=\"urlDefinitionSource\" class=\"sboss.framework.acegi.urlDefinitionSource\">
<property name=\"urlResourceProvider\"><ref local=\"urlResourceProvider\"/></property>
</bean>
<bean id=\"urlResourceProvider\" class=\"sboss.framework.acegi.urlResourceProviderImpl\">
<property name=\"dataSource\"><ref bean=\"dataSource\"/></property>
<property name=\"Cache\"><ref local=\"sourceCache\"></property>
</bean>
代碼中,Cache是給urlResourceProvider加的一層緩存,目的在于把權限信息存于其中,避免反復的訪問數據庫影響系統性能。方法調用的攔截器MethodSecurityInterceptor與URL的攔截器有所不同,它是借助于Spring AOP實現的。但其配置與filterInvocationInterceptor類似,它的權限配置也涉及到面向數據庫的移植,這里通過類businessDefinitionSource來實現,它擴展了MethodDefinitionMap類,用戶從數據庫結構中讀取權限配置信息并存儲在內存中。
權限配置面向數據庫的移植的過程中,我們加入了cache(緩存),其好處在于當系統讀取一次權限配置信息后,即把該信息存于內存的cache中,當下次需要用到的時候,直接從cache中獲取而不用再次去訪問數據庫,這會節約大量的系統性能。但這也帶來另一個問題,如果通過系統操作改變了數據庫中的權限配置,而cache中存儲的是先前數據庫中的信息,勢必會導致權限的混亂。這時就需要對cache中的權限信息作數據同步處理。
這里采用AOP技術來實現數據同步:利用Spring AOP攔截修改權限配置的業務方法,在該業務方法執行之后,重新從數據庫讀取權限配置信息放入cache中。該過程通過自定義的攔截器retrieveDefinitionSourceInterceptor來實現。配置如下:
<bean id=\"retrieveDefinitionSourceInterceptor\"
class=\"org.springframework.aop.RegexpMethodPointcutAdvisor\">
<property name=\"advice\"><ref bean=\"refreshResourceCache\"/></property>
<property name=\"pattern\">
<list><value>sboss.framework.web.action.RoleAction.add</value>
<value>sboss.framework.web.action.RoleAction.update</value></list></property>
</bean>
類refreshResourceCache實現從數據庫重新讀取權限配置信息再存入cache。
6 結束語
本文主要探討的將Acegi安全框架應用于Web服務中的方法對于構建安全的系統具有重要的參考意義,同時解決了Web服務中的權限管理問題,實現了數據的同步處理,提高了Web服務系統的安全性。
參考文獻:
[1] 夏榆濱,宣明付.基于RBAC的統一權限管理系統研究[J].微計算機信息,2006,22(30):114-116.
[2] 羅時飛.精通Spring[M].北京:電子工業出版社,2005.
[3] Acegi Security System contactssample[EB/OL].http://acegisecurity.org.
[4] Joseph D,Nicholas Lesiecki.精通AspectJ[M].北京:清華大學出版社,2005.
[5] 魏楚元,李陶深,張增芳.J2EE安全機制的分析與研究[J].計算機工程與設計,2005,26(6):1434-1437.