什么是授权?
- 即该用户是否有权限访问某个资源.(即校验权限)
Shiro权限的实现方式
1. 硬编码方式:实现授权访问校验.
- 在自定义中的realm中的授权方法中进行编写代码.
- 根据传进来的PrincipalCollection获取用户对象.
- 该授权方法的返回值是AuthorizationInfo,该对象是一个接口,因此我们需要创建它的实现类,SimpleAuthorizationInfo.
- 使用该类的方法
addRole 对应action 中的subject.checkRole方法.
/**
* 授权
*
* @param principalCollection
* @return
*/
@Override
protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principalCollection) {
User user = (User) principalCollection.getPrimaryPrincipal();
SimpleAuthorizationInfo sai = new SimpleAuthorizationInfo();
sai.addStringPermission("部门管理");
return sai;
}
复制代码
- 访问部门列表前需要进行权限校验
@Action(value = "deptAction_list")
public String toList() {
Subject subject = SecurityUtils.getSubject();
subject.checkPermission("部门管理");
return "toList";
}
复制代码
- 这里通过主体subject,提供用户的权限信息.并将用户的权限信息通过方法与Realm中的进行校验.
使用到的方法 | 区别 |
---|---|
subject.isPermitted() | 返回的是一个boolean,有权限则返回true,没有返回false.该方法需要我们自己处理没有权限后要处理的事 |
subject.checkPremission | 该方法如果没有权限会直接报错 |
以上的两个方法的作用是一样的,都是校验用户是否有权限访问资源.但第一个方法需要自己进行判断.第二个方法我们只需把异常处理了就可以了.
2. 过滤器配置(与Spring整合的配置文件中配置)
特点:权限校验是通过配置文件配置实现,因此权限校验与业务代码完全解耦.
-
在applicationContext-shiro.xml中的配置
-
格式为: 左边为需要进行权限校验的url 右边为perms[url所需要的权限]
/sysadmin/deptAction_list = perms[部门列表]
/** = authc
复制代码
如果该用户没有权限,会跳转到错误页面:
是因为在配置文件上我们配置了未授权的跳转页面
<!--未授权校验的页面-->
<property name="unauthorizedUrl" value="/login.jsp"/>
复制代码
<!--1. 创建shiroFilterFactoryBean-->
<bean id="shiroFilter" class="org.apache.shiro.spring.web.ShiroFilterFactoryBean">
<property name="securityManager" ref="securityManager"/>
<!--认证失败跳转的页面-->
<property name="loginUrl" value="/login.jsp"/>
<!--认证成功的页面.如果代码中指定了,以代码跳转的地址为准,通常会以登录成功跳转的页面为准-->
<property name="successUrl" value="/home.jsp"/>
<!--未授权校验的页面-->
<property name="unauthorizedUrl" value="/login.jsp"/>
<!--过滤器链-->
<property name="filterChainDefinitions">
<value>
/index.jsp* = anon
/home* = anon
/sysadmin/login/login.jsp* = anon
/sysadmin/login/loginAction_logout* = anon
/login* = anon
/logout* = anon
/components/** = anon
/css/** = anon
/img/** = anon
/js/** = anon
/plugins/** = anon
/images/** = anon
/js/** = anon
/make/** = anon
/skin/** = anon
/stat/** = anon
/ufiles/** = anon
/validator/** = anon
/resource/** = anon
/sysadmin/deptAction_list = perms[部门列表]
/** = authc
</value>
</property>
</bean>
复制代码
资源路径问题:如果第一位的过滤所匹配的资源路径为/**的话,因为/**匹配的是所有资源路径,所以下面的过滤器中的资源路径都不会再匹配了.只会执行第一个过滤器.因此配置资源路径为/**的过滤器一般放在过滤器链的最后.
注意:授权过滤器需要放在认证过滤器之前.否则会失效(资源路径为/**的情况下)
方式3:注解
使用shiro注解实现权限校验步骤:
- 开启注解支持
- 使用注解
根据官方文档说明,开启注解支持我们需要在shiro与Spring的配置文件中,配置三个Bean.
- 开启注解支持
<!--开启shiro授权校验注解支持-->
<bean id="lifecycleBeanPostProcessor" class="org.apache.shiro.spring.LifecycleBeanPostProcessor"/>
<bean class="org.springframework.aop.framework.autoproxy.DefaultAdvisorAutoProxyCreator"
depends-on="lifecycleBeanPostProcessor"/>
<bean class="org.apache.shiro.spring.security.interceptor.AuthorizationAttributeSourceAdvisor">
<property name="securityManager" ref="securityManager"/>
</bean>
复制代码
注意:这里使用到了depend-on,表示创建该对象需要depend-on的对象,因此在创建该对象之前先创建depend-on的对象,然后再创建当前对象.
- 使用注解(@RequiresPermissions)
注意:这个注解要定义到Service上.当使用struts注解开发的时候如果将shiro的注解写到action上会对struts有干扰.传入的service可能会有问题.如果想在action上使用shiro注解,那么使用struts.xml 配置文件来进行开发.
@RequiresPermissions("部门列表")
@Override
public Page<Dept> findAll(Specification<Dept> spec, Pageable pageable) {
return deptDao.findAll(spec, pageable);
}
复制代码
- 该种方式校验到用户没有该权限访问资源,不会报错而是以下的这种效果:
方式4 :shiro的自定义标签
使用前需要把标签库导入
<%@ taglib prefix="shiro" uri="http://shiro.apache.org/tags" %>
复制代码
- 使用案列:
<shiro:hasPermission name="">这个标签会去到我们自定义的Realm中进行权限的校验.匹配我们name的值与Realm中的值
<%@ taglib prefix="shiro" uri="http://shiro.apache.org/tags" %>
<html>
<head>
<title>Title</title>
</head>
<script type="text/javascript" src="${ctx}/js/jquery-1.11.3.min.js"></script>
<body>
<shiro:hasPermission name="部门列表">
<a href="#">部门列表</a> <br>
</shiro:hasPermission>
<shiro:hasPermission name="删除部门">
<a href="#">删除部门</a> <br>
</shiro:hasPermission>
<shiro:hasPermission name="添加部门">
<a href="#">添加部门</a> <br>
</shiro:hasPermission>
<shiro:hasPermission name="修改部门">
<a href="#">修改部门</a> <br>
</shiro:hasPermission>
</body>
</html>
复制代码
这种方式多用于Jsp页面上.用于动态的显示菜单.
总结:
- 在Service上面使用的shiro的授权方式:硬编码,注解.
- 在Action上面使用的shiro的授权方式:
-
如果开发使用的是struts.xml的配置文件, 并且没有引入struts注解开发支持包,action上做权限校验可以使用硬编码,注解,过滤器.
-
如果开发使用的是struts注解开发支持包,action上做权限校验可以使用硬编码,过滤器.
- 在JSp上的权限校验:使用第四种方式,使用shiro的自定义标签