基于Shiro的用户认证(不包含授权)

Spring整合Shiro

shiro原理

1.1   搭建环境

1.1.1      web模块 pom.xml

<dependency>
<groupId>org.apache.shiro</groupId>
<artifactId>shiro-spring</artifactId>
<version>1.3.2</version>
</dependency>
<!--shiro核心包-->
<dependency>
<groupId>org.apache.shiro</groupId>
<artifactId>shiro-core</artifactId>
<version>1.3.2</version>
</dependency>

1.1.2  Web.xml配置

<!-- Shiro Security filter  filter-name这个名字的值将来还会在spring中用到,本段代码原样粘贴,注意该过滤器是代理过滤器,它什么都不干,可以通过再Spring整合中配置相应的过滤器权限拦截器进行相应的过滤器拦截-->
<filter>
<filter-name>shiroFilter</filter-name>
<filter-class>org.springframework.web.filter.DelegatingFilterProxy</filter-class>
<init-param>
<!--如果设置"targetFilterLifecycle"为true,则spring来管理Filter.init()和Filter.destroy();若为false,则这两个方法失效-->
<param-name>targetFilterLifecycle</param-name>
<param-value>true</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>shiroFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>

1.1.3  Spring整合shiro  applicationContext-shiro.xml

 <description>Shiro与Spring整合</description>

    <!--安全管理器-->
<bean id="securityManager" class="org.apache.shiro.web.mgt.DefaultWebSecurityManager">
<!-- 引用自定义的realm -->
<property name="realm" ref="authRealm"/>
</bean> <!-- 自定义Realm域的编写 -->
<bean id="authRealm" class="此处为自定义Realm域的全限定类名">
<!-- 注入自定义Realm域的密码比较器 -->
<property name="credentialsMatcher" ref="customerCredentialsMatcher" ></property>
</bean> <!-- 密码比较器:密码加密和比较 -->
<bean id="customerCredentialsMatcher" class="自定义的证书匹配器所在的全限定类名"/> <!-- filter-name这个名字的值来自于web.xml中filter的名字 -->
<bean id="shiroFilter" class="org.apache.shiro.spring.web.ShiroFilterFactoryBean">
<property name="securityManager" ref="securityManager"/>
<!--登录页面 -->
<property name="loginUrl" value="/login.jsp"></property>
<!-- 登录失败后 跳转到未经授权的页面 -->
<property name="unauthorizedUrl" value="/unauthorized.jsp"></property>
<!--过滤器链定义,此处为访问路径设置过滤器链-->
<property name="filterChainDefinitions">
<!-- /**代表下面的多级目录也过滤,等号后面的单词就是过滤器 -->
<value> <!--如果该路径的用户不包含“模块管理”权限就禁止访问-->
<!-- /system/module/list.do = perms["模块管理"] userLogin.do /userLogin* = anon
mylogiin.jsp /mylogin* = anon
-->
/index.jsp* = anon
/login.jsp* = anon
/login* = anon
/logout* = anon
/css/** = anon
/img/** = anon
/plugins/** = anon
/make/** = anon
<!--
-->
/** = authc
/*.* = authc
</value>
</property>
</bean> <!-- 保证实现了Shiro内部lifecycle函数的bean执行 -->
<bean id="lifecycleBeanPostProcessor" class="org.apache.shiro.spring.LifecycleBeanPostProcessor"/> <!-- 生成代理,通过代理进行控制 -->
<bean class="org.springframework.aop.framework.autoproxy.DefaultAdvisorAutoProxyCreator"
depends-on="lifecycleBeanPostProcessor">
<property name="proxyTargetClass" value="true"/>
</bean> <!-- 安全管理器 -->
<bean class="org.apache.shiro.spring.security.interceptor.AuthorizationAttributeSourceAdvisor">
<property name="securityManager" ref="securityManager"/>
</bean> <aop:aspectj-autoproxy proxy-target-class="true"/>

2.1 自定义realm

/**
* 自定义reamlm*/
public class AuthRealm extends AuthorizingRealm {
@Autowired
private UserService userService;
@Autowired
private ModuleService moduleService;
/**
* 授权管理:授权
*/
protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principalCollection) {
return null;
}
/**
* 身份认证
* 用于验证输入的用户名密码给,登录
*/
protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken authenticationToken) throws AuthenticationException {
//1.获取到用户界面输入的用户名和密码
UsernamePasswordToken upToken = (UsernamePasswordToken) authenticationToken;
//2.获取用户出入的用户名和密码
String username = upToken.getUsername();
String password = new String(upToken.getPassword());
//3.根据用户名查询用户对象
User user = userService.findByUsername(username);
if(user != null) {
//第一个参数:安全数据(user对象)
//第二个参数:密码(数据库密码)
//第三个参数:当前调用realm域的名称(类名即可)
SimpleAuthenticationInfo info = new SimpleAuthenticationInfo(user,user.getPassword(),this.getName());
return info;
}
return null; //subject.login()方法的时候会抛出异常
}
}
AuthorizingRealm抽象类中被重写的方法来源

