1.什么是Shiro

Shiro是Java的一个安全框架, 完成权限控制的任务.

权限控制的基本功能: 认证(让系统知道你是谁); 授权(让系统知道你能做什么)
权限控制常用的技术: 过滤器/拦截器, 或者使用代理模式
权限控制的数据模型: 权限表-(多对多)-角色表-(多对多)-用户表

shiri的组成

shiro的调用流程

Application code:应用程序代码
Subject:当前用户
SecurityManager:安全管理器,shiro框架的核心对象,管理各个组件
Realm:获取权限信息, 决定subject的访问权限, 可以有多个

2.Shiro的使用

2.1登录

Subject subject = SecurityUtils.getSubject();
UsernamePasswordToken token = new UsernamePasswordToken(username, password);
try{
// 注意:登录不成功以抛异常的方式通知
subject.login(token);
}catch (UnknownAccountException e) {
// 没找到用户名
}catch (IncorrectCredentialsException e) {
// 用户名密码不匹配
}catch (AuthenticationException e) {
// 其他登录错误
}
if (subject.isAuthenticated()) {
// 登录成功后, 取回认证时通过签名存储的对象
User user = (User) subject.getPrincipal();
}

2.2 在realm里管理用户~权限

public class MyRealm extends AuthorizingRealm {

  // 登录及认证
@Override
protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken token) throws AuthenticationException {
// 获得登录用的token
UsernamePasswordToken token = (UsernamePasswordToken) token;
// 获得封装的username
String username = token.getUsername();
User user = userDao.findByUsername(username);
if (null == user) {
return null;
} else {
// 获得真正的password
String password = user.getPassword();
// 创建简单认证对象, 返回给安全管理器
// 参数一:可放入任何对象的签名, 执行subject.login()方法后可从subject.getPrincipal()取回
// 参数二:封装真正的密码, 交由安全管理器比对
// 参数三:当前realm的名称
SimpleAuthenticationInfo info = new SimpleAuthenticationInfo(user, password, this.getClass().getSimpleName());
return info;
}
} // 授权
@Override
protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principals) {
// 获得签名, 可做进一步查询
User user = (User) principals.getPrimaryPrincipal(); // 创建简单授权对象
SimpleAuthorizationInfo info = new SimpleAuthorizationInfo();
//授予perms["keyword"]
info.addStringPermission("staff");
//授予role["keyword"]
info.addRole("staff"); return info;
}
}

2.3 配置及管理访问目标~权限

2.3.1 过滤器方式:

web.xml

  <!-- shiro过滤器, 从spring工厂拿, beanname为"shiroFilter" -->
<filter>
<filter-name>shiroFilter</filter-name>
<filter-class>org.springframework.web.filter.DelegatingFilterProxy</filter-class>
</filter>
<filter-mapping>
<filter-name>shiroFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>

applicationContext.xml

  <!-- shiro: 自定义的realm -->
