在WebSphere Application Server V7上通過JAX-WS 實現消息級安全性: 集成JEE授權
在第 1 部分中,您了解了如何在 WebSphere Application Server V7 上使用 JAX-WS 提供消息級安全性,包括如何使用策略集對消息進行加密和簽名,以及如何使用 UsernameToken 概要文件進行身份驗證。在第 2 部分中,您將了解如何使用 SOAP 頭部中傳遞的 UsernameToken 作為 JEE principal 在服務提供者中提供編程式的授權。
簡介
Web Services Security (WS-Security) 是一種描述如何對 Web 服務實現消息級安全性的 OASIS 標准。具體來講,WS-Security 描述如何實現機密性(例如加密)、完整性(例如數字簽名)並在 SOAP 消息中傳播用於身份驗證的安全令牌(token)(例如用戶名和密碼)。然而,WS-Security 允許在 SOAP 消息中同時發送多個安全令牌,並且典型的 Java™ Platform, Enterprise Edition (JEE) Web 服務提供者實現根據來自其中一個安全令牌的 principal(身份)執行授權檢查。在本文中,我們將描述如何配置 WebSphere 來選擇 SOAP 消息的安全令牌作為 JEE principal,後者可用於作出授權決策。
注意,JEE 安全模型對 Web 容器和 EJB 容器支持聲明式安全授權以及編程安全性。使用 Web 容器編程 API(比如 getUserPrincipal())和使用 EJB 容器編程 API(比如 getCallerPrincipal())之間存在著細微的差別。然而,本文的內容是討論如何配置 Web 服務以將 SOAP 頭部中的其中一個令牌指定為 JEE principal。一旦對這個 principal 進行了設置,您就可以像往常那樣使用 JEE 安全模型和 WebSphere Base Security API。
您可以通過聲明或編程的方式對 servlet 和 EJB 使用 JEE 安全模型以實現授權。然而,考慮到本文的意圖,我們將演示一個基於 servlet 的 Web 服務,它將使用編程式 JEE API 獲得 principal。您可以對樣例進行擴展以使用 JEE 編程式 API 來對基於 servlet 的基礎 Web 服務提供者執行編程式授權檢查,或者為 EJB 配置基於角色的 JEE 消息級安全性。針對 web 容器以及 EJB 容器的 JEE 聲明式和編程安全性已在其他資料中加以介紹,因此不會作為本文的重點。。我們的目標是演示如何支持消息級安全令牌的集成,以在 WebSphere Application Server 上結合使用 JEE 授權框架。
創建一個 JAX-WS 服務提供者
使用 Rational Application Developer (Application Developer) V7.5.2,創建一個新的動態 Web 項目,項目名為 HelloWorldProject。
接下來,使用 HelloWorldProvider 作為名稱創建一個新的 Java 類,並將清單 1 的內容復制到這個新類。
清單 1. HelloWorldProvider.java
package com.ibm.dwexample;
import javax.annotation.Resource;
import javax.jws.WebService;
import javax.xml.ws.WebServiceContext;
@WebService public class
HelloWorldProvider { @Resource WebServiceContext wsCtx;
public
String sayHello(String msg) { System.out.println("[provider]
received " + msg); System.out.println("[provider] user = " +
wsCtx.getUserPrincipal()); return "Hello " + msg; } }
HelloWorldProvider 代碼中比較有趣的部分是 @Resource WebServiceContext。這行代碼允許 JAX-WS 運行時注入 Web 服務上下文並使您能夠從該上下文訪問 JEE principal。然而,為了使代碼在 Application Server 中實際返回正確的 principal,您必須在服務提供者綁定中配置 Caller;否則,結果可能會是 “Principal: /UNAUTHENTICATED*quot;”。
右鍵單擊 HelloWorldProject 並選擇 Run As => Run on Server。確保選中 Publishing settings for WebSphere Application Server 區段中的 Run server with resources on Server。
選擇 WebSphere Application Server v7.0 服務器概要文件並單擊 Finish。
為服務提供者提供安全性
策略集和策略集綁定已在 第 1 部分 中介紹,因此我們將直接創建一個策略集,使用它為 Web 服務指定一個 UsernameToken 作為身份驗證令牌。當創建好策略集並將其附加到服務提供者後,您將創建一個服務器端綁定,在其中指定將用作主安全令牌的令牌 —— 即 JEE principal。這樣做的原因是因為 WS-Security 規范允許為身份驗證附加多個令牌,這樣就需要更多的元數據來識別哪一個是主安全令牌。在 WebSphere 中,這些元數據稱作 Caller 並被配置為 WS-Security 綁定的一部分,本文將展示這一點。
我們將使用 Application Server 管理控制台創建策略集並將其附加到您的服務提供者,然後創建一個綁定,服務提供者將通過該綁定遵守策略。
從 Application Developer 中,右鍵單擊 Servers 視圖中的 Application Server V7 運行時並選擇 Administration => Run administrative console,如圖 1 所示。
圖 1. 啟動管理控制台
從管理控制台中,選擇 Services => Policy sets => Application policy sets,如圖 2 所示。
圖 2. 應用程序策略集
單擊 New 創建一個新策略集。
指定 My UNT 作為新策略集的名稱並在 Description 字段中添加描述,然後單擊 Apply。
接下來單擊 Policies 區段中的 Add 並選擇 WS-Security 作為將要添加的策略,如圖 3 所示。
圖 3. 新策略集
將策略添加到您的新策略集後,只需單擊 WS-Security 即可配置它。
單擊 Main policy;您應當看到如圖 4 所示的畫面。
圖 4. 配置 WS-Security 策略
默認情況下,WS-Security 策略在創建時使用了消息級別的保護,如 第 1 部分 所述。然而,為了使事情簡單一些,本文將禁用消息級保護,方法是取消選中 Message level protection,然後單擊 Apply。
由於我們的策略需要一個 UsernameToken 來提取 JEE principal,因此您需要將 UsernameToken 添加到 WS-Security 策略,執行以下操作:
在 Main Policy 中,單擊 Policy Details 區段中的 Request token policies。
單擊 Add Token Type 並選擇 UserName,如圖 5 所示。
圖 5. 將 UsernameToken 添加到 Request Token 策略
指定 MyUsernameToken 作為 Username token,選擇 WS-Security 1.0 作為 WS-Security 版本,如圖 6 所示,然後單擊 Apply。
圖 6. 指定 UsernameToken
單擊 Save,將更改直接保存到主配置。您應當會看到如圖 7 所示的畫面。
圖 7. 已配置的 UsernameToken 策略
現在策略集已經創建,您需要將其附加到服務提供者。從管理控制台中,選擇 Services => Service providers 來獲得 JAX-WS 服務提供者的列表,然後選擇 HelloWorldProviderService,如圖 8 所示。
圖 8. JAX-WS 服務提供者
選中 HelloWorldProviderService,單擊 Attach Policy Set,然後選擇您的策略集(例如 My UNT)。
My UNT 策略集現在被附加到 HelloWorldProviderService,如圖 9 所示。
圖 9. 將策略集附加到服務提供者
策略集指定了 “內容”,而綁定則指定了 “方式”。因此,您需要為這個服務提供者配置策略集綁定。為此,執行以下操作:
選中 HelloWorldProviderService,然後單擊 Assign Binding 並選擇 New Application Specific Binding。
指定 ServerUNTBinding 作為 Bindings configuration name,然後單擊 Add 並選擇 WS-Security 以創建特定於應用程序的綁定,如圖 10 所示。
圖 10. 策略集綁定配置
注意,綁定分配將檢查策略集以確定需要對哪些策略進行配置。在本文中,策略集包含了一個 WS-Security 策略,這也是該策略被包含到 Add 下拉菜單中的原因。
由於您添加到服務提供者中的 WS-Security 策略集包含 UsernameToken 作為必需的請求者令牌,您需要執行以下步驟以在綁定中為該策略指定 “方式”:
通過單擊 Authentication and protection 顯示 ServerUNTBinding 的細節
導航到身份驗證令牌部分並單擊 request:MyUsernameToken。您應當會看到如圖 11 所示的畫面。
圖 11. UsernameToken 身份
為該場景保留默認值,然後單擊 OK。
根據 WS-Security 規范,您現在已經將在 SOAP 頭部傳遞的 UsernameToken 指定為供服務提供者使用的身份驗證令牌。然而,注意 WS-Security 規范允許在請求消息中傳遞多個令牌,因此您將需要向 WebSphere 指定使用哪些令牌創建 WebSphere 憑證(即 JEE 對象),這樣特定令牌的身份就可以用於 JEE 安全性,比如基於角色的授權檢查。在 WebSphere 中,這是通過按如下方式配置調用方實現的:
從 Callers 對話框中單擊 Caller(參見 圖 10),然後單擊 New 。
輸入 Caller 作為 Name。
為 Caller identity local part 輸入 http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-username-token-profile-1.0#UsernameToken,如圖 12 所示。注意此 URL 是 圖 11 所示的身份驗證令牌的 Local part 的值。
圖 12. 指定調用方
單擊 OK 接受該調用方,然後單擊 Save,將綁定保存到主配置中。
使用安全服務
要確保服務使用者遵循服務提供者的策略,最簡單的方法也許就是使用相同的策略集。具體操作就是從 Application Server 管理控制台導出服務提供者策略集,然後將其導入到 Application Developer。
要導出策略集,執行下面的步驟:
從管理控制台中,選擇 Services => Policy sets => Application policy sets。
選中 My UNT 策略集,然後單擊 Export =>,如圖 13 所示。
圖 13. 導出策略集
單擊 MyUNT.zip 並將文件保存到本地驅動中的某個位置;例如,c:\temp。
單擊 OK 保存文件。
要將策略集導入到 Application Developer,執行下面的操作:
從 Application Developer 主菜單中,選擇 File => Import => Web services => WebSphere Policy Sets ,然後單擊 Next。
單擊 Browse 並選擇您前面導出的 MyUNT.zip 文件。向導將讀取 zip 文件並顯示其中包含的策略集,如圖 14 所示。
圖 14. 導入策略集
確保選中 MyUNT 並單擊 Finish。
現在您已經將策略集導入到 Application Developer 中,您需要創建一個服務使用者客戶機,以將策略集附加到其上:
在 Application Developer 中,選擇 File => New => Other => Java => Java Project 創建一個新的 Java 項目來保存使用者。
指定 HelloWorldConsumer 作為 Client project name,然後單擊 Finish。如果出現要您切換到 Java 透視圖的提示,單擊 No。
現在選擇服務提供者,Application Developer 將從其中生成一個客戶機代理並選擇 Generate => Client,如圖 15 所示。
圖 15. 生成 JAX-WS 客戶機代理
從 Web Service Client 向導中,確保選中 IBM WebSphere JAX-WS 作為 Web 服務運行時,然後單擊 Client project:。
指定 HelloWorldConsumer 作為 Client project name,然後選擇 HelloWorldConsumer 作為客戶機項目並單擊 OK。
接受默認值並單擊 Finish。Application Developer 將生成 JAX-WS 客戶機代理類和支持類。
右鍵單擊生成的 HelloWorldConsumer 項目,並選擇 New => Class。
指定 com.ibm.dwexample 作為包名並指定 ClientTest 作為 Java 類名,然後單擊 Finish。
使用清單 2 中的代碼替換生成的客戶機代碼並保存文件。
清單 2. ClientTest.java
package com.ibm.dwexample; import
com.ibm.dwexample.HelloWorldProvider; import
com.ibm.dwexample.HelloWorldProviderService;
public class
ClientTest { public static void main(String[] args) {
HelloWorldProviderService srv
= new HelloWorldProviderService();
HelloWorldProvider port
= srv.getHelloWorldProviderPort();
String
resp = port.sayHello("World");
System.out.println("[response] " +
resp); } }
現在,您已經創建了 JAX-WS 使用者,您需要將導入的策略集附加到使用者,然後生成客戶端策略集綁定。為此,執行下面的步驟:
導航到 HelloWorldConsumer 項目並選擇 Services => Clients => {http://dwexample.ibm.com/}HelloWorldProviderService => Manage Policy Set Attachment,如圖 16 所示。
圖 16. 管理策略集附件
單擊 Next,然後單擊 Add。
檢查服務名是否被設置為 {http://dwexample.ibm.com/}HelloWorldProviderService,然後選擇 Policy Set => MyUNT。
輸入 ClientUNTBinding 作為 Binding name,然後單擊 OK,如圖 17 所示。
圖 17. 將策略集附加到使用者
您現在已經將 Application Server 中創建的策略集附加到了 JAX-WS 使用者。您還為客戶端綁定指定了名稱(ClientUNTBinding)。最後的步驟是對綁定進行配置:
在綁定配置中選擇 WSSecurity 策略類型並單擊 Configure。
選擇 com.ibm.websphere.wssecurity.callbackhandler.UNTGUIPromptCallbackHandler 作為回調處理程序,如圖 18 所示。
圖 18. JAX-WS 使用者綁定配置
單擊 OK,然後單擊 Finish。
您現在已經指定了一個策略集以及與服務使用者對應的策略集綁定。您現在可以測試代碼以確保它能夠實際起作用。
運行樣例應用程序
由於本文使用的代碼演示的是使用 UsernameToken(即 SOAP 頭部中的用戶名和密碼)作為身份驗證令牌來實現 Application Server 的身份驗證,因此您需要確保在執行測試前對 Application Server 啟用了安全性。為此,從 Application Server 管理控制台中,確保選中 Enable administrative security 和 Enable application security。如果沒有啟用安全性,您將需要重啟 Application Server 來使安全更改生效。
要測試應用程序,執行下面的步驟:
從 Application Developer 中,右鍵單擊 ClientTest.java 並選擇 Run As => Run Configurations。
如圖 19 所示,由於使用者需要使用 Java Authentication 和 Authorization Service (JAAS) 來傳遞 Username 憑證,為 VM arguments 指定下面的內容,以指向 JAAS 登錄配置文件:
-Djava.security.auth.login.config=
"C:\ProgramFiles\IBM\SDP\
runtimes\base_v7\profiles\was70profile1\
properties
\wsjaas_client.conf"
圖 19. 為 ClientTest 設置 JAAS 參數
單擊 Run。您應當看到如圖 20 所示的客戶機結果以及如圖 21 所示的服務器端結果。
圖 20. JAX-WS 使用者結果
圖 21. JAX-WS 提供者結果
結束語
除了身份驗證、完整性和機密性以外,許多 Web 服務都需要實現授權。在本文中,您了解了如何配置 WebSphere Application Server V7 來選擇一個安全令牌,它將作為 JEE 安全 principal 包含到 SOAP 頭部。由於這種配置是在綁定級別對策略集完成的,每個 Web 服務端口可以具有不同的配置(如果需要的話),或者可以像本文一樣,在服務級別指定配置。設置好配置後,開發人員就可以開始使用 JEE 授權 API,從而做出授權決策。對於基於 EJB 的 Web 服務,通過使用注釋或部署描述符,經過配置的 JEE principal 就可以用於 JEE 的基於角色的授權檢查。
本文配套源碼