shiro权限框架
权限的组成部分:用户 资源 角色 权限
数据库关系表设计是根据自己项目需求设计的
account表
role表(id,rolename)
account_role(id,aid,rid)
permission(id,pername)
role_permission(id,rid,pid)
没有设置用户和权限的关系,我们可以认为用户的权限是通过角色来决定的
1.导入jar包
shiro-all-1.2.1.jar
2.配置web.xml
<!-- 权限过滤器-->
<filter>
<filter-name>shiroFilter</filter-name>
<!-- 委托给spring,所以还要在spring中配置 -->
<filter-class>org.springframework.web.filter.DelegatingFilterProxy</filter-class>
</filter>
<filter-mapping>
<filter-name>shiroFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
3.新建applicationContext-shiro.xml
因为在web.xml中有配置spring容器,它会读取applicationContext开头的配置文件
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:applicationContext*.xml</param-value>
</context-param>
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"
>
<bean id="securityManager" class="org.apache.shiro.web.mgt.DefaultWebSecurityManager">
<property name="cacheManager" ref="cacheManager"/>
<!-- 权限框架的操作类 myShiroRealm,可以service中新建这个类-->
<property name="realm" ref="myShiroRealm"/>
</bean> <bean id="shiroFilter" class="org.apache.shiro.spring.web.ShiroFilterFactoryBean">
<property name="securityManager" ref="securityManager"/> <!-- 以下是跟登录权限有关的配置 --> <!-- 配置登录的url -->
<property name="loginUrl" value="/"/>
<!-- 登录成功的url -->
<property name="successUrl" value="/book/1"/>
<!-- 没有权限的url -->
<property name="unauthorizedUrl" value="/403"/> <property name="filterChainDefinitions">
<value> <!-- 静态资源不用认证 要放在/** = authc之前,因为当所有的都要认证的时候再写它就没用了-->
/static/** = anon
<!-- 角色配置,没有管理员这个角色的账户是不能访问/book/**里面的内容的 -->
/book/** = roles[管理员]
<!-- 权限配置,不要只在界面上用标签配置 没有book:add的权限的账户是不能访问/book/add的
但是如果没有权限你还是要访问的话,就要到上面的<property name="unauthorizedUrl" value="/403"/>
里面了,自定义一个403页面,这里举出一个例子,可以在mvc-servlet配置静态资源
<mvc:view-controller path="/403" view-name="403"/>-->
/book/add = perms[book:add] <!-- (根目录及其子目录)所有的资源都是需要认证的 这个时候以前mvc-servlet里面的拦截器就不用写了-->
/** = authc
</value>
</property>
</bean> <bean id="cacheManager"
class="org.apache.shiro.cache.MemoryConstrainedCacheManager" />
<bean id="lifecycleBeanPostProcessor"
class="org.apache.shiro.spring.LifecycleBeanPostProcessor" /> </beans>
举例
package com.kaishengit.service; import javax.inject.Inject;
import javax.inject.Named; import org.apache.shiro.authc.AuthenticationException;
import org.apache.shiro.authc.AuthenticationInfo;
import org.apache.shiro.authc.AuthenticationToken;
import org.apache.shiro.authc.SimpleAuthenticationInfo;
import org.apache.shiro.authc.UsernamePasswordToken;
import org.apache.shiro.authz.AuthorizationInfo;
import org.apache.shiro.authz.SimpleAuthorizationInfo;
import org.apache.shiro.realm.AuthorizingRealm;
import org.apache.shiro.subject.PrincipalCollection; import com.kaishengit.pojo.Admin; // 需要继承自AuthorizingRealm并实现它的方法
@Named
public class MyShiroRealm extends AuthorizingRealm{ @Inject
private AdminService adminService; /**
* 权限认证方法
*/
@Override
protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection pCollection) {
//获取当前登录的用户名
String loginName = (String) pCollection.fromRealm(getName()).iterator().next(); Admin admin = adminService.findByName(loginName);
if(admin != null) {
SimpleAuthorizationInfo sInfo = new SimpleAuthorizationInfo();
//1. 获取当前用户拥有的所有角色
sInfo.setRoles(adminService.getRoles(admin));
/* adminService中的该方法
public Set<String> getRoles(Admin admin) {
List<Role> roles = roleDao.findByAdminId(admin.getId());
因为是要返回的set集合
Set<String> roleNames = new HashSet<String>(); for(Role r : roles) {
roleNames.add(r.getRolename());
}
return roleNames;
}*/ //2. 获取当前用户拥有的所有权限
// 还有一个方法,跟下面的不同的是set第二次会覆盖,add表示添加
//sInfo.addStringPermissions(adminService.getPermissions(admin));
sInfo.setStringPermissions(adminService.getPermissions(admin)); /* adminService中的该方法
public Set<String> getPermissions(Admin admin) {
一个账户可能有多个角色
List<Role> roles = roleDao.findByAdminId(admin.getId()); Set<String> permissions = new HashSet<String>(); for(Role role : roles) {
一个角色可能有多个权限
List<Permission> perList = permissionDao.findByRoleId(role.getId());
for(Permission p : perList) {
装入set集合
permissions.add(p.getPername());
}
}
return permissions;
}
*/
return sInfo;
} return null;
} /**
* 登录认证方法
*/
@Override
protected AuthenticationInfo doGetAuthenticationInfo(
AuthenticationToken auToken) throws AuthenticationException {
// 强制转换
UsernamePasswordToken token = (UsernamePasswordToken) auToken;
// 通过名字查询,用的是token.getUsername,那这个名字是从哪里放进来的呢,是在controller中new出来
// 的token,然后传进去的账户信息,然后在这里get
Admin admin = adminService.findByName(token.getUsername()); if(admin != null) {
// 如果查询得到一个admin就算登录成功 ,因为下面的构造函数会传入账户和密码,然后自动检测
return new SimpleAuthenticationInfo(admin.getName(),admin.getPassword(),getName());
}
return null;
} }
@Controller
public class AdminController { @Inject
private AdminService adminService; @RequestMapping(value="/",method=RequestMethod.POST)
public String login(Admin admin,HttpSession session,RedirectAttributes redirectAttributes) { try {
/* 在这里new出来 UsernamePasswordToken,传入账户信息
当在这里调用login的时候就会自动调用MyShiroRealm中登录认证的那个方法 这个方法是不会抛出异常的,但是我们还是要try catch一下,因为这个方法不能做判断
所以当来到catch的时候就说明登录失败了*/
SecurityUtils.getSubject().login(new UsernamePasswordToken(admin.getName(), admin.getPassword()));
return "redirect:/book/1";
} catch (AuthenticationException e) {
redirectAttributes.addFlashAttribute("message", "账号或密码错误");
return "redirect:/";
} /*
这是以前的方法
Admin currAdmin = adminService.login(admin.getName(),admin.getPassword());
if(currAdmin == null) {
redirectAttributes.addFlashAttribute("message", "账号或密码错误");
return "redirect:/";
} else {
session.setAttribute("curr_admin", currAdmin);
return "redirect:/book";
}*/
} }
jsp中对应的标签
首先导入标签
<%@ taglib prefix="shiro" uri="http://shiro.apache.org/tags" %>
<!-- 该账户有的角色中存在权限 book:add权限的话就能添加书籍-->
<shiro:hasPermission name="book:add">
<a href="/book/add" class="btn btn-success">添加书籍</a>
</shiro:hasPermission> <table class="table">
<thead>
<tr>
<th>书籍编号</th>
<th>书籍名称</th>
<th>作者</th>
<th>出版社</th>
<th>总数量</th>
<th>当前数量</th>
<th>#</th>
</tr>
</thead>
<tbody> <c:forEach items="${bookList }" var="book">
<tr>
<td>${book.code }</td>
<td>${book.name }</td>
<td>${book.author }</td>
<td>${book.publish }</td>
<td>${book.total}</td>
<td>${book.nowcount }</td>
<td>
<shiro:hasPermission name="book:edit">
<a href="/book/edit/${book.id }">修改</a>
</shiro:hasPermission>
<shiro:hasPermission name="book:remove">
<a href="/book/del/${book.id }">删除</a>
</shiro:hasPermission>
</td>
</tr>
</c:forEach>
</tbody>
</table>
这个标签只是在界面上控制不让它显示,但是如果在url上直接进入还是控制不住的,所以要在
applicationContext-shiro.xml 配置,见上...
shiro权限框架的更多相关文章
- Shiro权限框架简介
http://blog.csdn.net/xiaoxian8023/article/details/17892041 Shiro权限框架简介 2014-01-05 23:51 3111人阅读 评论 ...
- 在前后端分离的SpringBoot项目中集成Shiro权限框架
参考[1].在前后端分离的SpringBoot项目中集成Shiro权限框架 参考[2]. Springboot + Vue + shiro 实现前后端分离.权限控制 以及跨域的问题也有涉及
- (转) shiro权限框架详解06-shiro与web项目整合(上)
http://blog.csdn.net/facekbook/article/details/54947730 shiro和web项目整合,实现类似真实项目的应用 本文中使用的项目架构是springM ...
- Apache Shiro权限框架在SpringMVC+Hibernate中的应用
在做网站开发中,用户权限必须要考虑的,权限这个东西很重要,它规定了用户在使用中能进行哪 些操作,和不能进行哪些操作:我们完全可以使用过滤器来进行权限的操作,但是有了权限框架之后,使用起来会非常的方便, ...
- Shiro 权限框架使用总结
我们首先了解下什么是shiro ,Shiro 是 JAVA 世界中新近出现的权限框架,较之 JAAS 和 Spring Security,Shiro 在保持强大功能的同时,还在简单性和灵活性方面拥有巨 ...
- SpringMVC整合Shiro权限框架
尊重原创:http://blog.csdn.net/donggua3694857/article/details/52157313 最近在学习Shiro,首先非常感谢开涛大神的<跟我学Shiro ...
- shiro权限框架(一)
不知不觉接触shiro安全框架都快三个月了,这中间配合项目开发踩过无数的坑.现在回想总结下,也算是一种积累,一种分享.中间有不够完美的地方或者不好的地方,希望大家指出来能一起交流.在这里谢谢开涛老师的 ...
- 关于Apache Shiro权限框架的一些使用误区的解释
多了不说了,进入正题,shiro是个权限框架提供权限管理等功能,网上的教程一般都是互相抄,比如<shiro:principal property="xxx"/>这个标签 ...
- SpringBoot整合Shiro权限框架实战
什么是ACL和RBAC ACL Access Control list:访问控制列表 优点:简单易用,开发便捷 缺点:用户和权限直接挂钩,导致在授予时的复杂性,比较分散,不便于管理 例子:常见的文件系 ...
随机推荐
- XMLTProcessor根据XSLT样式规则将节点转换为document对象
最近使用Firefox进行网页的调试,发现有些javascript XSLT处理xml的语句仅仅支持IE浏览器.而网络中的一些介绍Javascript XSLT 处理XML的文章基本上都是依据Ajax ...
- MinGW 编译zlib、libpng、libjpeg、libcurl等(全都是Qt项目)
MinGW 这里使用的是Qt5自带的MinGw版本,将路径D:\Qt\Qt5.1.0\Tools\mingw48_32\bin加到"环境变量"→"系统变量"→& ...
- 面试题:在O(1)时间删除链表结点
题目:给定单向链表的头指针和一个结点指针,定义一个函数在O(1)时间删除该结点. 链表结点与函数的定义如下: struct ListNode { int m_nValue; ListNode* m_p ...
- perl5 附录一 函数集(未定稿)
附录一 函数集(未定稿) by flamephoenix 一.进程处理函数 1.进程启动函数 2.进程终止函数 3.进程控制函数 4.其它控制函数二.数学函数三.字符串处理函数四.标量转换函数 ...
- CDLinux环境下WiFi密码破解
> 准备好所需软件以及上篇教程中使用Fbinstool制作的可启动U盘 2 > 解压CDLinux-0.9-spring-0412.iso到U盘的根目录 如图 3 > 打开fbin ...
- TEX Quotes(字符串,水)
TEX Quotes Time Limit: 1000MS Memory Limit: 10000K Total Submissions: 9674 Accepted: 5073 Descri ...
- Linux升级Python提示Tkinter模块找不到解决
一.安装tkinter 在Linux中python默认是不安装Tkinter模块, [root@li250- ~]# python Python (r266:, Feb , ::) [GCC (Red ...
- google chrome字体最小12px的问题
解决Google浏览器不支持12px以下的字体大小的问题,有时设定了12PX,可在浏览器看时确不起作用 网络出现内核的浏览器有微软的Internet Explorer, Mozilla的Firefox ...
- 如何在UILable上添加点击事件?
最近开始学习iOS开发,今天上来写第一个iOS笔记 昨天碰到一个需求,在UILable上添加点击事件,网上找了写资料,有人建议用透明的UIButton覆盖,有人建议写一个集成自UILable的类,扩展 ...
- 基于百度地图api + AngularJS 的入门地图
转载请注明地址:http://www.cnblogs.com/enzozo/p/4368081.html 简介: 此入门地图为简易的“广州大学城”公交寻路地图,采用很少量的AngularJS进行inp ...