2.2 自定义密码比较

在spring与shiro的整合文件中已经将该类交给realm域中,所以直接重写方法doCredentialsMatch即可

/**
* 密码比较器
*/
public class CustomCredentialsMatcher extends SimpleCredentialsMatcher { /**
* 用户密码比较
* 1.对用户输入的密码进行加密
* 2.比较用户输入的密码和数据库密码是否一致
* @param token 用户界面输入的邮箱和密码
* @param info 安全数据:用户对象user
*
* 111111 + 固定值(加盐) = xxxxxx
*/
public boolean doCredentialsMatch(AuthenticationToken token, AuthenticationInfo info) {
//1.获取用户输入的密码
UsernamePasswordToken upToken = (UsernamePasswordToken) token;
String loginPassword = new String(upToken.getPassword());
String email = upToken.getUsername();
//2.对登录密码进行加密
//加密:使用MD5加密
String md5Paasword = Encrypt.md5(loginPassword, email);//密码,盐 //info.getPrincipals();//获取安全数据,用户对象
//获取数据库密码
String dbPassword = (String)info.getCredentials(); //true:登录成功,false:抛出异常
return md5Paasword.equals(dbPassword);
}
}

2.3 用户登录url映射

//用户登录
@RequestMapping("/login")
public String login(String username,String password) { //1、通过shiro框架提供的SecurityUtils工具类获取Subject
Subject subject = SecurityUtils.getSubject();
//2、构造用户名密码的安全对象upToken
UsernamePasswordToken upToken = new UsernamePasswordToken(username,password);
//3、通过Subject的login()方法将安全对象交给shiro的安全管理器SecurityManager
subject.login(upToken);
//4、通过shiro获取用户对象主体,保存到session
User user = (User) subject.getPrincipal(); //获取完全对象
session.setAttribute("user",user);
//5、查询菜单数据
List<Module> moduleList = moduleService.findModuleByUserid(user.getId());
session.setAttribute("modules",moduleList);
return "home/main";
}

 shiro学习推荐阅读》》》》》

》》》shiro的权限管理的注解开发只需要一个注解代码

 /**
* RequiresPermissions:
* value : 权限名称(标识)
* 如果具备此权限:进入方法
* 不具备此权限:抛出异常
*/
@RequiresPermissions("模块管理")
@RequestMapping(value = "/list",name = "查询所有")
public String list(@RequestParam(defaultValue = "1")int page,@RequestParam(defaultValue = "3")int size){
PageInfo info = moduleService.findAll(page,size);
request.setAttribute("page",info);
return "system/module/module-list";
}

2.4   页面标签展示

通过shiro标签控制页面按钮和菜单的显示

2.4.1      引入标签库

<%@ taglib prefix="shiro" uri="http://shiro.apache.org/tags" %>

2.4.2      控制显示

<shiro:hasPermission name="删除部门">
<button type="button" class="btn btn-default" title="删除" onclick='deleteById()'><i class="fa fa-trash-o"></i> 删除</button>
</shiro:hasPermission>

2.4 用户退出

//退出
@RequestMapping(value = "/logout",name="用户登出")
public String logout(){
SecurityUtils.getSubject().logout(); //登出
return "forward:login.jsp";
}

shiro自动管理session,此处会将session中的用户信息清除。

shiro获取当前用户的用户名

Subject subject = SecurityUtils.getSubject();
Object principal = subject.getPrincipal();

点击查看SpringBoot整合Shiro

