概念
授權,又稱作爲訪問控制,是對資源的訪問管理的過程,即對於認證通過的用戶,授予他可以訪問某些資源的權限。
授權流程圖
簡單授權實現
在shiro-permession.ini文件中設置
[users]
#用戶admin的密碼是123456,此用戶具有role2角色
coco=123456,role1
admin=123456,role1,role2
[roles]
#角色role1對資源user擁有create、update、delete權限
role1=user:create,user:update,user:delete
#角色role2對資源user擁有create權限
role2=user:create
#角色role3對資源user擁有select權
role3=user:select
驗證角色和權限
@Test
public void demoTree(){
// 裝入 INI 配置
Factory<SecurityManager> factory = new IniSecurityManagerFactory("classpath:shiro-permession.ini");
//創建SecurityManager對象
SecurityManager instance = factory.getInstance();
//使SecurityManager可以訪問
SecurityUtils.setSecurityManager(instance);
//接受提交的用戶名和密碼:
UsernamePasswordToken tooken = new UsernamePasswordToken("admin","123456");
//獲取當前主體
Subject subject = SecurityUtils.getSubject();
try {
subject.login(tooken);
} catch (UnknownAccountException e) {
System.out.println("用戶名錯誤!");
}
catch (IncorrectCredentialsException e) {
System.out.println("密碼錯誤!");
}
System.out.println("是否認證成功:" + subject.isAuthenticated());
//粗顆粒度授權 ===> 角色驗證
System.out.println(subject.getPrincipal()+" 是否具有role1角色====> "+subject.hasRole("role1"));
System.out.println(subject.getPrincipal()+" 是否具有role2角色====> "+subject.hasRole("role2"));
System.out.println(subject.getPrincipal()+" 是否具有role3角色====> "+subject.hasRole("role3"));
System.out.println(subject.getPrincipal()+" 是否具有role1和role2角色====> "+subject.hasAllRoles(Arrays.asList("role1","role2")));
//subject.checkRole("role1");
//細顆粒度授權 ===> 資源驗證
System.out.println(subject.getPrincipal()+" 是否具有user:create資源權限====> "+subject.isPermitted("user:create"));
System.out.println(subject.getPrincipal()+" 是否具有user:delete資源權限====> "+subject.isPermitted("user:delete"));
System.out.println(subject.getPrincipal()+" 是否具有user:delete,user:update資源權限====> "+subject.isPermittedAll("user:delete","user:update"));
}
輸出結果
是否認證成功:true
admin 是否具有role1角色====> true
admin 是否具有role2角色====> true
admin 是否具有role3角色====> false
admin 是否具有role1和role2角色====> true
admin 是否具有user:create資源權限====> true
admin 是否具有user:delete資源權限====> true
admin 是否具有user:delete,user:update資源權限====> true
注意
subject.checkRole("role1");
subject.checkPermission("user:create");
檢查是否存在該角色和權限,如果不存在則會拋異常
自定義Realm授權
重寫授權的方法
注意:這裏認證方法中採用的是明文認證
public class ShiroRealmsOne extends AuthorizingRealm{
/**
* 認證
*/
@Override
protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken token) throws AuthenticationException {
String username =(String)token.getPrincipal();
if(!"admin".equals(username)){
return null;
}
//String pwd = "123456"; 密碼
//String salt = "copy"; 鹽值
// acd1b8d62a8369c3d6278ea6f663407b 兩次迭代加密後的密碼
String salt = "copy";
ByteSource saltByte = ByteSource.Util.bytes(salt);
String password = "123456";
SimpleAuthenticationInfo info = new SimpleAuthenticationInfo(username,password,this.getName());
return info;
}
/**
* 授權
*/
@Override
protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principals) {
String username = (String)principals.getPrimaryPrincipal();
List<String> list = new ArrayList<String>();
list.add("project:create");
list.add("user:delete");
SimpleAuthorizationInfo info = new SimpleAuthorizationInfo();
info.addStringPermissions(list);
return info;
}
}
shiro-realms.ini文件
[main]
shiroUserRealm=com.sumeng.shiro.ShiroRealmsOne
securityManager.realms=$shiroUserRealm
測試
@Test
public void demoTree(){
// 裝入 INI 配置
Factory<SecurityManager> factory = new IniSecurityManagerFactory("classpath:shiro-realms.ini");
//創建SecurityManager對象
SecurityManager instance = factory.getInstance();
//使SecurityManager可以訪問
SecurityUtils.setSecurityManager(instance);
//接受提交的用戶名和密碼:
UsernamePasswordToken tooken = new UsernamePasswordToken("admin","123456");
//獲取當前主體
Subject subject = SecurityUtils.getSubject();
try {
subject.login(tooken);
} catch (UnknownAccountException e) {
System.out.println("用戶名錯誤!");
}
catch (IncorrectCredentialsException e) {
System.out.println("密碼錯誤!");
}
System.out.println("是否認證成功:" + subject.isAuthenticated());
//細顆粒度授權 ===> 資源驗證
System.out.println(subject.getPrincipal()+" 是否具有user:create資源權限====> "+subject.isPermitted("user:create"));
System.out.println(subject.getPrincipal()+" 是否具有user:delete資源權限====> "+subject.isPermitted("user:delete"));
System.out.println(subject.getPrincipal()+" 是否具有project:create資源權限====> "+subject.isPermitted("project:create"));
System.out.println(subject.getPrincipal()+" 是否具有user:delete,project:create資源權限====> "+subject.isPermittedAll("user:delete","project:create"));
}
輸出結果
是否認證成功:true
admin 是否具有user:create資源權限====> false
admin 是否具有user:delete資源權限====> true
admin 是否具有project:create資源權限====> true
admin 是否具有user:delete,project:create資源權限====> true