shiro学习总结(一)
来源:互联网 发布:mac 视频截取gif 编辑:程序博客网 时间:2024/05/19 15:45
shiro学习总结(一)
一、shiro简介
shiro是Java的一个安全(权限框架)。
shiro可以完成:认证、授权、加密、会话管理、与web集成、缓存等;
最主要的四个功能:认证(如密码匹配)、授权、会话管理、加密;
Subject:即“当前操作用户”。但是,在Shiro中,Subject这一概念并不仅仅指人,也可以是第三方进程、后台帐户(Daemon Account)或其他类似事物。它仅仅意味着“当前跟软件交互的东西”。但考虑到大多数目的和用途,你可以把它认为是Shiro的“用户”概念。
Subject代表了当前用户的安全操作,SecurityManager则管理所有用户的安全操作。
SecurityManager:它是Shiro框架的核心,典型的Facade模式,Shiro通过SecurityManager来管理内部组件实例,并通过它来提供安全管理的各种服务。
Realm: Realm充当了Shiro与应用安全数据间的“桥梁”或者“连接器”。也就是说,当对用户执行认证(登录)和授权(访问控制)验证时,Shiro会从应用配置的Realm中查找用户及其权限信息。
二、HelloWorld
shiroFilter是一个入口;
anon 拦截器表示匿名访问,既不需要登录即可访问;
authc 拦截器表示需要身份认证通过后才能进行访问;
logout 表示登出的过滤器
没有配置成 authc 的可以进行访问;配置成 anon 匿名的可以进行访问;
<property name="filterChainDefinitions"> <value> /login.jsp = anon /** = authc </value></property>
在 applicatioContext.xml 中配置的 org.apache.shiro.spring.web.ShiroFilterFactoryBean 的名字必须和 web.xml 中的 org.springframework.web.filter.DelegatingFilterProxy 的名字相同;若不一致,则会在加载项目时抛出
org.springframework.beans.factory.NoSuchBeanDefinitionException 异常,因为 shiro 会在 IOC 容器中 查找和 <filter-name>
相同的对象的bean(也可以通过 targetBeanName 这个参数配置);
DelegatingFilterProxy 实际上是 Filter 的一个代理对象,默认情况回到 IOC 容器中查找和 <filter-name>
对应的filter bean,也可以通过 targetBeanName 的初始化参数来配置 filter bean 的id;
URL 匹配模式使用 Ant 风格模式:
?:匹配一个字符;
*:匹配零个或多个字符;
**:匹配路径中的另个或多个路径;
URL匹配采用第一匹配优先的模式;
shiro认证:
1. 获取当前的Subject,调用 SecurityUtils.getSubject();
2.测试当前的用户是否已经被认证,即是否已经登录, 调用 Subject 的 isAuthenticates()
3.若没有被认证,则把用户名和密码封装为 UsernamePasswordToken对象;
1).创建一个表单页面
2).把请求提交到 SpringMVC的Handler
3).获取用户名和密码
4.执行登录:调用Subject 的login(AuthenticationToken )方法。
5.自定义 Realm 的方法,从数据库中获取对应的记录,返回给 shiro;
1).实际上需要继承 org.apache.shiro.realm.AuthenticatingRealm 类
2).实现doGetAuthenticationInfo(AuthenticationToken) 方法。
6.由 shiro 完成对密码的比对。
自定义Realm:
package com.vincent.shiro.realms;import org.apache.shiro.authc.AuthenticationException;import org.apache.shiro.authc.AuthenticationInfo;import org.apache.shiro.authc.AuthenticationToken;import org.apache.shiro.authc.LockedAccountException;import org.apache.shiro.authc.SimpleAuthenticationInfo;import org.apache.shiro.authc.UnknownAccountException;import org.apache.shiro.authc.UsernamePasswordToken;import org.apache.shiro.realm.AuthenticatingRealm;public class ShiroRealm extends AuthenticatingRealm{ @Override protected AuthenticationInfo doGetAuthenticationInfo( AuthenticationToken token) throws AuthenticationException { //1、把 AuthenticationToken 转换为 UsernamePasswordToken UsernamePasswordToken upToken = (UsernamePasswordToken) token; //2、从 UsernamePasswordToken 中获取 username String username = upToken.getUsername(); //3、调用数据库的方法,从数据库中查询 username 对应的用户记录 System.out.println("从数据库中获取username:"+username+" 所对应的用户信息。"); //4、若用户不存在,则可以抛出 UnknownAccountException 异常 if("unknown".equals(username)){ throw new UnknownAccountException("用户不存在"); } //5、根据用户信息的情况,决定是否需要抛出其他的 AuthenticationException 异常 if("monster".equals(username)){ throw new LockedAccountException("用户被锁定"); } //6、根据用户的情况,来构建 AuthenticationException 对象并返回。通常使用的实现类为:SimpleAuthencationInfo //以下信息是从数据中获取的 //(1)、principle:认证的实体信息,可以是username,也可以是数据表对应的用户的实体类对象. Object principal = username; //(2)、credentials:从数据表中获取的密码 Object credentials = "123456"; //(3):realmName:当前 realm 对象的 name,调用父类的 getName() 方法即可 String realmName = getName(); SimpleAuthenticationInfo info = new SimpleAuthenticationInfo(principal, credentials, realmName); return info; }}
tips:由于存在shiro 缓存,因此需要在登录成功后需要执行登出操作才能测试其他效果;
密码的比对:
通过 AuthenticationRealm 的credentialsMatcher 属性来进行的密码的比对!可以通过 credentialsMatcher 来进行密码的加密。
密码的加密(MD5加密、SHA1加密):
在数据库中保存的密码不应该是明文,而且加密操作应该是不可逆的;
1)、如何把一个字符串加密为 MD5(对从数据库中获取的字符串进行加密);
2)、替换当前 Realm 的credentialsMatcher 。直接使用HashedCredentialsMatcher 对象,并设置属性加密算法即可(用于把从前台获取的密码进行 MD5 加密);
<bean id="jdbcRealm" class="com.vincent.shiro.realms.ShiroRealm"> <property name="credentialsMatcher"> <bean class="org.apache.shiro.authc.credential.HashedCredentialsMatcher"> <property name="hashAlgorithmName" value="MD5"></property> </bean> </property> </bean>
密码的MD5盐值加密(salt):
密码的MD5加密存在的问题:如果两人使用的密码一样,则加密后的结果将会一样;
步骤:
1):在 doGetAuthenticationInfo 方法返回值创建 SimpleAuthenticationInfo 对象时,需要使用如下构造器:
new SimpleAuthenticationInfo(principal, credentials, credentialsSalt, realmName)
2)、使用 ByteSource.Util.bytes() 计算盐值;
3)、盐值需要唯一:一般使用随机字符串或 user id;
4)、使用 new SimpleHash(algorithmName, source, salt, iterations); 来计算盐值加密后的密码的值;
使用以上方法,即使两个人使用同样的密码,数据库中保存的密码也不相同;
多Realm:
配置流程:
<bean id="authenticator" class="org.apache.shiro.authc.pam.ModularRealmAuthenticator"> <property name="realms"> <list> <ref bean="jdbcRealm"/> <ref bean="secondRealm"/> </list> </property> </bean> <bean id="securityManager" class="org.apache.shiro.web.mgt.DefaultWebSecurityManager"> <property name="cacheManager" ref="cacheManager"/> <!-- Single realm app. If you have multiple realms, use the 'realms' property instead. --> <property name="authenticator" ref="authenticator"/> </bean>
多个realm是有认证顺序的;
- Shiro学习总结(一)--关于Shiro
- shiro学习总结(一)
- shiro学习(一)
- shiro学习(一)
- shiro学习(一)
- Shiro学习(总结)
- Shiro学习(总结)
- shiro学习摘录(一)
- shiro学习总结(二)
- Shiro 总结一
- Shiro学习总结(10)——Spring集成Shiro
- Shiro学习总结(1)——Apache Shiro简介
- Shiro学习总结(二)--Shiro的入门小例子
- 权限验证框架Shiro学习(一)
- Apache Shiro学习(一)架构介绍
- Shiro个人学习笔记(一)
- shiro学习-基础介绍(一)
- apache Shiro学习笔记(一)
- Java 中的异常和处理详解
- Java学习笔记(一)
- Parencodings(POJ1068 模拟)
- ROS06-能力进阶-硬件连接
- Java中数组与字符串之间的转换方法(一)
- shiro学习总结(一)
- ROS07-能力进阶-远程调试
- Codeforces Round #436 (Div. 2)
- 疯狂JAVA讲义-接口
- C++ 隐藏和IsA
- 机器学习 第一周 总结 知识点
- 浅谈linux中的根文件系统(rootfs的原理和介绍)
- Mysql Repliaction(复制)集群架构理论实践篇
- 查找算法