Shiro安全框架案例的更多相关文章

  1. Shiro 安全框架详解二(概念+权限案例实现)

    Shiro 安全框架详解二 总结内容 一.登录认证 二.Shiro 授权 1. 概念 2. 授权流程图 三.基于 ini 的授权认证案例实现 1. 实现原理图 2. 实现代码 2.1 添加 maven ...

  2. Shiro 安全框架详解一(概念+登录案例实现)

    shiro 安全框架详细教程 总结内容 一.RBAC 的概念 二.两种常用的权限管理框架 1. Apache Shiro 2. Spring Security 3. Shiro 和 Spring Se ...

  3. shiro安全框架

    原文:http://blog.csdn.net/boonya/article/details/8233303 可能大家早先会见过 J-security,这个是 Shiro 的前身.在 2009 年 3 ...

  4. Shiro 核心功能案例讲解 基于SpringBoot 有源码

    Shiro 核心功能案例讲解 基于SpringBoot 有源码 从实战中学习Shiro的用法.本章使用SpringBoot快速搭建项目.整合SiteMesh框架布局页面.整合Shiro框架实现用身份认 ...

  5. thymeleaf模板引擎shiro集成框架

    shiro权限框架.前端验证jsp设计.间tag它只能用于jsp系列模板引擎. 使用最近项目thymeleaf作为前端模板引擎,采用HTML档,未出台shiro的tag lib,假设你想利用这段时间s ...

  6. shiro权限框架(一)

    不知不觉接触shiro安全框架都快三个月了,这中间配合项目开发踩过无数的坑.现在回想总结下,也算是一种积累,一种分享.中间有不够完美的地方或者不好的地方,希望大家指出来能一起交流.在这里谢谢开涛老师的 ...

  7. Shiro安全框架【快速入门】就这一篇!

    Shiro 简介 照例又去官网扒了扒介绍: Apache Shiro™ is a powerful and easy-to-use Java security framework that perfo ...

  8. SpringBoot集成Shiro安全框架

    跟着我的步骤:先运行起来再说 Spring集成Shiro的GitHub:https://github.com/yueshutong/shiro-imooc 一:导包 <!-- Shiro安全框架 ...

  9. Shiro权限框架简介

    http://blog.csdn.net/xiaoxian8023/article/details/17892041   Shiro权限框架简介 2014-01-05 23:51 3111人阅读 评论 ...

随机推荐

  1. 2019三六零 java面试笔试题 (含面试题解析)

    本人3年开发经验.18年年底开始跑路找工作,在互联网寒冬下成功拿到阿里巴巴.今日头条.360等公司offer,岗位是Java后端开发,最终选择去了三六零. 面试了很多家公司,感觉大部分公司考察的点都差 ...

  2. Grafana+prometheus+AlertManager+钉钉机器人

    一.Grafana (1)安装Grafana的Linux环境 在官网下载windows的Grafana的压缩包到指定目录,解压缩Grafana压缩文件到包含当前Grafana版本的文件夹.将该文件夹解 ...

  3. python3基础之“术语表(2)”

    51.编程: 让计算机执行的指令. 52.代码: 让计算机执行的命令. 53.底层编程语言: 与高级语言相比,更接近二进制的语言. 54.高级编程语言: 读起来像英语的易于理解的语言. 55.汇编语言 ...

  4. Oracle数据库之四大语言

    一.数据定义语言: 1.用于改变数据库结构,包括创建.更改和删除数据库对象: 2.命令: create table :创建 alter table 修改 drop table 删除表 truncate ...

  5. k8s资源清单基础

    资源清单介绍 创建资源的方法  apiserver仅接收JSON格式的资源定义  yaml格式提供配置清单 apiserver可自动把yaml转换成json格式数据 资源清单五个一级字段   1.ap ...

  6. MySQL5.7应当注意的参数

    简介: 本篇文章主要介绍 MySQL 初始化应当注意的参数,对于不同环境间实例迁移,这些参数同样应当注意. 注: 本文介绍的参数都是在配置文件 [mysqld] 部分. server_id 和 log ...

  7. day 09 预科

    目录 函数 定义函数 函数定义的三种形式 空函数 有参函数(有参数()的函数) 无参函数 函数的返回值 函数的参数 形参 位置形参 实参 位置实参 关键字实参 函数 def twoSum(nums,t ...

  8. Pycharm中连接数据库乱码问题解决

    当我们使用pycharm建立数据库之后,看到里面的数据都是乱码,就像下面一样: 其实这个并不是pycharm的显示问题,而是建立数据库时产生的. 解决方法是到指定字符集的命令提示符中重新建表并指定字符 ...

  9. Oracle Block Cleanouts 块清除

    当用户发出提交(commit)之后,oracle是需要写出redo来保证故障时数据可以被恢复,oracle并不需要在提交时就写出变更的数据块.由于在事务需要修改数据时,必须分配ITL事务槽,必须锁定行 ...

  10. Deprecated: Automatically populating $HTTP_RAW_POST_DATA is deprecated and will be removed in a future version. To avoid this warning set 'always_populate_raw_post_data' to '-1' in php.ini and use the

    参考链接 解决方法: 修改 php.ini  : always_populate_raw_post_data = -1 PHP 5.6已经废弃了$HTTP_RAW_POST_DATA