Subject(主体)
通过安全管理器进行 认证 和授权
SecurityMannager 安全管理器
SecurityMannager 是shiro框架的核心
Authenticator 认证器
对主体进行认证
Authorizer 授权器
用户通过认证器认证通过,在访问功能时通过授权器判断用户是否有此功能的操作权限
Realm
SecurityMannager 进行安全认证需要通过Realm湖区用户权限数据 Realm 也是一个接口
Realm:
从配置文件或者数据库等读取用户的权限信息
多实现:
1.将用户的权限信息存储到配置文件
2.将用户的权限信息存储到数据库
SessionManager 会话管理器
shiro框架有一套自己的session容器
shiro可以使用到非wevb项目上的,也可以实现单点登录
SessionDao
是对session会话操作的一套接口,比如要将会话信息存储到redis数据库
CacheManager 缓存管理器(提高性能)缓存第三方
防止用户每次或是重复登陆,都需要在数据库获取一次权限信息,所以存放在缓存中
对于用户反复查询访问自身那个权限的这种操作,便提供了缓存管理器
第一次访问后将信息放入缓存管理器,在接下来的操作中,直接从缓存中获取用户权限
Cryptography
密码管理器,shiro提供了一套加密/解密的组件,方便开发。比如提供常用的散列,加密解密等功能
接下来的使用就是调用方法或类,来完成shiro的操作
搭建maven依赖包
<!-- https://mvnrepository.com/artifact/junit/junit -->
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.12</version>
<scope>test</scope>
</dependency>
<!-- https://mvnrepository.com/artifact/org.apache.shiro/shiro-core -->
<dependency>
<groupId>org.apache.shiro</groupId>
<artifactId>shiro-core</artifactId>
<version>1.3.2</version>
</dependency>
<!-- ----------------- 用于slf4j 和log4j的一个桥接------------------------- -->
<!-- https://mvnrepository.com/artifact/org.apache.logging.log4j/log4j-slf4j-impl -->
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-slf4j-impl</artifactId>
<version>2.12.1</version>
<scope>test</scope>
</dependency>
slf4j 提供了一个日志访问的统一接口,为各种日志框架提供了统一格式的访问api
日志的门面系统
搭建 配置文件:
1.shiro配置文件为 .ini (权限文档)
[users]
test=123456,admin
test1=7891011,public
[roles]
admin=product:view,prodcut:create,product:update
public=product:view
(格式):test 为用户 ,123456为密码,admin为url权限
roles:配置admin=权限1,权限2,。。。。 多个权限以逗号隔开
读取配置文件加载框架
---------------------------------------初始化shiro环境只运行一次-----------------------------------------
1.初始化shiro的安全管理器器,SecurityMannager
DefautSecurityMannager securityMannager =new DefautSecurityMannager ();
2.设置用户的权限信息到安全管理器
Realm realm=new IniRealm("classpath:shiro.ini")
//配置好读取权限后交给SecurityMannager
securityMannager.setRealm(realm)
3.使用SecurityUtils将SecurityMannager 设置到运行环境中(shiro框架提供的工具类SecurityUtils)
SecurityUtils.setSecurityManager(securityManager);
-------------------------------已完成安全管理器------------------------------------------------------
4.创建需要认证的主题(Subject)
Subject subject=SecurityMannager.getSubject();
5.创建用于认证的的认证器 ,记录用户认证的身份信息和凭证及账号和密码
UsernamePasswordToken token=new UsernamePasswordToken("test","123456");
6.主题进行登陆,登陆时及认证检查
subject.login(token);
//subject.login(token); 登陆
//subject.isAuthenticated() 返回布尔值 ,检测用户认证状态
//subject.hasRole("admin"); 返回布尔值,检查校色授权状态
//subject.isPermitted("product:view"); 返回布尔,查询登陆者的url是否存在
//subject.isPermitted("product:view","product:update")[2]; 返回一个数组,查询登陆者多个url是否存在
//subject.getPrincipal();返回String 登陆者用户账号
//subject.logout(); 退出
User currentUser = (User) SecurityUtils.getSubject().getPrincipal(); //获取当前用户
Realm realm=new IniRealm("classpath:shiro.ini")//此方法只适用于学习,ini 配置文件
如果需要数据库管理那么需要使用jdbcRealm 方法来读取数据库的用户权限
===========================使用jdbcRealm 方法来读取数据库的用户权限========================
定义连接器池
DruidDataSource druidDataSource = new DruidDataSource();
{
druidDataSource.setUrl("jdbc:mysql://49.232.54.156:3306/mw");
druidDataSource.setUsername("root");
druidDataSource.setPassword("root");
}
---------------------------------------------------配置JdbcRealm()连接数据库-------------------------------------------------------------------------
// 创建jdbcRealm数据源对象
JdbcRealm jdbcRealm = new JdbcRealm();
// 将druidDataSource绑定在jdbcRealm
jdbcRealm.setDataSource(druidDataSource);
// 设置开启可查询权限角色等SQL功能,一定要开启这个,才可以使用自定义的SQL查询语句
jdbcRealm.setPermissionsLookupEnabled(true);
// 查询用户名,密码
String UsernamePasswordSQL = "select user_password from user where user_name =?";
jdbcRealm.setAuthenticationQuery(UsernamePasswordSQL);
// 查询用户所对应的角色
String RoleSQL="select role_name from role as r left join user_role as ur on ur.role_id=r.role_id\r\n" +
"left join user as u on u.user_id=ur.user_id where u.user_name=?";
jdbcRealm.setUserRolesQuery(RoleSQL);
// 查询角色所对应的权限
String PermissionSQL="select permission_name from permission as p\r\n" +
"left join role_permission as rp on p.permission_id=rp.permission_id\r\n" +
"left join role as r on rp.role_id=r.role_id where r.role_name=?";
jdbcRealm.setPermissionsQuery(PermissionSQL);
---------------------------------------------------------注意自定义查询------------------------------------------------
realm.setAuthenticationQuery(String sql)// 该方法设置身份验证的sql语句。
realm.setUserRolesQuery(String sql)// 该方法设置角色验证的sql语句。
realm.setPermissionsQuery(String sql)// 该方法设置权限验证的sql语句。