shiro--身份授权的基本流程
身份授权基本流程
- 先调用Subject.isPermitted/hasRole接口,其会委托给SecurityManager
- SecurityManager再交给Authorizer
- Authorizer再交给Realm去做,Realm才是真正干活的
- Realm将用户请求的参数封装成权限对象。再从我们重写的doGetAuthorizationInfo方法中获取从数据库中查到的权限集合
- Realm将用户传入的权限和数据库中查到的权限进行对比,如果传入的权限对象在数据库查到的权限集合中,则返回true,否则返回false
demo
DefinitionRealm自定义Realm类
package realm;
import org.apache.shiro.authc.AuthenticationException;
import org.apache.shiro.authc.AuthenticationToken;
import org.apache.shiro.authc.SimpleAuthenticationInfo;
import org.apache.shiro.authc.UnknownAccountException;
import org.apache.shiro.authc.credential.HashedCredentialsMatcher;
import org.apache.shiro.authz.AuthorizationInfo;
import org.apache.shiro.authz.SimpleAuthorizationInfo;
import org.apache.shiro.realm.AuthorizingRealm;
import org.apache.shiro.subject.PrincipalCollection;
import org.apache.shiro.util.ByteSource;
import service.SecurityService;
import service.impl.SecurityServiceImpl;
import tools.DigestsUtil;
import java.util.List;
import java.util.Map;
public class DefinitionRealm extends AuthorizingRealm {
// 在构造函数中修改密码比较器
public DefinitionRealm(){
// 指定密码匹配方式sha1
HashedCredentialsMatcher matcher = new HashedCredentialsMatcher(DigestsUtil.SHA1);
// 指定密码迭代次数
matcher.setHashIterations(DigestsUtil.ITERATIONS);
// 使用父层方法是匹配方式生效
setCredentialsMatcher(matcher);
}
/***
* 鉴权方法
* @param principalCollection
* @return
*/
@Override
protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principalCollection) {
// 拿到用户凭证信息
String loginName = (String) principalCollection.getPrimaryPrincipal();
// 从数据库中查询对应的角色和权限
SecurityService securityService = new SecurityServiceImpl();
List<String> roles = securityService.findRoleByLoginName(loginName);
List<String> Permissions = securityService.findPermissionByLoginName(loginName);
// 构建资源校验对象
SimpleAuthorizationInfo info = new SimpleAuthorizationInfo();
info.addRoles(roles);
info.addStringPermissions(Permissions);
return info;
}
/***
* 认证方法
* @param authenticationToken
* @return
* @throws AuthenticationException
*/
@Override
protected SimpleAuthenticationInfo doGetAuthenticationInfo(AuthenticationToken authenticationToken) throws AuthenticationException {
// 获取登录名
String username = (String) authenticationToken.getPrincipal();
SecurityService service = new SecurityServiceImpl();
Map<String,String> map = service.findPasswordByUsername(username);
if(map.isEmpty()){
throw new UnknownAccountException("账号不存在!");
}
String password = map.get("password");
String salt = map.get("salt");
return new SimpleAuthenticationInfo(username, password, ByteSource.Util.bytes(salt), getName());
}
}
service 和serviceImpl
package service;
import java.util.List;
import java.util.Map;
// 模拟数据库操作
public interface SecurityService {
Map<String,String> findPasswordByUsername(String username);
// 查询角色
List<String> findRoleByLoginName(String username);
// 查询资源
List<String> findPermissionByLoginName(String username);
}
package service.impl;
import service.SecurityService;
import tools.DigestsUtil;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Map;
public class SecurityServiceImpl implements SecurityService {
@Override
public Map<String,String> findPasswordByUsername(String username) {
return DigestsUtil.entryptPassword("123");
}
@Override
public List<String> findRoleByLoginName(String username) {
List<String> roles = new ArrayList<>();
roles.add("admin");
roles.add("dev");
return roles;
}
@Override
public List<String> findPermissionByLoginName(String username) {
List<String> permissions = new ArrayList<>();
permissions.add("order:add");
permissions.add("order:list");
permissions.add("order:del");
return permissions;
}
}
demo类
import org.apache.shiro.SecurityUtils;
import org.apache.shiro.authc.UsernamePasswordToken;
import org.apache.shiro.config.IniSecurityManagerFactory;
import org.apache.shiro.mgt.SecurityManager;
import org.apache.shiro.subject.Subject;
import org.junit.Test;
public class ShiroDemo {
public Subject shiroLogin( ){
//1.导入权限ini文件,创建SecurityManagerFactory
IniSecurityManagerFactory factory = new IniSecurityManagerFactory("classpath:shiro.ini");
//2.获取SecurityManager,绑定到SecurityUtils中
SecurityManager securityManager =factory.getInstance();
SecurityUtils.setSecurityManager( securityManager);
//3.获取一个用户主体
Subject currentUser = SecurityUtils.getSubject();
UsernamePasswordToken token = new UsernamePasswordToken("guest", "123");
currentUser.login(token);
System.out.println("是否登录成功:"+currentUser.isAuthenticated());
return currentUser;
}
@Test
public void testPermissionRealm() {
Subject currentUser = shiroLogin();
// 校验当前用户是否有管理员角色
System.out.println("是否有管理员角色:"+currentUser.hasRole("admin"));
// 校验当前用户没有的角色
try {
currentUser.checkRole("coder");
System.out.println("当前用户有coder角色");
}catch (Exception e){
System.out.println("当前用户没有coder角色");
}
// 校验当前用户的权限信息
System.out.println("是否有查询权限:"+currentUser.isPermitted("order:list"));
// 校验当前用户没有的权限
try {
currentUser.checkPermission("order:update");
System.out.println("当前用户有修改的权限");
}catch (Exception e){
System.out.println("当前用户没有修改的权限");
}
}
}
运行结果

本文来自博客园,作者:NE_STOP,转载请注明原文链接:https://www.cnblogs.com/alineverstop/p/19453897
浙公网安备 33010602011771号