Apache shiro介绍
原文鏈接Application Security With Apache Shiro(翻譯)
前面自己自己配合谷歌翻譯,后面大部分谷歌翻譯。
當你嘗試保護你的程序時候你會被困擾嗎?你會覺得現(xiàn)有的java安全方案難以使用并且將來還會困惑你?這篇文章介紹Apach shiro,一個簡單而又強大的保護程序安全的安全框架。它解釋了Apache的項目目標。架構原理和如何使用shiro保護你的程序。
什么是shiro?
shiro是強大易用的java安全框架,提供身份認證,授權,加密和會話管理(authentication, authorization, cryptography, and session management )并且能夠用于任何命令行應用程序,移動應用到最大的web和企業(yè)應用。
shiro提供安全api來執(zhí)行一下方面(作者喜歡把它稱作程序安全的四個基石)
- 身份認證(Authentication)-證明用戶身份,通常叫做登陸(login)。
- 授權(Authorization)-訪問控制
- 加密(Cryptography)-保護或隱藏數(shù)據(jù)
- 會話管理(session management)每個用戶時間敏感狀態(tài)
shiro也支持一些輔助功能,例如 web程序安全,單元測試, 多線程支持。但是這些都是為了加強上述四個功能。
shiro咋被產(chǎn)生了呢(Why was Apache Shiro created?)?
對于一個真正為其存在提供良好案例的框架,因此你有理由使用它,他應該滿足其他替代方案無法滿足的需求,我們應該去看看shiro被創(chuàng)建時的歷史和替代方案來理解它。
在2008進入apache之前,shiro就已經(jīng)5歲了,以前被稱為JSecurity project,在2003上半年完成,在2003沒有太多的通用安全方案被java開發(fā)者使用。-我們堅持使用java身份驗證和授權管理。盡管有JAAS,但是缺點太多了-盡管他的身份驗證還能將就忍忍用著,但是授權方面真的是難用的一批并且困擾著我們,況且JAAS是嚴重依賴虛擬機級別的安全問題。例如,決定允許一個類在虛擬機中載入,作為一個應用開發(fā)者,我更關心的是最終用戶能在程序上做什么,而不是我的代碼能在JVM虛擬機中做什么。
由于當時我正在處理應用程序,我也需要一個干凈的,與容器無關的會話機制。在當時的項目中唯一的會話選擇就是HttpSessions,這需要一個web容器,或者需要EJB 2.1 stateful Beans,我需要一些和容器分離的東西,可以在我選擇的任何環(huán)境中使用。
最后,存在加密問題,有時我們都需要保證數(shù)據(jù)傳輸?shù)陌踩?。但除非你是加密專?#xff0c;否則java密碼體系結構很難理解。API充滿了異常并且使用起來很笨重。我希望一個更清潔的開箱即用的解決方案,可以根據(jù)需要輕松加密和解密數(shù)據(jù)。
所有在2003年早期的安全領域,你可以快速明白這兒沒有任何東西能夠滿足指標。有凝聚力的框架,因為這個,JSecurity,還有后來的Apache shiro,誕生了。
為什么你今天會使用Apache shiro?
自從2003框架領域已經(jīng)發(fā)生了巨大的變化,所以應該有令人信服的理由讓人在今天還使用shiro。實際上原因很多:
- 容易使用-易于使用應該是項目的最終目標。應用安全可能是個極大的困擾和阻撓并且被認為是 ‘必不可少的惡魔’。如果你能使他簡單并且新手程序員能夠開始使用它,那么將不會有任何煩惱。
- 全面-shiro生稱沒有其他安全框架像shiro一樣范圍廣泛,因此它可能是您的“一站式服務”來滿足你的安全需求。
- 靈活-shiro能夠在各種應用環(huán)境下工作,雖然它適合用于web,EJB,和IoC環(huán)境,但它不需要它們。shiro也沒用要求強制任何規(guī)范,甚至依賴都很少。
- web能力shiro有良好的web應用支持性。允許你根據(jù)URL或者web協(xié)議(例如REST)創(chuàng)建靈活的安全策略。同時還提供一組jsp庫來控制輸出。
- 可植入性shiro簡潔的API和設計規(guī)范讓它很容易整合其他框架和應用,你可以很容易看到shiro整合Spring,Grails,Wicket,Tapestry,Mule,Apache Camel,Vaadin,和許多其他。
- 被支持shiro是Apache 軟件基金會的成員。
誰在使用shiro?
Shiro及其前身JSecurity在大小公司和企業(yè)中已經(jīng)被使用多年,由于變成了一個apache的頂級項目,網(wǎng)站流量和采用率顯著上漲,許多開源社區(qū)也在使用shiro,例如Spring, Grails, Wicket, Tapestry, Tynamo, Mule, and Vaadin,僅僅是名單的小部分。
像Katasoft,Sonatype,MuleSoft這樣的主要社交網(wǎng)絡之一的商業(yè)公司以及一些紐約商業(yè)銀行使用Shiro來保護他們的商業(yè)軟件和網(wǎng)站。
核心部分:Subject, SecurityManager, and Realms
Subject
當你保護你的程序時,你最可能會問你的問題是:“當前的使用者是誰”?或者“當前的使用著是否允許執(zhí)行 X”?當我們寫代碼或者寫用戶接口時我們很容易這樣問自己,應用程序通常基于用戶的故事,并且你希望基于每個用戶表示(和保護)功能。所以,你就會自然而然的想到基于當前用戶在應用程序中的安全性,shiro的API的Subject概念從根本上代表這種思維。
subject代表“當前操作的對象”,他不是‘User’因為user通常代表一個人。你可以把它當成shiro的user對象。
listing 1,獲得Subject對象。
import org.apache.shiro.subject.Subject; import org.apache.shiro.SecurityUtils; ... Subject currentUser = SecurityUtils.getSubject();一旦你獲得Subject對象,你立馬能夠為當前user在shiro中做90%你想做的事情,比如login,logout,獲取session,執(zhí)行授權檢查等等,但是在這之后,這里的關鍵的是Shiro的API在很大程度是直觀的,因為它反應了開發(fā)人員在“per-user”安全控制中的思考。當然在代碼的任何地方獲取Subject也是容易的,允許在需要安全的地方進行任何安全操作。
SecurityManager
Subject的幕后對應物應該是SecurityManager。當Subject代表當前user的安全操作時SecurityManager管理所有user的安全操作,他是shiro的核心架構,充當一種“傘形”對象,它引用了許多形成對象圖的內部嵌套安全組件。 但是,一旦配置了SecurityManager及其內部對象圖,通常就會將其保留,應用程序開發(fā)人員幾乎將所有時間花在Subject API上。
所以你將如何創(chuàng)建一個SecurityManager?當然,它基于應用的環(huán)境,比如 一個web程序通常指定一個shiro servlet filter在web.xml,這將建立SecurityManager實例。
每個應用程序幾乎總是有一個SecurityManager實例,他本質上是一個應用程序單例(盡管它不需要靜態(tài)單例),與shiro中所有事情幾乎一致,默認的SecurityManager實現(xiàn)是POJO,可以使用任何兼容POJO的配置機制進行配置 - 普通Java代碼,Spring XML,YAML,.properties和.ini文件等?;旧先魏文軌驅嵗惖臇|西 并且可以使用調用JavaBeans兼容的方法。
最后,Shiro通過基于文本的INI配置提供默認的“公分母”解決方案。 INI易于閱讀,易于使用,并且需要很少的依賴性。 您還將看到,通過對對象圖導航的簡單理解,可以有效地使用INI來配置像SecurityManager這樣的簡單對象圖。 請注意,Shiro還支持Spring XML配置和其他替代方案,但我們將在此處介紹INI。
Listing 2. Configuring Shiro with INI
[main] cm = org.apache.shiro.authc.credential.HashedCredentialsMatcher cm.hashAlgorithm = SHA-512 cm.hashIterations = 1024 # Base64 encoding (less text): cm.storedCredentialsHexEncoded = falseiniRealm.credentialsMatcher = $cm
[users] jdoe = TWFuIGlzIGRpc3Rpbmd1aXNoZWQsIG5vdCBvbmx5IGJpcyByZWFzb2 asmith = IHNpbmd1bGFyIHBhc3Npb24gZnJvbSBvdGhlciBhbXNoZWQsIG5vdCB在list2中,我們將看到用于配置SecurityManager實例的示例INI配置。 有兩個INI部分:[main]和[users]。
[main]部分用于配置SecurityManager對象和/或SecurityManager使用的任何對象(如Realms)。 在此示例中,我們看到正在配置兩個對象:
您可以在[users]部分指定用戶帳戶的靜態(tài)列表 - 方便簡單應用程序或測試時。
出于本簡介的目的,理解每個部分的復雜性并不重要,而是要看INI配置是配置Shiro的一種簡單方法。 有關INI配置的更多詳細信息,請參閱Shiro的文檔。
Listing 3. Loading shiro.ini Configuration File
import org.apache.shiro.SecurityUtils; import org.apache.shiro.config.IniSecurityManagerFactory; import org.apache.shiro.mgt.SecurityManager; import org.apache.shiro.util.Factory; --- --- ...//1. Load the INI configuration Factory factory = new IniSecurityManagerFactory("classpath:shiro.ini");//2. Create the SecurityManager SecurityManager securityManager = factory.getInstance();//3. Make it accessible SecurityUtils.setSecurityManager(securityManager);在list3,我們看到一個簡單例子的三個步驟。
Realms
Shiro的第三個也是最后一個核心概念是一個領域。 Realm充當Shiro與應用程序安全數(shù)據(jù)之間的“橋接”或“連接器”。 也就是說,當實際與安全相關的數(shù)據(jù)(如用戶帳戶)進行交互以執(zhí)行身份驗證(登錄)和授權(訪問控制)時,Shiro會從為應用程序配置的一個或多個領域中查找許多這些內容。
從這個意義上講,Realm本質上是一個特定于安全性的DAO:它封裝了數(shù)據(jù)源的連接細節(jié),并根據(jù)需要使相關數(shù)據(jù)可用于Shiro。 配置Shiro時,必須至少指定一個Realm用于身份驗證和/或授權。 可以配置多個Realm,但至少需要一個。
Shiro提供了開箱即用的Realms,可以連接到許多安全數(shù)據(jù)源(也稱為目錄),如LDAP,關系數(shù)據(jù)庫(JDBC),文本配置源(如INI和屬性文件等)。 如果默認域不符合您的需要,您可以插入自己的Realm實現(xiàn)來表示自定義數(shù)據(jù)源。 下面的list4是配置Shiro(通過INI)將LDAP目錄用作應用程序領域之一的示例。
Listing 4. Example realm configuration snippet to connect to LDAP user data store
[main] ldapRealm = org.apache.shiro.realm.ldap.JndiLdapRealm ldapRealm.userDnTemplate = uid={0},ou=users,dc=mycompany,dc=com ldapRealm.contextFactory.url = ldap://ldapHost:389 ldapRealm.contextFactory.authenticationMechanism = DIGEST-MD5現(xiàn)在我們已經(jīng)了解了如何設置基本的Shiro環(huán)境,讓我們討論一下,作為開發(fā)人員,您將如何使用該框架。
Authentication
身份驗證是驗證用戶身份的過程。 也就是說,當用戶使用應用程序進行身份驗證時,他們證明他們實際上是他們所說的人。 這有時也被稱為“登錄”。 這通常是一個三步過程。
每個人都熟悉的這個過程的一個常見例子是用戶名/密碼組合。 當大多數(shù)用戶登錄軟件應用程序時,他們通常會提供用戶名(主體)和支持密碼(憑證)。 如果存儲在系統(tǒng)中的密碼(或其表示)與用戶指定的密碼匹配,則認為它們已經(jīng)過身份驗證。
Shiro以簡單直觀的方式支持相同的工作流程。 正如我們所說,Shiro有一個以Subject為中心的API - 幾乎所有你在運行時用Shiro做的事都是通過與當前正在執(zhí)行的Subject進行交互來實現(xiàn)的。 因此,要登錄Subject,只需調用其登錄方法,傳遞一個AuthenticationToken實例,該實例表示提交的主體和憑據(jù)(在本例中為用戶名和密碼)。 此示例如下面的list5所示。
Listing 5. Subject Login
//1. Acquire submitted principals and credentials: AuthenticationToken token = new UsernamePasswordToken(username, password); //2. Get the current Subject: Subject currentUser = SecurityUtils.getSubject(); //3. Login: currentUser.login(token);如您所見,Shiro的API很容易反映出常見的工作流程。 您將繼續(xù)將此簡單性視為所有Subject操作的主題。 調用login方法時,SecurityManager將接收AuthenticationToken并將其分派給一個或多個已配置的域,以允許每個域根據(jù)需要執(zhí)行身份驗證檢查。 每個Realm都能夠根據(jù)需要對提交的AuthenticationTokens做出反應。 但是如果登錄嘗試失敗會發(fā)生什么? 如果用戶指定了錯誤的密碼該怎么辦? 您可以通過對Shiro的運行時AuthenticationException作出反應來處理故障,如list6所示。
Listing 6. Handle Failed Login
//3. Login: try {currentUser.login(token); } catch (IncorrectCredentialsException ice) { … } catch (LockedAccountException lae) { … } … catch (AuthenticationException ae) {… }您可以選擇捕獲其中一個AuthenticationException子類并進行具體反應,或者通常處理任何AuthenticationException(例如,向用戶顯示通用的“不正確的用戶名或密碼”消息)。 根據(jù)您的應用要求,您可以選擇。
在成功登錄主題后,它們將被視為已通過身份驗證,通常您允許它們使用您的應用程序。 但僅僅因為用戶證明了他們的身份并不意味著他們可以在您的應用程序中做任何他們想做的事情。 這引出了下一個問題,“我如何控制允許用戶做什么?”決定允許用戶做什么稱為授權。 我們將介紹Shiro如何啟用授權。
Authorization
授權本質上是訪問控制 - 控制用戶可以在應用程序中訪問的內容,例如資源,網(wǎng)頁等。大多數(shù)用戶通過使用角色和權限等概念來執(zhí)行訪問控制。 也就是說,通常允許用戶基于分配給他們的角色和/或許可來做某事或不做某事。 然后,您的應用程序可以根據(jù)對這些角色和權限的檢查來控制公開的功能。 正如您所料,Subject API允許您非常輕松地執(zhí)行角色和權限檢查。 例如,list7中的代碼片段顯示了如何檢查Subject是否已分配了某個角色。
Listing 7. Role Check
if ( subject.hasRole(“administrator”) ) {//show the ‘Create User’ button } else {//grey-out the button? }如您所見,您的應用程序可以根據(jù)訪問控制檢查啟用或禁用功能。
權限檢查是執(zhí)行授權的另一種方式。 檢查上面示例中的角色會遇到一個重大缺陷:您無法在運行時添加或刪除角色。 您的代碼使用角色名稱進行了硬編碼,因此如果您更改了角色名稱和/或配置,您的代碼就會被破壞! 如果您需要能夠在運行時更改角色的含義,或者根據(jù)需要添加或刪除角色,則必須依賴其他內容。
為此,Shiro支持其權限概念。 權限是一個原始的功能聲明,例如“打開一扇門”,“創(chuàng)建一個博客條目”,“刪除’jsmith’用戶’等。通過擁有反映應用程序原始功能的權限,您只需要更改權限 更改應用程序的功能時檢查。 反過來,您可以在運行時根據(jù)需要為角色或用戶分配權限。
作為一個例子,如下面的list8所示,我們可以重寫之前的角色檢查,而是使用權限檢查。
Listing 8. Permission Check
if ( subject.isPermitted(“user:create”) ) {//show the ‘Create User’ button } else {//grey-out the button? }這樣,任何分配了“user:create”權限的角色或用戶都可以單擊“創(chuàng)建用戶”按鈕,這些角色和分配甚至可以在運行時更改,為您提供非常靈活的安全模型。
“user:create”字符串是遵循某些解析約定的權限字符串的示例。 Shiro通過WildcardPermission開箱即用,支持這種約定。 雖然超出了本介紹文章的范圍,但您會看到WildcardPermission在創(chuàng)建安全策略時可以非常靈活,甚至可以支持實例級訪問控制等內容。
Listing 9. Instance-Level Permission Check
if ( subject.isPermitted(“user:delete:jsmith”) ) {//delete the ‘jsmith’ user } else {//don’t delete ‘jsmith’ }此示例顯示,如果需要,您甚至可以控制對非常細粒度的實例級別的訪問。 如果您愿意,您甚至可以創(chuàng)建自己的權限語法。 有關更多信息,請參閱Shiro權限文檔。 最后,就像身份驗證一樣,上述調用最終會進入SecurityManager,它將咨詢一個或多個Realms以做出訪問控制決策。 這允許Realm根據(jù)需要響應身份驗證和授權操作。
這是對Shiro授權功能的簡要概述。 雖然大多數(shù)安全框架都停止了身份驗證和授權,但Shiro提供了更多功能。 接下來我們將討論Shiro的高級會話管理功能。
Session Management
Apache Shiro在安全框架領域提供了獨特的東西:一致的會話session API,可用于任何應用程序和任何架構層。 也就是說,Shiro為任何應用程序啟用了會話編程范例 - 從小型守護程序獨立應用程序到最大的集群Web應用程序。 這意味著希望使用會話的應用程序開發(fā)人員不再需要使用Servlet或EJB容器,否則就不需要它們。 或者,如果使用這些容器,開發(fā)人員現(xiàn)在可以選擇在任何層中使用統(tǒng)一且一致的會話API,而不是servlet或EJB特定的機制。
但也許Shiro session會話最重要的好處之一就是它們與容器無關。 這具有微妙但極其強大的含義。 例如,讓我們考慮會話群集。 有多少特定于容器的方法來集群會話以進行容錯和故障轉移? Tomcat的做法與Jetty有所不同,它與Websphere等不同。但是通過Shiro會話,您可以獲得與容器無關的群集解決方案。 Shiro的架構允許可插入的Session數(shù)據(jù)存儲,例如企業(yè)緩存,關系數(shù)據(jù)庫,NoSQL系統(tǒng)等。 這意味著您可以配置一次會話群集,無論您的部署環(huán)境如何,它都將以相同的方式工作 - Tomcat,Jetty,JEE Server或獨立應用程序。 無需根據(jù)部署應用程序的方式重新配置應用程序。
Shiro會話的另一個好處是,如果需要,可以跨客戶端技術共享會話數(shù)據(jù)。 例如,如果需要,Swing桌面客戶端可以參與同一個Web應用程序會話 - 如果最終用戶同時使用兩者,則會很有用。 那么如何在任何環(huán)境中訪問主題會話? 有兩種主題方法,如下例所示。
Listing 10. Subject’s Session
Session session = subject.getSession(); Session session = subject.getSession(boolean create);如您所見,這些方法在概念上與HttpServletRequest API相同。 第一種方法將返回Subject的現(xiàn)有Session,或者如果還沒有,它將創(chuàng)建一個新的并返回它。 第二種方法接受一個布爾參數(shù),該參數(shù)確定是否將創(chuàng)建新的Session(如果它尚不存在)。 獲得Subject會話后,您幾乎可以使用它與HttpSession相同。 Shiro團隊認為HttpSession API對Java開發(fā)人員來說最為舒適,因此我們保留了很多感覺。 當然,最大的區(qū)別在于您可以在任何應用程序中使用Shiro Sessions,而不僅僅是Web應用程序。 list11顯示了這種熟悉程度。
Listing 11. Session methods
Session session = subject.getSession(); session.getAttribute(“key”, someValue); Date start = session.getStartTimestamp(); Date timestamp = session.getLastAccessTime(); session.setTimeout(millis);Cryptography
密碼學是隱藏或混淆數(shù)據(jù)的過程,因此窺探眼睛無法理解它。 Shiro在加密方面的目標是簡化并使JDK的加密支持變得可用。
重要的是要注意密碼學一般不是特定于受試者,因此它是Shiro API的一個非特定Subject的區(qū)域。 您可以在任何地方使用Shiro的加密支持,即使沒有使用Subject。 Shiro真正關注其加密支持的兩個領域是加密哈希(也稱為消息摘要)和加密密碼。 讓我們更詳細地看一下這兩個。
Hashing
如果您使用過JDK的MessageDigest類,您很快就會意識到使用它有點麻煩。 它有一個笨拙的靜態(tài)方法基于工廠的API而不是面向對象的API,你被迫捕獲可能永遠不需要捕獲的已檢查異常。 如果您需要十六進制編碼或Base64編碼消息摘要輸出,您可以自己 - 沒有標準的JDK支持。 Shiro使用簡潔直觀的散列API解決了這些問題。
例如,讓我們考慮相對常見的MD5散列文件并確定該散列的十六進制值的情況。 稱為“校驗和”,在提供文件下載時會定期使用 - 用戶可以在下載的文件上執(zhí)行自己的MD5哈希,并聲明其校驗和與下載站點上的校驗和匹配。 如果它們匹配,則用戶可以充分地假設文件在傳輸中未被篡改。
如果沒有Shiro,您可以嘗試這樣做:
Listing 12. JDK’s MessageDigest
try {MessageDigest md = MessageDigest.getInstance("MD5");md.digest(bytes);byte[] hashed = md.digest(); } catch (NoSuchAlgorithmException e) {e.printStackTrace(); }這對于如此簡單和相對常見的事情來說是一項重要的工作。 現(xiàn)在,這里是如何與Shiro完全相同的事情。
String hex = new Md5Hash(myFile).toHex();當您使用Shiro簡化所有工作時,它會變得非常簡單和容易理解。 SHA-512哈希和密碼的Base64編碼同樣簡單。
String encodedPassword =new Sha512Hash(password, salt, count).toBase64();您可以看到Shiro簡化了散列和編碼的程度,在此過程中為您節(jié)省了一些理智。
Ciphers
密碼是加密算法,可以使用密鑰可逆地轉換數(shù)據(jù)。 我們使用它們來保證數(shù)據(jù)安全,特別是在傳輸或存儲數(shù)據(jù)時,數(shù)據(jù)特別容易被窺探的時候。
如果你曾經(jīng)使用過JDK Cryptography API,特別是javax.crypto.Cipher類,你知道它可能是一個令人難以置信的復雜野獸。 對于初學者,每個可能的密碼配置總是由javax.crypto.Cipher的實例表示。 需要做公鑰/私鑰加密嗎? 您使用密碼。 需要使用Block Cipher進行流媒體操作嗎? 您使用密碼。 需要創(chuàng)建AES 256位密碼來保護數(shù)據(jù)? 您使用密碼。 你明白了。
您如何創(chuàng)建所需的Cipher實例? 您創(chuàng)建了一個復雜的,不直觀的以令牌分隔的密碼選項字符串,稱為“轉換字符串”,并將此字符串傳遞給Cipher.getInstance靜態(tài)工廠方法。 使用此密碼選項字符串方法,沒有類型安全性來確保您使用有效選項。 這也隱含地意味著沒有JavaDoc來幫助您理解相關選項。 如果您的String配置不正確,即使您知道配置正確,您還需要處理已檢查的異常。 如您所見,使用JDK Ciphers是一項非常繁瑣的任務。 這些技術很久以前就已成為Java API的標準,但時代已經(jīng)發(fā)生變化,我們想要一種更簡單的方法。
Shiro試圖通過引入其CipherService API來簡化加密密碼的整個概念。 CipherService是大多數(shù)開發(fā)人員在保護數(shù)據(jù)時所需要的:一個簡單的,無狀態(tài)的,線程安全的API,可以在一個方法調用中完整地加密或解密數(shù)據(jù)。 您需要做的就是提供密鑰,您可以根據(jù)需要進行加密或解密。 例如,可以使用256位AES加密,如下面的list13所示。
Listing 13. Apache Shiro’s Encryption API
AesCipherService cipherService = new AesCipherService(); cipherService.setKeySize(256); //create a test key: byte[] testKey = cipherService.generateNewKey(); //encrypt a file’s bytes: byte[] encrypted =cipherService.encrypt(fileBytes, testKey);與JDK的Cipher API相比,Shiro示例更簡單:
Shiro的CipherService API還有其他好處,例如支持基于字節(jié)數(shù)組的加密/解密(稱為“塊”操作)以及基于流的加密/解密(例如,加密音頻或視頻)的能力。
Java密碼學不需要痛苦。 Shiro的加密支持旨在簡化您保護數(shù)據(jù)安全的工作。
Web Support
最后,但并非最不重要的是,我們將簡要介紹Shiro的web支持。 Shiro附帶強大的Web支持模塊,可幫助保護Web應用程序。 為Web應用程序設置Shiro很簡單。 唯一需要的是在web.xml中定義Shiro Servlet過濾器。 list14顯示了此代碼。
Listing 14. ShiroFilter in web.xml
ShiroFilter</filter-name>org.apache.shiro.web.servlet.IniShiroFilter</filter-class></filter>ShiroFilter</filter-name>/*</url-pattern> </filter-mapping>此過濾器可以讀取前面提到的shiro.ini配置,因此無論部署環(huán)境如何,您都可以獲得一致的配置體驗。 配置完成后,Shiro過濾器將過濾每個請求,并確保在請求期間可以訪問特定于請求的主題。 并且因為它會過濾每個請求,您可以執(zhí)行特定于安全性的邏輯,以確保只允許滿足特定條件的請求。
URL-Specific Filter Chains
Shiro通過其創(chuàng)新的URL過濾器鏈接功能支持特定于安全性的過濾規(guī)則。 它允許您為任何匹配的URL模式指定ad-hoc過濾器鏈。 這意味著您可以使用Shiro的過濾機制在執(zhí)行安全規(guī)則(或規(guī)則組合)方面具有很大的靈活性 - 遠遠超過您可以單獨在web.xml中定義過濾器。 list15顯示了Shiro INI中的配置代碼段。
Listing 15. Path-specific Filter Chains
[urls] /assets/** = anon /user/signup = anon /user/** = user /rpc/rest/** = perms[rpc:invoke], authc /** = authc如您所見,Web應用程序可以使用[urls] INI部分。 對于每一行,等號左側的值表示與上下文相關的Web應用程序路徑。 右側的值定義了一個Filter鏈 - 一個有序的逗號分隔的Servlet過濾器列表,用于給定路徑執(zhí)行。 每個過濾器都是一個普通的Servlet過濾器,但您在上面看到的過濾器名稱(anon,user,perms,authc)是Shiro提供的特殊安全相關過濾器。 您可以混合和匹配這些安全篩選器,以創(chuàng)建非常自定義的安全體驗。 您還可以指定您可能擁有的任何其他現(xiàn)有Servlet過濾器。
與使用web.xml相比,這有多好,在這里您定義了一個過濾器塊,然后是一個單獨的斷開的過濾器模式塊? 使用Shiro的方法,更容易看到為給定匹配路徑執(zhí)行的過濾器鏈。 如果您愿意,您可以在web.xml中僅定義Shiro Filter,并在shiro.ini中定義所有其他過濾器和過濾器鏈,以獲得比web.xml更簡潔易懂的過濾器鏈定義機制。 即使您沒有使用Shiro的任何安全功能,僅此一個小便利就可以使Shiro值得使用。
JSP Tag Library
Shiro還提供了一個JSP標記庫,允許您根據(jù)當前Subject的狀態(tài)控制JSP頁面的輸出。 這有用的一個常見示例是在用戶登錄后顯示“Hello ”文本。 但如果他們是匿名的,你可能想要展示別的東西,比如“你好! 立即注冊!“相反。 list16顯示了如何使用Shiro的JSP標記來支持它。
Listing 16. JSP Taglib Example
<%@ taglib prefix="shiro"uri="http://shiro.apache.org/tags" %> ...Hello! </shiro:user>! Register today!</a> </shiro:guest> </p>還有其他標記允許您根據(jù)他們擁有(或沒有)的角色,分配(或未分配)的權限以及是否通過“記住我”服務記住它們,或者記住它們來包含輸出 匿名客人。
Shiro支持許多其他特定于Web的功能,例如簡單的“記住我”服務,REST和BASIC身份驗證,當然還有透明的HttpSession支持,如果您想使用Shiro的本機企業(yè)會話。 有關更多信息,請參閱Apache Shiro Web文檔。
Web Session Management
最后,有趣的是指出Shiro對Web環(huán)境中的會話的支持。
Default Http Sessions
對于Web應用程序,Shiro默認其會話基礎結構使用我們以前習慣的現(xiàn)有Servlet容器會話。 也就是說,當你調用方法subject.getSession()和subject.getSession(boolean)時,Shiro將返回由Servlet容器的HttpSession實例支持的Session實例。 這種方法的優(yōu)點在于調用subject.getSession()的業(yè)務層代碼與Shiro Session實例交互 - 它沒有“知識”它正在使用基于Web的HttpSession對象。 在跨建筑層保持清潔分離時,這是一件非常好的事情。
Shiro’s Native Sessions in the Web Tier
如果您已經(jīng)在Web應用程序中啟用了Shiro的本機會話管理,因為您需要Shiro的企業(yè)會話功能(如與容器無關的群集),您當然希望HttpServletRequest.getSession()和HttpSession API與“本機”會話一起使用,不是servlet容器會話。如果你必須重構任何使用HttpServletRequest和HttpSession API的代碼來改為使用Shiro的Session API,那將是非常令人沮喪的。 Shiro當然不會指望你這樣做。相反,Shiro完全實現(xiàn)了Servlet規(guī)范的Session部分,以支持Web應用程序中的本機會話。這意味著無論何時調用相應的HttpServletRequest或HttpSession方法調用,Shiro都會將這些調用委托給其內部本地Session API。最終結果是,即使您正在使用Shiro的“本機”企業(yè)會話管理,您也不必更改您的Web代碼 - 這確實是一個非常方便(和必要)的功能。
Additional Features
Apache Shiro框架中還有其他一些對保護Java應用程序有用的功能,例如:
Framework Limitations
盡管我們可能會喜歡它,但Apache Shiro并不是一個“銀彈” - 它無法毫不費力地解決所有安全問題。 Shiro沒有提到可能值得了解的事情:
Upcoming Features
Apache Shiro的社區(qū)每天都在不斷發(fā)展,有了它,Shiro的功能也是如此。 在即將推出的版本中,您可能會看到:
- 更清晰的Web過濾機制,允許更多的可插入過濾支持,無需子類化。
- 更多可插入的默認Realm實現(xiàn)更有利于組合而不是繼承。 您將能夠插入查找身份驗證和授權數(shù)據(jù)的組件,而不是要求您繼承Shiro Realm實現(xiàn)
強大的OpenID和OAuth(以及可能的混合)客戶端支持 - Captcha支持
- 更輕松地配置100%無狀態(tài)應用程序(例如,許多REST環(huán)境)。
- 通過請求/響應協(xié)議進行多階段身份驗證。
- 通過AuthorizationRequest進行粗粒度授權。
- 安全斷言查詢的ANTLR語法(例如(‘role(admin)&&(guest ||!group(developer))’)
Summary
Apache Shiro是一個功能齊全,功能強大且通用的Java安全框架,可用于保護應用程序。 通過簡化應用程序安全性的四個方面,即身份驗證,授權,會話管理和加密,應用程序安全性在實際應用程序中更容易理解和實現(xiàn)。 Shiro的簡單架構和JavaBeans兼容性使其幾乎可以在任何環(huán)境中進行配置和使用。 額外的Web支持和輔助功能(如多線程和測試支持)使框架更加完善,可以為應用程序安全提供“一站式服務”。 Apache Shiro的開發(fā)團隊繼續(xù)向前發(fā)展,完善代碼庫并支持社區(qū)。 隨著持續(xù)的開源和商業(yè)應用,Shiro預計只會變得更強大。
Resources
-
Apache Shiro的主頁。
-
Shiro的下載頁面,包含Maven和Ant Ivy用戶的其他信息。
-
Apache Shiro的文檔頁面,包含指南和參考手冊
-
由項目的PMC主席Les Hazlewood提供的Apache Shiro演示視頻和幻燈片。
-
其他Apache Shiro文章和演示文稿
-
Apache Shiro郵件列表和論壇。
-
Katasoft - 一家提供Apache Shiro專業(yè)支持和應用程序安全產(chǎn)品的公司。
-
如果對后端、爬蟲、數(shù)據(jù)結構算法等感性趣歡迎關注我的個人公眾號交流:bigsai
總結
以上是生活随笔為你收集整理的Apache shiro介绍的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Springboot制作小网盘系统(小项
- 下一篇: ElasticSearch学习笔记(一)