久久国产成人av_抖音国产毛片_a片网站免费观看_A片无码播放手机在线观看,色五月在线观看,亚洲精品m在线观看,女人自慰的免费网址,悠悠在线观看精品视频,一级日本片免费的,亚洲精品久,国产精品成人久久久久久久

分享

第四章:Shiro的身份認證(Authentication)

 wayne_liberary 2014-08-07

Authentication概述

n概述

  Authentication 是指身份驗證的過程——即證明一個用戶實際上是不是他們所說的他們是誰,。也就是說通過提交用戶的身份和憑證給Shiro,,以判斷它們是否和應用程序預期的相匹配,。

n基本概念

1:Principals(身份):是Subject 的‘identifying attributes(標識屬性)’,。比如我們登錄提交的用戶名,。

2:Credentials(憑證):通常是只被Subject 知道的秘密值,它用來作為一種起支持作用的證據(jù),,此證據(jù)事實上包含著所謂的身份證明,。比如我們登錄提供的密碼

 

n認證的基本步驟

1. 收集Subjects 提交的Principals(身份)和Credentials(憑證);

2. 提交Principals(身份)和Credentials(憑證)進行身份驗證,;

3. 如果提交成功,,則允許訪問,否則重新進行身份驗證或者阻止訪問,。

 

認證樣例

n使用用戶名/密碼的樣例

UsernamePasswordToken token = new UsernamePasswordToken(username, password);

token.setRememberMe(true);

  樣例使用UsernamePasswordToken 來支持最常見的用戶名/密碼的身份驗證方法,。這是Shiro的org.apache.shiro.authc.AuthenticationToken 的接口,,是Shiro 代表提交的Principals(身份)和Credentials(憑證)的身份驗證系統(tǒng)所使用的基本接口的一個實現(xiàn),。

n提交用戶名/密碼進行認證

Subject currentUser = SecurityUtils.getSubject();

currentUser.login(token);

n處理認證成功和失敗

  如果認證成功,會沒有返回,,也沒有例外,,通過。

  如果認證失敗,,會拋出例外,,你可以在程序中捕獲并處理,如下示例:

 

try {

  currentUser.login(token);

} catch ( UnknownAccountException uae ) { …

} catch ( IncorrectCredentialsException ice ) { …

} catch (LockedAccountException lae ) { …

} catch (ExcessiveAttemptsException eae ) { …

} … catch your own …

nlogout(注銷)

  currentUser.logout();

  當你調用logout,任何現(xiàn)有的Session 都將會失效,,而且任何身份都將會失去關聯(lián)(例如,,在Web 應用程序中,RememberMe cookie 也將被刪除),。在Subject 注銷后,,該Subject的實例被再次認為是匿名的,當然,,除了Web 應用程序,。

  注意:由于在Web 應用程序記住身份往往是依靠Cookies,然而Cookies 只能在Response 被committed 之前被刪除,,所以強烈建議在調用subject.logout()后立即將終端用戶重定向到一個新的視圖或頁面,。

  這樣能夠保證任何與安全相關的Cookies 都能像預期的一樣被刪除。這是HTTP cookies 的功能限制,,而不是Shiro的,。

 

RememberedAuthenticated

nRemembered(記住我)

  一個記住我的Subject 不是匿名的,是有一個已知的身份ID(也就是subject.getPrincipals()是非空的),。但是這個被記住的身份ID 是在之前的session 中被認證的,。如果subject.isRemembered()返回true,則Subject 被認為是被記住的,。

 

nAuthenticated(已認證)

  一個已認證的Subject 是指在當前Session 中被成功地驗證過了(也就是說,,login方法被調用并且沒有拋出異常)。如果subject.isAuthenticated()返回true 則認為Subject 已通過驗證,。

 

n注意他們是互斥的

  Remembered 和Authenticated 是互斥的——若其中一個為真則另一個為假,,反之亦然

 

認證順序

 

nStep 1:應用程序代碼調用Subject.login 方法,傳遞創(chuàng)建好的包含終端用戶的Principals(身份)和Credentials(憑證)的AuthenticationToken 實例,。
nStep 2:Subject實例,,通常是DelegatingSubject(或子類)委托應用程序的SecurityManager通過調用securityManager.login(token)開始真正的驗證。
nStep3:SubjectManager 接收token 以及簡單地委托給內部的Authenticator 實例通過調用authenticator.authenticate(token),。這通常是一個ModularRealmAuthenticator 實例,,支持在身份驗證中協(xié)調一個或多個Realm 實例。
n
nStep 4:如果應用程序中配置了一個以上的Realm,,ModularRealmAuthenticator 實例將利用配置好的AuthenticationStrategy 來啟動Multi-Realm 認證嘗試,。在Realms 被身份驗證調用之前,期間和以后,,AuthenticationStrategy 被調用使其能夠對每個Realm 的結果作出反應,。
n
nStep 5:每個配置的Realm 用來幫助看它是否支持提交的AuthenticationToken。如果支持,,那么支持Realm 的getAuthenticationInfo 方法將會伴隨著提交的token 被調用,。getAuthenticationInfo 方法有效地代表一個特定Realm 的單一的身份驗證嘗試,。
初識自定義 Realm
n這里先來個例子,認識一下:

