新聞中心
如何使用 Acegi 保護(hù)在 servlet 容器中運(yùn)行的 JavaServer Faces (JSF) 應(yīng)用程序。本文首先解釋 Acegi 針對(duì)此目標(biāo)提供的特性,并澄清一些關(guān)于使用 Acegi和JSF 的常見誤解。然后提供一個(gè)簡單的 web.xml 文件,可以用來部署 Acegi,從而保護(hù) JSF應(yīng)用程序。然后深入探討 Acegi和JSF 組件,了解在部署 web.xml 文件和用戶訪問 JSF應(yīng)用程序時(shí)所發(fā)生的事件。本文最后提供了一個(gè)由 Acegi 保護(hù)的示例 JSF應(yīng)用程序。

創(chuàng)新互聯(lián)從2013年創(chuàng)立,先為大余等服務(wù)建站,大余等地企業(yè),進(jìn)行企業(yè)商務(wù)咨詢服務(wù)。為大余企業(yè)網(wǎng)站制作PC+手機(jī)+微官網(wǎng)三網(wǎng)同步一站式服務(wù)解決您的所有建站問題。
無需編寫 Java 代碼即可添加安全性
回顧一下本系列的第一個(gè)示例 Acegi 應(yīng)用程序(請(qǐng)參閱 第 1 部分 中的 “一個(gè)簡單 Acegi 應(yīng)用程序” 一節(jié))。該應(yīng)用程序使用 Acegi 提供了以下安全特性:
◆當(dāng)一個(gè)未經(jīng)驗(yàn)證的用戶試圖訪問受保護(hù)的資源時(shí),提供一個(gè)登錄頁面。
◆將授權(quán)用戶直接重定向到所需的受保護(hù)資源。
◆如果用戶未被授權(quán)訪問受保護(hù)資源,提供一個(gè)訪問拒絕頁面。
回想一下,您無需編寫任何 Java 代碼就能獲得這些特性。只需要對(duì) Acegi 進(jìn)行配置。同樣,在 JSF應(yīng)用程序中,無需編寫任何 Java 代碼,也應(yīng)該能夠從 Acegi 實(shí)現(xiàn)相同的特性。
澄清誤解
其他一些作者似乎認(rèn)為將 Acegi 與 JSF 集成需要 JSF應(yīng)用程序提供登錄頁面(參見 參考資料)。這種觀點(diǎn)并不正確。在需要時(shí)提供登錄頁面,這是 Acegi 的職責(zé)。確保登錄頁面在安全會(huì)話期間只出現(xiàn)一次,這也是 Acegi 的職責(zé)。然后,經(jīng)過身份驗(yàn)證和授權(quán)的用戶可以訪問一個(gè)受保護(hù)資源,無需重復(fù)執(zhí)行登錄過程。
如果使用 JSF 提供登錄頁面,將會(huì)發(fā)生兩個(gè)主要的問題:
◆當(dāng)需要時(shí),沒有利用 Acegi 的功能提供登錄頁面。必須編寫 Java 代碼實(shí)現(xiàn)所有邏輯來提供登錄頁面。
◆至少需要編寫一些 Java 代碼將用戶憑證(用戶名和密碼)從 JSF 的登錄頁面移交到 Acegi。
Acegi 的目的是避免編寫 Java 安全代碼。如果使用 JSF 提供登錄頁面,則沒有實(shí)現(xiàn)這一用途,并且會(huì)引發(fā)一系列其他 JSF-Acegi 集成問題,所有這些問題都源于 “Acegi 是用來提供可配置安全性” 這一事實(shí)。如果試圖使用 JSF 來完成 Acegi 的工作,將會(huì)遇到麻煩。
本文余下部分將解釋并演示獨(dú)立于 Acegi 的 JSF應(yīng)用程序開發(fā),并在稍后配置 Acegi 以保護(hù) JSF應(yīng)用程序 — 無需編寫任何 Java 代碼。首先看一下 web.xml 文件,可以部署該文件保護(hù) JSF應(yīng)用程序。
部署 Acegi 保護(hù) JSF應(yīng)用程序
清單 1 展示了一個(gè) web.xml 文件(通常稱為部署描述符),可以使用這個(gè)文件部署 Acegi,從而保護(hù)運(yùn)行在 servlet 容器(比如 Apache Tomcat)中的 JSF應(yīng)用程序:
清單 1. 用于部署 Acegi 和 servlet 容器中的 JSF 的 web.xml 文件
- version="1.0"?>
- Web Application 2.3//EN http://java.sun.com/dtd/web-app_2_3.dtd">
contextConfigLocation /WEB-INF/acegi-config.xml javax.faces.STATE_SAVING_METHOD server javax.faces.CONFIG_FILES /WEB-INF/faces-config.xml - org.springframework.web.context.ContextLoaderListener
- com.sun.faces.config.ConfigureListener
Faces Servlet javax.faces.webapp.FacesServlet 1 Faces Servlet *.faces Acegi Filter Chain Proxy - org.acegisecurity.util.FilterToBeanProxy
targetClass - org.acegisecurity.util.FilterChainProxy
Acegi Filter Chain Proxy /*
注意,清單 1 包含以下標(biāo)記:
◆3 個(gè)
◆2 個(gè)
◆1 個(gè)
◆1 個(gè)
◆1 個(gè)
◆1 個(gè)
閱讀該文件,了解每個(gè)標(biāo)記在 JSF-Acegi 應(yīng)用程序中的用途。
向 Acegi和JSF 提供上下文參數(shù)
清單 1 中的每個(gè) 標(biāo)記定義一個(gè)參數(shù),供 Acegi 或 JSF 在啟動(dòng)或執(zhí)行期間使用。第一個(gè)參數(shù) — contextConfigLocation — 定義 Acegi 的 XML 配置文件的位置。
JSF 需要 javax.faces.STATE_SAVING_METHOD 和 javax.faces.CONFIG_FILES 參數(shù)。javax.faces.STATE_SAVING_METHOD 參數(shù)指定希望在客戶機(jī)還是服務(wù)器上存儲(chǔ) JSF 頁面-視圖狀態(tài)。Sun 的參考實(shí)現(xiàn)的默認(rèn)行為是將 JSF 視圖存儲(chǔ)在服務(wù)器上。
javax.faces.CONFIG_FILES 參數(shù)指定 JSF 需要的配置文件的位置。JSF 配置文件的詳細(xì)信息不屬于本文討論的范圍(參見 參考資料,獲取涉及該主題的資源鏈接)。
為 Acegi和JSF 配置偵聽器
現(xiàn)在看一下 清單 1 中的 2 個(gè) 標(biāo)記。 標(biāo)記定義偵聽器類,偵聽器類偵聽并處理 JSP 或 servlet 應(yīng)用程序啟動(dòng)和執(zhí)行期間發(fā)生的事件。例如:
◆啟動(dòng) JSP 或 servlet 應(yīng)用程序時(shí)servlet容器創(chuàng)建一個(gè)新的 servlet 上下文。每當(dāng) JSP 或 servlet 應(yīng)用程序啟動(dòng)時(shí),就會(huì)觸發(fā)此事件。
◆servlet 容器創(chuàng)建一個(gè)新的 servlet 請(qǐng)求對(duì)象。每當(dāng)容器從客戶機(jī)收到一個(gè) HTTP 請(qǐng)求時(shí),此事件就會(huì)發(fā)生。
◆建立一個(gè)新的 HTTP 會(huì)話。當(dāng)請(qǐng)求客戶機(jī)建立一個(gè)與 servlet 容器的會(huì)話時(shí),此事件就會(huì)發(fā)生。
◆一個(gè)新屬性被添加到 servlet 上下文、servlet 請(qǐng)求和 HTTP 會(huì)話對(duì)象。
◆servlet 上下文、servlet 請(qǐng)求或 HTTP 會(huì)話對(duì)象的一個(gè)現(xiàn)有屬性被修改或刪除。
標(biāo)記就像一種可擴(kuò)展性機(jī)制,允許在 servlet 容器內(nèi)部運(yùn)行的應(yīng)用程序協(xié)同某些事件進(jìn)行處理。servlet 規(guī)范定義了偵聽器類為處理事件而實(shí)現(xiàn)的一些接口。
例如,Spring Framework 實(shí)現(xiàn)一個(gè) javax.servlet.ServletContextListener servlet 接口。實(shí)現(xiàn)此接口的 spring 類是 org.springframework.web.context.ContextLoaderListener。注意,這是 清單 1 的第一個(gè) 標(biāo)記中的偵聽器類。
類似地,JSF 實(shí)現(xiàn)一個(gè) com.sun.faces.config.ConfigureListener 類,該類實(shí)現(xiàn)一些事件-偵聽接口??梢栽?清單 1 的第二個(gè) 標(biāo)記中找到 ConfigureListener 類。
本文稍后將解釋不同的事件-偵聽器接口,以及 Acegi和JSF 事件-偵聽器類內(nèi)部執(zhí)行的處理(請(qǐng)參閱 “啟動(dòng) JSF-Acegi 應(yīng)用程序” 和 “處理對(duì)受 Acegi 保護(hù)的 JSF 頁面的請(qǐng)求”)。
配置和映射 servlet 過濾器
現(xiàn)在看一下 清單 1 中的 標(biāo)記。在請(qǐng)求的 servlet 處理傳入的請(qǐng)求之前,servlet 應(yīng)用程序使用過濾器對(duì)其進(jìn)行預(yù)處理。在請(qǐng)求執(zhí)行之前,Acegi 使用 servlet 過濾器對(duì)用戶進(jìn)行身份驗(yàn)證。
請(qǐng)注意 清單 1 中的 標(biāo)記,它的 子標(biāo)記指定一個(gè) org.acegisecurity.util.FilterToBeanProxy 類。FilterToBeanProxy 類是 Acegi 的一部分。此類實(shí)現(xiàn)一個(gè) javax.servlet.Filter 接口,該接口是 servlet 應(yīng)用程序的一部分。javax.servlet.Filter 接口有一個(gè) doFilter() 方法,servlet 容器在收到請(qǐng)求時(shí)調(diào)用該方法。
還需注意,清單 1 的 標(biāo)記有另一個(gè)子標(biāo)記 。 標(biāo)記指定實(shí)例化 FilterToBeanProxy 類所需的參數(shù)??梢詮?清單 1 中看出,F(xiàn)ilterToBeanProxy 類只需要一個(gè)參數(shù),該參數(shù)是 FilterChainProxy 類的一個(gè)對(duì)象。FilterChainProxy 類表示 第 1 部分 1 中討論的整個(gè) Acegi 過濾器鏈(請(qǐng)參閱 “安全過濾器” 小節(jié))。FilterToBeanProxy 類的 doFilter() 方法使用 FilterChainProxy 類執(zhí)行 Acegi 的安全過濾器鏈。
清單 1 中的 標(biāo)記指定調(diào)用 Acegi 的 FilterToBeanProxy 的請(qǐng)求 URL。我已經(jīng)將所有的 JSF 頁面映射到 Acegi 的 FilterToBeanProxy。這意味著只要用戶試圖訪問 JSF 頁面,F(xiàn)ilterChainProxy doFilter() 方法就會(huì)自動(dòng)獲得控制權(quán)。
配置 JSF servlet
web.xml 文件中的 標(biāo)記指定希望從特定 URl 調(diào)用的 servlet(在本例中是一個(gè) JSF servlet)。 標(biāo)記定義該 URL。幾乎所有的 JSP 或 servlet 應(yīng)用程序都包含這兩個(gè)標(biāo)記,所以無需再作討論(參見 參考資料,獲取討論 servlet 編程的資源鏈接)。
現(xiàn)在,您已經(jīng)看到,web.xml 文件要部署 Acegi 以保護(hù) JSF 應(yīng)用程序所需的所有標(biāo)記。您已經(jīng)了解了偵聽器、過濾器和 servlet 如何相互協(xié)作。從這里的討論中可以看出,如果在 servlet 容器中部署 清單 1 中的 web.xml 文件,Acegi和JSF 都試圖在兩種情形下進(jìn)行一些處理:
◆當(dāng)啟動(dòng)應(yīng)用程序時(shí)
◆當(dāng)應(yīng)用程序收到對(duì) JSF 頁面的請(qǐng)求時(shí)
網(wǎng)頁名稱:使用Acegi保護(hù)JSF應(yīng)用程序
文章分享:http://m.fisionsoft.com.cn/article/codjsoo.html


咨詢
建站咨詢
