shiro授權
本文介紹
授權流程
授權方式
授權測試
自定義授權realm
授權流程
開始
構造SecurityManager環境
subject.isPermitted()授權
securityManager.isPermitted()執行授權
Authorizer執行授權
Realm根據身份獲取資源權限信息
結束
授權方式
Shiro支持三種方式的授權:
編程式:通過寫if/else授權代碼塊完成。
Subject subject = SecurityUtils.getSubject();
if(subject.hasRole("admin")){
//有權限
}else{
//沒有權限
}
1
2
3
4
5
6
註解式:通過在執行的Java方法上放置相應的註解完成。
@RequiresRole("admin")
public void hell(){
//有權限
}
1
2
3
4
JSP標籤:在Jsp頁面通過相應的標籤完成:
<shiro:hasRole name="admin">
<!--有權限-->
</shiro:hasRole>
1
2
3
授權測試
創建ini配置文件
在classpath路徑下創建shiro-permission.ini文件,內容如下:
[users]
#用戶zhangsan的密碼是123,此用戶具有role1和role2兩個角色
zhangsan=123,role1,role2
lisi=123,role2
[roles]
#角色role1對資源user擁有create、update權限
role1=user:create,user:update
#角色role2對資源user擁有create、delete權限
role2=user:create,user.delete
#角色role3對資源user擁有create權限
role3=user:create
1
2
3
4
5
6
7
8
9
10
11
12
在ini文件中用戶、角色、權限的配置規則是: 用戶名=密碼,角色1,角色2 、角色=權限1,權限2。首先根據用戶找角色,再根據角色找權限,角色是權限集合。
權限字符串規則
權限字符串的規則是:”資源標識符:操作:資源實例標識符”,意思是對哪個資源的哪個實例具有什麼操作,”:”是資源/操作/實例的分割符,權限字符串也可以使用*通配符。
例子:
用戶創建權限:user:create或user:create:*
用戶修改實例001的權限:user:update:001
用戶實例001的所有權限:user:*:001
測試代碼
@Test
public void testPermission() {
// 構建SecurityManager工廠,IniSecurityManagerFactory可以從ini文件中初始化SecurityManager環境
Factory<SecurityManager> factory = new IniSecurityManagerFactory("classpath:shiro-permission.ini");
// 通過工廠創建SecurityManager
SecurityManager securityManager = factory.getInstance();
// 將SecurityManager設置到運行環境中
SecurityUtils.setSecurityManager(securityManager);
//創建一個Subject實例,該實例認證需要使用上面創建的SecurityManager
Subject subject = SecurityUtils.getSubject();
//創建token令牌,賬號和密碼是ini文件中配置的
//AuthenticationToken token = new UsernamePasswordToken("zhangsan", "123");//賬號密碼正確token 角色是 role1,role2
AuthenticationToken token = new UsernamePasswordToken("lisi", "123");//lisi賬號的token 角色是role3
/**
* role1=user:create,user:update
role2=user:create,user.delete
role3=user:create
*/
try {
//用戶登錄
subject.login(token);
} catch (AuthenticationException e) {
e.printStackTrace();
}
//用戶認證狀態
Boolean isAuthenticated = subject.isAuthenticated();
System.out.println("用戶認證狀態:"+isAuthenticated);//輸出true
//用戶授權檢測
//是否擁有一個角色
System.out.println("是否擁有一個角色:"+subject.hasRole("role1"));
//是否擁有多個角色
System.out.println("是否擁有多個角色:"+subject.hasAllRoles(Arrays.asList("role1","role2")));
//檢測權限
try {
subject.checkPermission("user:create");
} catch (AuthorizationException e) {
e.printStackTrace();
}
try {
subject.checkPermissions("user:create","user.delete");
} catch (AuthorizationException e) {
e.printStackTrace();
}
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
基於角色的授權
//是否擁有一個角色
System.out.println("是否擁有一個角色:"+subject.hasRole("role1"));
//是否擁有多個角色
System.out.println("是否擁有多個角色:"+subject.hasAllRoles(Arrays.asList("role1","role2")));
1
2
3
4
對應的check方法:
subject.checkRole("role1");
subject.checkRoles(Arrays.asList("role1","role2"));
1
2
上邊check方法如果授權失敗則拋出異常:
org.apache.shiro.authz.UnauthorizedException: Subject does not have role [.....]
1
基於資源授權
System.out.println("是否擁有某個權限:"+subject.isPermitted("user:create"));
System.out.println("是否擁有多個權限:"+subject.isPermittedAll("user:create","user.delete"));
1
2
對應的check方法:
subject.checkPermission("user:create");
subject.checkPermissions("user:create","user.delete");
1
2
上邊check方法如果授權失敗則拋出異常:
org.apache.shiro.authz.UnauthorizedException: Subject does not have permission [....]
1
自定義realm
在shiro認證那篇博客中編寫的自定義realm類中有一個doGetAuthorizationInfo 方法,此方法需要完成:根據用戶身份信息從數據庫查詢權限字符串,由shiro進行授權。
realm代碼
/**
* 授權方法
*/
@Override
protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principals) {
//後去身份信息,這個字段就是前面的username
String username = (String)principals.getPrimaryPrincipal();
//模擬通過身份信息獲取所有權限
List<String> permissions = new ArrayList<>();
permissions.add("user:create");
permissions.add("user:delete");
//將權限信息封裝到AuthorizationInfo中,並返回
SimpleAuthorizationInfo authorizationInfo = new SimpleAuthorizationInfo();
authorizationInfo.addStringPermissions(permissions);
return authorizationInfo;
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
shiro-realm.ini文件
需要使用這個配置文件。
測試代碼
同上邊的授權測試代碼,注意修改ini地址爲shiro-realm.ini。
授權執行流程
1、 執行subject.isPermitted(“user:create”)
2、 securityManager通過ModularRealmAuthorizer進行授權
3、 ModularRealmAuthorizer調用realm獲取權限信息
4、 ModularRealmAuthorizer再通過permissionResolver解析權限字符串,校驗是否匹配
---------------------
作者:在路上的JavaCoder-尹騎
來源:CSDN
原文:https://blog.csdn.net/facekbook/article/details/54910606?utm_source=copy
版權聲明:本文爲博主原創文章,轉載請附上博文鏈接!