shiro与spring的集成

一、认识

Spring中的security:重量级的安全框架、是细粒度的、功能很多

Apache中的Shiro:轻量级安全框架、是粗粒度,功能没有security多,但是也足够用了

二、shiro的四大基石

身份验证、授权、密码学、会话管理

三、shiro的架构

Submit:当前用户

Shiro securityManager:权限管理器、shiro的核心类、所有功能的核心

Realm:读取当前用户的信息、登录权限和角色

四、shiro与spring的集成

1.导包

 1 <!-- shiro的支持包 -->
 2         <dependency>
 3             <groupId>org.apache.shiro</groupId>
 4             <artifactId>shiro-all</artifactId>
 5             <version>1.4.0</version>
 6             <type>pom</type>
 7         </dependency>
 8         <!-- shiro与Spring的集成包 -->
 9         <dependency>
10             <groupId>org.apache.shiro</groupId>
11             <artifactId>shiro-spring</artifactId>
12             <version>1.4.0</version>
13         </dependency>

2.配置web.xml

<!-- Shiro的过滤器(拦截所有请求) -->
  <!--
      这个过滤器只过滤,它什么功能都没有! 它什么都不做!
        真正的过滤功能是在Spring中的过滤器完成的!!!
        名字很重要:必需和shiro.xml中的过滤器名称一样
   -->
  <filter>
    <filter-name>shiroFilter</filter-name>
    <filter-class>org.springframework.web.filter.DelegatingFilterProxy</filter-class>
    <init-param>
      <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>

3.准备自定义realm

 1 public class CRMRealm extends AuthorizingRealm {
 2 
 3     @Autowired
 4     private IEmployeeService employeeService;
 5     @Autowired
 6     private IPermissionService permissionService;
 7 
 8     @Override
 9     protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principalCollection) {
10         //获取主体
11         Employee employee = (Employee) principalCollection.getPrimaryPrincipal();
12         //获取权限
13         Set<String> perms = permissionService.findByUserId(employee.getId());
14 
15         //创建对象
16         SimpleAuthorizationInfo simpleAuthorizationInfo = new SimpleAuthorizationInfo();
17         simpleAuthorizationInfo.setStringPermissions(perms);
18         return simpleAuthorizationInfo;
19     }
20 
21     @Override
22     protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken authenticationToken) throws AuthenticationException {
23         //获取令牌
24         UsernamePasswordToken token = (UsernamePasswordToken) authenticationToken;
25         //获取用户名
26         String username = token.getUsername();
27         //通过用户名在数据库获取密码
28         Employee employee = employeeService.findByLoginUsername(username);
29         if(employee==null){
30             return null;
31         }
32         //创建对象
33         //盐值
34         ByteSource salt = ByteSource.Util.bytes("su");
35         SimpleAuthenticationInfo simpleAuthenticationInfo = new SimpleAuthenticationInfo(employee, employee.getPassword(), salt,getName());
36         return simpleAuthenticationInfo;
37     }

4.自定义拦截器

 1 public class FilterChainDefinitionMapBuilder {
 2     @Autowired
 3     private IPermissionService permissionService;
 4 
 5     public Map<String,String> createFilterChainDefinitionMap(){
 6         LinkedHashMap<String, String> filterChainDefinitionBuilderMap = new LinkedHashMap<>();
 7         //放行
 8         filterChainDefinitionBuilderMap.put("/static/**", "anon");
 9         filterChainDefinitionBuilderMap.put("/login.jsp", "anon");
10         filterChainDefinitionBuilderMap.put("/login/login", "anon");
11         filterChainDefinitionBuilderMap.put("/department/list", "anon");
12 
13         //拦截
14         List<Permission> perms = permissionService.findAll();
15         perms.forEach(e->{
16             //  perms 改成自定义拦截器的key aiSell
17             filterChainDefinitionBuilderMap.put(e.getUrl(), "aiSell["+e.getSn()+"]");
18         });
19 
20         filterChainDefinitionBuilderMap.put("/**", "authc");
21         return filterChainDefinitionBuilderMap;
22     }
23 }

