导入依赖
代码语言:javascript复制<!--shiro整合Spring-->
<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>
web.xml中配置如下:
代码语言:javascript复制<!-- Shiro Security filter filter-name这个名字的值将来还会在spring中用到-->
<filter>
<filter-name>shiroFilter</filter-name>
<filter-class>org.springframework.web.filter.DelegatingFilterProxy</filter-class>
<init-param>
<!-- 过滤器的生命周期交给了spring管理-->
<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>
Spring 配置文件中添加如下
我在web.xml中加载配置是这样写的:<param-value>classpath*:spring/applicationContext-*.xml</param-value>
我的spring配置文件是分开的叫: 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" xmlns:aop="http://www.springframework.org/schema/aop"
xsi:schemaLocation="
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd">
<!-- 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>
<!-- 未登录时也能访问 /login.jsp页面-->
/login.jsp = anon
/css/** = anon
/img/** = anon
/plugins/** = anon
/make/** = anon
/favicon.ico= anon
/login.do = anon
<!-- 当前登录人一定要有“企业管理”权限才能进入到 /company/list.do的方法中-->
/company/list.do = perms["权限管理"]
/systems/module/list.do = perms["模块管理"]
/systems/role/list.do = perms["角色管理"]
/systems/user/list.do = perms["用户管理"]
/systems/log/list.do = perms["日志管理"]
<!-- 所有剩余的资源必须登录后才能访问-->
/** = authc
</value>
</property>
</bean>
<!-- 引用自定义的realm -->
<bean id="SsmRealm" class="cn.itcast.realm.SsmRealm"/>
<bean id="securityManager" class="org.apache.shiro.web.mgt.DefaultWebSecurityManager">
<property name="realm" ref="SsmRealm"/>
</bean>
<!-- 安全管理器 -->
<bean class="org.apache.shiro.spring.security.interceptor.AuthorizationAttributeSourceAdvisor">
<property name="securityManager" ref="securityManager"/>
</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>
<aop:aspectj-autoproxy proxy-target-class="true"/>
</beans>
自定义realm
- 认证方法返回null,会报异常的
import cn.itcast.domain.system.Module;
import cn.itcast.domain.system.User;
import cn.itcast.service.system.ModuleService;
import cn.itcast.service.system.UserService;
import org.apache.shiro.authc.*;
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 org.springframework.beans.factory.annotation.Autowired;
import java.util.List;
public class SsmRealm extends AuthorizingRealm {
@Autowired //注入UserService
private UserService userService;
@Autowired//注入ModuleService
private ModuleService moduleService;
//认证方法返回null,会报异常的
//授权
@Override
protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principalCollection) {
System.out.println(">>>>>>>>>>>>>>>>>>>>>>>授权方法 ");
//告诉shiro框架 当前登录人有哪些菜单权限
System.out.println("------进入了授权方法AuthorizationInfo");
//AuthorizationInfo是接口,返回它的实现类 SimpleAuthorizationInfo
SimpleAuthorizationInfo authorizationInfo = new SimpleAuthorizationInfo();
//获得主题对象类
User user = (User) principalCollection.getPrimaryPrincipal();
//根据用户查询所拥有的菜单权限
List<Module> moduleList = moduleService.findModuleListByUser(user);
for (Module module : moduleList) {
authorizationInfo.addStringPermission(module.getCpermission());
}
return authorizationInfo;
}
//认证
@Override
protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken authenticationToken) throws AuthenticationException {
System.out.println(">>>>>>>>>>>>>>>>>>>>>>>认证方法 ");
//获取 UsernamePasswordToken
UsernamePasswordToken token = (UsernamePasswordToken) authenticationToken;
//获取令牌中的 邮箱和密码
String email = token.getUsername();
String password = new String(token.getPassword());
//根据邮箱查询数据
User user = userService.findByEmail(email);
//如果查询有结果,那么比较密码是否一致
if (user != null){
//一致向下继续走
if (!user.getPassword().equals(password)){
//不相等就返回 null
return null;
}
}else {
//查询无结果,返回null
return null;
}
//Object principal 主角, Object credentials 加密后的密码, String realmName 当前类名
return new SimpleAuthenticationInfo(user,password,getName());
}
}
Realm交给容器并且受securityManager的管理
在spring配置文件中加入:
代码语言:javascript复制<!-- 引用自定义的realm-->
<bean id="saasRealm" class="cn.itcast.realm.SaasRealm"/>
<bean id="securityManager" class="org.apache.shiro.web.mgt.DefaultWebSecurityManager">
<property name="realm" ref="saasRealm"/>
</bean>