shiro与erp系统整合
目的
1.认证:登陆了系统才有访问资源的资格(authentication)
2.授权:登陆后的用户具有访问某个资源的资格(authorization)
举个栗子:
我们出游买火车票,只有手持火车票你才有登陆火车的资格(用户登陆进系统才有访问资源的资格),而你手持火车票虽然能够登陆火车,但是你通宵抢票也才抢到一张站票,而不是卧票,你想去卧铺是不可能的(这就相当于你登陆系统但是没有被授权访问某个资源的资格)。权限验证
拦截url请求,判断是否登陆或有访问某个资源的权限shiro内置过滤器
anon | org.apache.shiro.web.filter.authc.AnonymousFilter |
---|---|
authc | org.apache.shiro.web.filter.authc.FormAuthenticationFilter |
authcBasic | org.apache.shiro.web.filter.authc.BasicHttpAuthenticationFilter |
perms | org.apache.shiro.web.filter.authz.PermissionsAuthorizationFilter |
port | org.apache.shiro.web.filter.authz.PortFilter |
rest | org.apache.shiro.web.filter.authz.HttpMethodPermissionFilter |
roles | org.apache.shiro.web.filter.authz.RolesAuthorizationFilter |
ssl | org.apache.shiro.web.filter.authz.SslFilter |
user | org.apache.shiro.web.filter.authc.UserFilter |
我们只用到其中的三个:
认证过滤器:anon(不认证也可以访问),authc(必须认证才能访问)
授权过滤器:perms(指定哪些资源需要授权才能访问)
- 在web.xml配置
<filter>
<filter-name>shiroFilter</filter-name>
<filterclass>
org.springframework.web.filter.DelegatingFilterProxy
</filter-class>
</filter>
<filter-mapping>
<filter-name>shiroFilter</filter-name>
<url-pattern>*.action</url-pattern>
<url-pattern>*.html</url-pattern>
<url-pattern>*</url-pattern>
</filter-mapping>
配置在struts2前openSessionInView后,如果放在openSessionInView的前面会报sessionclose的错,如果放在struts2后,别人都进去了你还拦个什么。
- 配置applicationContext_shiro.xml
<?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">
<!-- shiroFitler id要与web.xml中那代理的filter-name一致 -->
<bean id="shiroFilter" class="org.apache.shiro.spring.web.ShiroFilterFactoryBean">
<!-- 安全管理器: shiro核心大脑,认证和授权,会话,缓存。。。。 -->
<property name="securityManager" ref="securityManager" />
<!-- 使用自定义的过滤器 -->
<property name="filters">
<map>
<!-- 如果key值与默认的过滤的名称相同时,会替换掉过滤器 -->
<entry key="perms" value-ref="myPerms"></entry>
</map>
</property>
<!-- 如果用户没有登陆,就跳转到登陆页面 -->
<property name="xxxUrl" value="/lxxx.html" />
<!-- 如果用户没有权限,就跳转到报错页面 -->
<property name="xxxUrl" value="/xxx.html" />
<!-- 过滤链:拦截规则 -->
<property name="filterChainDefinitions">
<value>
#1. anon 匿名
#2. perms 授权
#3. authc 认证
/xxx.html = anon
/xxx.html=perms
/xxx.html=authc
</value>
</property>
</bean>
<!-- 安全管理器 -->
<bean id="securityManager" class="org.apache.shiro.web.mgt.DefaultWebSecurityManager">
<property name="realm" ref="xxxRealm"></property>
</bean>
<bean id="erpRealm" class="cn.itcast" >
<property name="xxxBiz" ref="xxxBiz"></property>
<property name="jedis" ref="jedis"></property>
</bean>
<bean id="myPerms" class="cn.itcast.erp.filter.MyAuthorizationFilter"></bean>
<!-- 启动shiro注解 -->
<bean class="org.springframework.aop.framework.autoproxy.DefaultAdvisorAutoProxyCreator"
depends-on="lifecycleBeanPostProcessor" >
<!-- 默认使用JDK代理 ,如被代理类没有实现接口,必须使用下列配置开启 cglib代理 -->
<property name="proxyTargetClass" value="true" />
</bean>
<bean class="org.apache.shiro.spring.security.interceptor.AuthorizationAttributeSourceAdvisor">
<property name="securityManager" ref="securityManager" />
</bean>
<!-- 对安全管理器 增强代码 , spring 后处理器 -->
<bean id="lifecycleBeanPostProcessor" class="org.apache.shiro.spring.LifecycleBeanPostProcessor"/>
</beans>
- 在登陆方法创建令牌
//创建令牌
UsernamePasswordToken upt=new UsernamePasswordToken(username,password);
//当事者,当前使用对象
Subject subject = SecurityUtils.getSubject();
- 自定义Realm
Realm:一个安全相关的dao,封装这数据源连接细节,当shiro需要时提供给shrio。
为什么要自定义:改用方法后,不会对登陆的业务层进行验证查询,也不会去数据库校对用户名密码,而是把这个工作交给shiro进行,所以需要调用Realm。
创建一个类继承AuthorizingRealm即可。
- 修改认证