Shiro:Apache Shiro is a powerful and easy-to-use Java security framework that performs authentication, authorization, cryptography, and session management.
简而言之,shiro是一个强大也易用的Java安全框架,可执行身份验证、授权、密码学和回话管理
概念
Authentication 认证 即 who are you? 其动词原形是authenicate,可翻译为 证明、鉴定、证实
Authorization 授权 即 what can you do? 其动词原形是authorize,可翻译为 授权、批准
运行流程
首先看看流程图
Application 用户编写的代码
Subject 主体 代表了当前“用户”,这个用户不一定是一个具体的人,与当前应用交互的任何东西都是Subject
SecurityManager 安全管理器 所有与安全有关的操作都会与SecurityManager交互,且它管理着所有的Subject
Realm 域 Shiro从Realm中获取安全数据,如果SecurityManager要验证用户身份,需要从Realm获取相应的用户进行比较以确定用户身份是否合法;可以把Realm看作DataSource,即安全数据源
Shiro进行权限控制的四种主要方式:
1. 在程序中通过Subject编程方式进行权限控制
2. 配置Filter实现Url级别粗粒度权限控制
3. 配置代理 基于注解实现细粒度权限控制
4. 在页面中使用Shiro自定义标签实现 页面显示权限控制
自定义Realm
需要继承AuthorizingRealm,重写父类中的两个方法:
import org.apache.shiro.authc.AuthenticationException; import org.apache.shiro.authc.AuthenticationInfo; import org.apache.shiro.authc.AuthenticationToken; import org.apache.shiro.authz.AuthorizationInfo; import org.apache.shiro.subject.PrincipalCollection; public class CustomizeAuthorizingRealm extends org.apache.shiro.realm.AuthorizingRealm { @Override protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken authenticationToken) throws AuthenticationException { //todo return null; }
@Override
protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principalCollection) {
//todo
return null;
}
}
doGetAuthenticationInfo
获取身份验证相关的信息:首先根据传入的用户名获取User信息;
如果User为空,那么抛出没找到帐号异常UnknownAccountException;
如果user找到但锁定了抛出锁定异常LockedAccountException;
最后生成AuthenticationInfo信息,交给间接父类AuthenticatingRealm使用CredentialsMatcher进行判断密码是否匹配,如果不匹配将抛出密码错误异常IncorrectCredentialsException;
另外如果密码重试此处太多将抛出超出重试次数异常ExcessiveAttemptsException;
在组装SimpleAuthenticationInfo信息时,需要传入:身份信息(用户名)、凭据(密文密码)、盐(username+salt),CredentialsMatcher使用盐加密传入的明文密码和此处的密文密码进行匹配
此方法的返回值 AuthenticationInfo
doGetAuthorizationInfo
PrincipalCollection是一个身份集合,如果现在就一个Realm,那直接调用getPrimaryPrincipal得到之前传入的用户名即可;
然后根据用户名调用UserService接口获取角色及权限信息
参考文章 https://www.cnblogs.com/maofa/p/6407102.html
END