public class MyRealm extends AuthorizingRealm{

  protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principals) {

  String userName = (String) getAvailablePrincipal(principals);

  //通過用戶名去獲得用戶的所有資源,,并把資源存入info中

  SimpleAuthorizationInfo info = new SimpleAuthorizationInfo();

  Set<String> s = new HashSet<String>();

  s.add("p1");  s.add("p2"); info.setStringPermissions(s);

  Set<String> r = new HashSet<String>();

  r.add("r1"); r.add("r2"); info.setRoles(r);

  return info;}

  protected AuthenticationInfo doGetAuthenticationInfo(

  AuthenticationToken token) throws AuthenticationException {

  //token中儲存著輸入的用戶名和密碼

  UsernamePasswordToken upToken = (UsernamePasswordToken)token;

  String username = upToken.getUsername();

  String password = String.valueOf(upToken.getPassword());

  //通常是與數(shù)據(jù)庫中用戶名和密碼進行比對,,這里就省略了

  //比對成功則返回info,比對失敗則拋出對應信息的異常AuthenticationException

  SimpleAuthenticationInfo info = new SimpleAuthenticationInfo(username, password .toCharArray(),getName());

  return info;  }}

 

 

配置多個Realm

n上面的例子可以作為第一個Realm
n再復制一份,,定義為MyRealm2,,在返回user前添加拋出一個例外,表示認真沒有通過,,如下:

if(username.equals("javass")){

  throw new AuthenticationException("MyRealm2 認證失敗");

}

SimpleAuthenticationInfo info = new SimpleAuthenticationInfo(username, password .toCharArray(),getName());

n在配置文件里面添加Realm的定義

myRealm1=cn.javass.hello.MyRealm

myRealm2=cn.javass.hello.MyRealm2

 

由于有多個realm,,一般就需要配置AuthenticationStrategy了,而AuthenticationStrategy是跟Authenticator(認證器)相關的,。

 

 

n配置Authenticator和AuthenticationStrategy

authenticator = org.apache.shiro.authc.pam.ModularRealmAuthenticator

authcStrategy = org.apache.shiro.authc.pam.AllSuccessfulStrategy

authenticator.authenticationStrategy = $authcStrategy

authenticator.realms=$myRealm2,$myRealm1

n當然,,你可以擴展并實現(xiàn)自己的Authenticator,一般沒有必要
n最后把Authenticator設置給securityManager

  securityManager.authenticator = $authenticator

n關于AuthenticationStrategy的配置,,有三種:

AtLeastOneSuccessfulStrategy :如果一個(或更多)Realm 驗證成功,,則整體的嘗試被認為是成功的。如果沒有一個驗證成功,,則整體嘗試失敗,。

FirstSuccessfulStrategy 只有第一個成功地驗證的Realm 返回的信息將被使用。所有進一步的Realm 將被忽略,。如果沒有一個驗證成功,,則整體嘗試失敗

AllSucessfulStrategy 為了整體的嘗試成功,所有配置的Realm 必須驗證成功,。如果沒有一個驗證成功,,則整體嘗試失敗。

 

ModularRealmAuthenticator 默認的是AtLeastOneSuccessfulStrategy

 

 

n自定義自己的AuthenticationStrategy,,通常是擴展自AbstractAuthenticationStrategy,,示例如下:

public class MyAuthenticationStrategy extends AbstractAuthenticationStrategy{

  public AuthenticationInfo afterAttempt(Realm realm, AuthenticationToken token, AuthenticationInfo singleRealmInfo, AuthenticationInfo aggregateInfo, Throwable t) throws AuthenticationException {

  if(realm.getName().equals("myRealm2")){

  if(singleRealmInfo==null || singleRealmInfo.getPrincipals()==null){

  throw new AuthenticationException("主戰(zhàn)認證未通過");

  }

  }

return super.afterAttempt(realm, token, singleRealmInfo, aggregateInfo, t);

  }

}

至于具體覆蓋擴展什么方法,需要根據(jù)你具體的策略來定,。

 

 

多個Realm的驗證順序

n概述

  非常重要的一點是:ModularRealmAuthenticator 將與Realm 實例以迭代的順序進行交互,。

  在SecurityManager 中已經(jīng)配置好了ModularRealmAuthenticator 對Realm實例的訪問。當執(zhí)行一個認證嘗試時,,它將會遍歷該集合,,并對每一個支持提交AuthenticationToken 的Realm 調用Realm 的getAuthenticationInfo 方法

n隱式排列

  當你配置多個realm的時候,處理的順序默認就是你配置的順序,。

  這種情況通常就是只定義了realm,,而沒有配置securityManager的realms

n顯示排列

  也就是顯示的配置securityManager.realms,,那么執(zhí)行的順序就是你配置該值的realm的順序,。

  通常更推薦顯示排列。

    本站是提供個人知識管理的網(wǎng)絡存儲空間,所有內容均由用戶發(fā)布,,不代表本站觀點,。請注意甄別內容中的聯(lián)系方式、誘導購買等信息,,謹防詐騙,。如發(fā)現(xiàn)有害或侵權內容,請點擊一鍵舉報,。
    轉藏 分享 獻花(0

    0條評論

    發(fā)表

    請遵守用戶 評論公約

    類似文章 更多