5.重写ajax请求的返回值

 1 public class CRMPermissionsAuthorizationFilter extends PermissionsAuthorizationFilter {
 2 
 3     @Override
 4     protected boolean onAccessDenied(ServletRequest request, ServletResponse response) throws IOException {
 5         Subject subject = this.getSubject(request, response);
 6         if (subject.getPrincipal() == null) {
 7             this.saveRequestAndRedirectToLogin(request, response);
 8         } else {
 9             //到这表示你没有权限
10             //强转成我们需要的http
11             HttpServletRequest httpRequest = (HttpServletRequest) request;
12             HttpServletResponse httpResponse = (HttpServletResponse) response;
13             //2.请求头有X-Requested-With表示为ajax请求
14             String xRequestedWith = httpRequest.getHeader("X-Requested-With");
15             if ("XMLHttpRequest".equals(xRequestedWith)) {
16                 //3.在这里就代表是ajax请求
17                 //表示ajax请求 {"success":false,"message":"没有权限"}
18                 httpResponse.setContentType("application/json; charset=UTF-8");
19                 //注意print没有ln
20                 httpResponse.getWriter().print("{\"success\":false,\"msg\":\"还没有权限哦~\"}");
21             }else {
22                 String unauthorizedUrl = this.getUnauthorizedUrl();
23                 if (StringUtils.hasText(unauthorizedUrl)) {
24                     WebUtils.issueRedirect(request, response, unauthorizedUrl);
25                 } else {
26                     WebUtils.toHttp(response).sendError(401);
27                 }
28             }
29         }
30         return false;
31     }
32 }

6.配置applicationContex-shiro.xml

 1 <?xml version="1.0" encoding="UTF-8"?>
 2 <beans xmlns="http://www.springframework.org/schema/beans"
 3        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
 4        xsi:schemaLocation="
 5        http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd">
 6 
 7 
 8     <!--shiro的核心类-->
 9     <bean id="securityManager" class="org.apache.shiro.web.mgt.DefaultWebSecurityManager">
10         <property name="realm" ref="aiSellRealm"/>
11     </bean>
12 
13     <!--自定义realm-->
14     <bean id="aiSellRealm" class="cn.susu.web.shiro.CRMRealm">
15         <property name="credentialsMatcher">
16             <bean class="org.apache.shiro.authc.credential.HashedCredentialsMatcher">
17                 <property name="hashAlgorithmName" value="MD5"/>
18                 <property name="hashIterations" value="10"/>
19             </bean>
20         </property>
21 </bean>
22 
23     <!--支持注解权限判断-->
24     <bean id="lifecycleBeanPostProcessor" class="org.apache.shiro.spring.LifecycleBeanPostProcessor"/>
25     <bean class="org.springframework.aop.framework.autoproxy.DefaultAdvisorAutoProxyCreator"
26           depends-on="lifecycleBeanPostProcessor"/>
27     <bean class="org.apache.shiro.spring.security.interceptor.AuthorizationAttributeSourceAdvisor">
28         <property name="securityManager" ref="securityManager"/>
29     </bean>
30 
31     <!--shiro真正的过滤器  名字与web.xml中的一致-->
32     <bean id="shiroFilter" class="org.apache.shiro.spring.web.ShiroFilterFactoryBean">
33         <property name="securityManager" ref="securityManager"/>
34         <!--登录失败返回的页面-->
35         <property name="loginUrl" value="/index.jsp"/>
36         <!--登录成功返回的页面-->
37         <property name="successUrl" value="/department/index"/>
38         <!--登录成功后没有权限跳转的界面-->
39         <property name="unauthorizedUrl" value="/shiro/unauthorized.jsp"/>
40         <!--<property name="filterChainDefinitions">
41             <value>
42                 /s/login = anon
43                 /login=anon
44                 /employee/index = perms[employee:index]
45                 /** = authc
46             </value>
47         </property>-->
48         <property name="filterChainDefinitionMap" ref="filterChainDefinitionBuilderMap"></property>
49         <property name="filters">
50             <map>
51                 <!--/employee/index = aiSell[employee:index]-->
52                 <entry key="aiSell" value-ref="aiSellFilter"></entry>
53             </map>
54         </property>
55     </bean>
56     <!--自定义拦截器-->
57     <bean id="aiSellFilter" class="cn.susu.web.shiro.CRMPermissionsAuthorizationFilter"></bean>
58     <!--数据库查拦截权限-->
59     <bean id="filterChainDefinitionBuilderMap" factory-bean="filterChainDefinitionMapBuilder" factory-method="createFilterChainDefinitionMap"></bean>
60     <bean id="filterChainDefinitionMapBuilder" class="cn.susu.web.shiro.FilterChainDefinitionMapBuilder"></bean>
61 </beans>

猜你喜欢

转载自www.cnblogs.com/guangbin0125/p/10680612.html
今日推荐