<bean id = "userDefineRealm" class="com.zx.bos.shiro.UserDefineRealm"></bean> <!-- 二级缓存-->
<bean id="ehCacheManager" class="org.apache.shiro.cache.ehcache.EhCacheManager">
<property name="cacheManagerConfigFile" value="classpath:ehcache.xml"></property>
</bean> <bean id="securityManager" class="org.apache.shiro.web.mgt.DefaultWebSecurityManager">
<!-- realm需注册给安全管理器 -->
<property name="realm" ref = "userDefineRealm"></property>
<!-- 使用ehcache二级缓存, 没必要频繁查询权限 -->
<property name="cacheManager" ref="ehCacheManager"></property>
</bean> <!-- shiro使用方式1, 对URL进行控制 -->
<bean id = "shiroFilter" class = "org.apache.shiro.spring.web.ShiroFilterFactoryBean">
<!-- 注入安全管理器 -->
<property name="securityManager" ref="securityManager"></property>
<!-- 未登录时跳转到登录页面 -->
<property name="loginUrl" value="/login.jsp"/>
<!-- 登录成功页面 -->
<property name="successUrl" value="/index.jsp"/> <!-- 登录后跳转到登陆前被拦截的页面, 不跳转至此 -->
<!-- 权限不足提示页面 -->
<property name="unauthorizedUrl" value="/unauthorizedUrl.jsp"/>
<!-- URL拦截规则 --> <!-- 有先后顺序 从上往下匹配 -->
<property name="filterChainDefinitions">
<value>
/css/** = anon
/images/** = anon
/js/** = anon
/login.jsp* = anon <!-- 后面带参数 -->
/validatecode.jsp* = anon
          /page_base_staff.action = roles["staff"]
/userAction_login.action = anon
/* = authc
</value>
</property>
</bean>

anon:可以匿名使用。
authc:需要认证(登录)才能使用
roles:可以带参数, 参数可以多个,例如roles["admin,guest"], 表示每个参数都通过才算通过
perms:可以带参数, 参数可以多个,perms["user:add:*,user:modify:*"]
port:port[8081]表示当请求的url的端口不是8081时跳转到schema://serverName:8081?queryParams
user:必须存在用户,登录操作时不做检查

2.3.2 注解方式:

    <!-- shiro使用方式2, 使用注解对方法进行控制. 不同于url方式权限不足时跳转界面,它直接抛出异常 -->
<!-- 代理 -->
<bean class="org.springframework.aop.framework.autoproxy.DefaultAdvisorAutoProxyCreator">
<property name="proxyTargetClass" value="true"></property> <!-- 使用cglib创建代理对象, 默认false用jdk动态代理 -->
</bean>
<!-- 切面类 -->
<bean class="org.apache.shiro.spring.security.interceptor.AuthorizationAttributeSourceAdvisor">
<property name="securityManager" ref="securityManager"/>
</bean>

注意捕获权限不足时抛出的异常. 如果在struts里需要配置

struts.xml

<global-results>
<result name="unauthorizedUrl">/unauthorizedUrl.jsp</result>
</global-results>
<!-- 接收异常 -->
<global-exception-mappings>
<exception-mapping result="unauthorizedUrl" exception="org.apache.shiro.authz.AuthorizationException"></exception-mapping>
</global-exception-mappings>
例如:
@RequiresRoles("rolename");
void someMethod();
@RequiresPermissions({"file:read", "write:aFile.txt"});
void someMethod();
最后说一遍, 需要处理可能的AuthorizationException异常
 
注解方式是在方法级别的控制,无法做类级别的控制访问。
过滤器方式是根据访问的URL进行控制。允许使用*通配URL,所以可以进行粗粒度,也可以进行细粒度控制。
 

2.4 在JSP页面使用shiro标签

使用shiro标签, 根据权限过滤部分内容
 
<shiro:authenticated>      登录之后
<shiro:notAuthenticated> 没有登录
<shiro:hasRole name="abc">     拥有角色abc
<shiro:lacksRole name="abc">   没有角色abc
<shiro:hasPermission name="abc">    拥有权限资源abc
<shiro:lacksPermission name="abc">  没有abc权限资源
<shiro:principal>   取回签名对象

Shiro快速入门的更多相关文章

  1. Apache Shiro 快速入门教程,shiro 基础教程

    第一部分 什么是Apache Shiro     1.什么是 apache shiro :   Apache Shiro是一个功能强大且易于使用的Java安全框架,提供了认证,授权,加密,和会话管理 ...

  2. Shiro学习总结(2)——Apache Shiro快速入门教程

    第一部分 什么是Apache Shiro 1.什么是 apache shiro : Apache Shiro是一个功能强大且易于使用的Java安全框架,提供了认证,授权,加密,和会话管理 如同 spr ...

  3. Apache Shiro 快速入门教程,shiro 基础教程 (这篇文章非常好)

    第一部分 什么是Apache Shiro     1.什么是 apache shiro :   Apache Shiro是一个功能强大且易于使用的Java安全框架,提供了认证,授权,加密,和会话管理 ...

  4. shiro 快速入门详解。

    package com.aaa.lee.shiro; import org.apache.shiro.SecurityUtils; import org.apache.shiro.authc.*; i ...

  5. Shiro第四篇【Shiro与Spring整合、快速入门、Shiro过滤器、登陆认证】

    Spring与Shiro整合 导入jar包 shiro-web的jar. shiro-spring的jar shiro-code的jar 快速入门 shiro也通过filter进行拦截.filter拦 ...

  6. Shiro官方快速入门10min例子源码解析框架2-Session

    Shiro自身维护了一套session管理组件,它可以独立使用,并不单纯依赖WEB/Servlet/EJB容器等环境,使得它的session可以任何应用中使用. 2-Session)主要介绍在quic ...

  7. Spring Boot:快速入门教程

    什么是Spring Boot? Spring Boot是由Pivotal团队提供的全新框架,其设计目的是用来简化新Spring应用的初始搭建以及开发过程.该框架使用了特定的方式来进行配置,从而使开发人 ...

  8. Web Api 入门实战 (快速入门+工具使用+不依赖IIS)

    平台之大势何人能挡? 带着你的Net飞奔吧!:http://www.cnblogs.com/dunitian/p/4822808.html 屁话我也就不多说了,什么简介的也省了,直接简单概括+demo ...

  9. SignalR快速入门 ~ 仿QQ即时聊天,消息推送,单聊,群聊,多群公聊(基础=》提升)

     SignalR快速入门 ~ 仿QQ即时聊天,消息推送,单聊,群聊,多群公聊(基础=>提升,5个Demo贯彻全篇,感兴趣的玩才是真的学) 官方demo:http://www.asp.net/si ...

随机推荐

  1. python中decorator的用法及原理(一)

    0. 概念 什么叫装饰器,其实也可以叫做包装器.即对于一个既有的函数func(args),在调用它之前和之后,我们希望都做一些事情,把这个函数包装起来. Python中的装饰器分为两类:函数装饰器和类 ...

  2. MTK平台环境搭建---Ubuntu Linux 下执行sudo apt-get install提示“现在没有可用的软件包……

    问题描述: sudo apt-get install openssh-server 正在读取软件包列表... 完成正在分析软件包的依赖关系树 Reading state information... ...

  3. 关于shared pool的深入探讨(三)

    基本命令: ALTER SESSION SET EVENTS 'immediate trace name LIBRARY_CACHE level LL'; 其中LL代表Level级别,对于9.2.0及 ...

  4. Python HTML Resolution Demo - SGMLParser & PyQuery

    1. SGMLParser: 这里定义了一个Parse类,继承SGMLParser里面的方法.使用一个变量is_h4做标记判定html文件中的h4标签,如果遇到h4标签,则将标签内的内容加入到Pars ...

  5. 浅谈 JS 内存泄露方式与避免方法(二)

    Concept WHAT : 内存泄露是指一块被分配的内存既不能使用,又不能回收,直到浏览器进程结束.正常情况下,垃圾回收器在DOM元素和event处理器不被引用或访问的时候回收它们.但是,IE的早些 ...

  6. Python(文件处理)

    二.基本操作 #r''------------------>> r:原生字符串,不判断符号的含义#文件处理 f=open(r’c:\a.txt’,’r’,encoding=’utf-8’) ...

  7. linq中将int类型转换为string类型,toString()报错

    今天同事在调试程序的时候,报了一个不寻常的错误, “LINQ to Entities 不识别方法"System.String ToString()",因此该方法无法转换为存储表达式 ...

  8. js验证真实姓名

    var regName = /^[\u4e00-\u9fa5]{2,4}$/; if (!regName.test(examinee.name)) { wx.showToast({ title: &q ...

  9. MAC brew软件安装

    之前一直怀念ubuntu下的apt-get,因为实在是方便,需要安装什么,一个命令搞定,相关的依赖包统统由apt-get维护.下载,编译,安装,那叫一个痛快.什么软件用着不爽,一个命令卸载! 怀念ap ...

  10. HDU - 2819 Swap (二分图匹配-匈牙利算法)

    题意:一个N*N的01矩阵,行与行.列与列之间可以互换.要求变换出一个对角线元素全为1的矩阵,给出互换的行号或列号. 分析:首先一个矩阵若能构成对角线元素全为1,那么矩阵的秩为N,秩小于N的情况无解. ...