ssm框架集成shiro管理用户登录------简单点

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/qq_37358860/article/details/89242495

ssm框架集成shiro管理用户登录------简单点

一. 首先你得有个ssm框架能够实现最简单的用户登录验证.

简单的maven构建ssm框架实现用户登录验证源码地址(maven3.5+jdk1.8)

二.将shiro集成到ssm框架中

  • 在pom.xml文件中添加shiro依赖
<!-- shiro start -->
<dependency>
	<groupId>org.apache.shiro</groupId>
	<artifactId>shiro-core</artifactId>
	<version>1.2.4</version>
</dependency>
<dependency>
	<groupId>org.apache.shiro</groupId>
	<artifactId>shiro-web</artifactId>
	<version>1.2.4</version>
</dependency>
<dependency>
	<groupId>org.apache.shiro</groupId>
	<artifactId>shiro-spring</artifactId>
	<version>1.2.4</version>
</dependency>
<dependency>
	<groupId>org.apache.shiro</groupId>
	<artifactId>shiro-ehcache</artifactId>
	<version>1.2.4</version>
</dependency>
<!-- shiro end -->
  • web.xml中配置shiro过滤器
<!-- 配置shiro的过滤器 -->
  <filter>
	<filter-name>shiroFilter</filter-name>
	<filter-class>org.springframework.web.filter.DelegatingFilterProxy</filter-class>
  </filter>
  <filter-mapping>
	<filter-name>shiroFilter</filter-name>
	<url-pattern>/*</url-pattern>
  </filter-mapping>
  • 在spring配置文件中配置shiro
<!-- 配置shiro框架的过滤器工厂bean -->
		<bean id="shiroFilter" class="org.apache.shiro.spring.web.ShiroFilterFactoryBean">
			<property name="securityManager" ref="securityManager" />
			<!-- 登录项目首次访问的地址 -->
			<property name="loginUrl" value="/index.jsp" />
			<property name="successUrl" value="/successUrl.jsp" />
			<property name="unauthorizedUrl" value="/unauthorizedUrl.jsp" />
			<!-- 指定URL拦截策略 ,静态资源放行,登录放行,其他的需要认证也就是登录-->
			<property name="filterChainDefinitions">
				<value>
					/index.jsp=anon
					/jsp/error.jsp=anon
					/login/loginPage.action=anon
					/**=authc
				</value>
			</property>
		</bean>
		<!-- 配置安全管理器 -->
		<bean id="securityManager" class="org.apache.shiro.web.mgt.DefaultWebSecurityManager">
			<property name="realm" ref="MyRealm" />
			<!-- 注入缓存管理器 -->
			<property name="cacheManager" ref="cacheManager" />
		</bean>
		<!-- 注册自定义realm -->
		<bean id="MyRealm"
			class="com.lgf.maven_ssm.shiro.MyRealm" />
		<!-- 注册缓存管理器 -->
		<bean id="cacheManager" class="org.apache.shiro.cache.ehcache.EhCacheManager">
			<!-- 注入ehcache配置文件 -->
			<property name="cacheManagerConfigFile" value="classpath:/ehcache_shiro.xml" />
		</bean>

安全管理器中的realm和cacheManager是我们自己配置的

  • 创建自定义realm类, MyRealm
package com.lgf.maven_ssm.shiro;

import javax.annotation.Resource;
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.realm.AuthorizingRealm;
import org.apache.shiro.subject.PrincipalCollection;
import com.lgf.maven_ssm.system.entity.CsdnUser;
import com.lgf.maven_ssm.system.service.ILoginService;



public class MyRealm extends AuthorizingRealm {

	@Resource
    private ILoginService loginService;
	
	@Override
	protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principals) {
		// TODO Auto-generated method stub
		return null;
	}

	@Override
	protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken token) throws AuthenticationException {
	 	UsernamePasswordToken userToken = (UsernamePasswordToken) token;
        CsdnUser user=loginService.getUserByName(userToken.getUsername());
        if (user != null){
            // 若存在,将此用户存放到登录认证 info 中,无需自己做密码对比,Shiro 会为我们进行密码对比校验
            return new SimpleAuthenticationInfo(user, user.getUserPassword(), getName());
        }
        return null;
	}
}

  • 创建shiro缓存的配置文件ehcache_shiro.xml
<?xml version="1.0" encoding="UTF-8"?>
<ehcache updateCheck="false" name="shiroCache">
    <!--
       name: 缓存名称。
       maxElementsInMemory: 缓存最大数目
       maxElementsOnDisk:硬盘最大缓存个数。
       eternal: 对象是否永久有效,一但设置了,timeout 将不起作用。
       overflowToDisk: 是否保存到磁盘,当系统当机时
       timeToIdleSeconds: 设置对象在失效前的允许闲置时间(单位:秒)。仅当 eternal=false 对象不是永久有效时使用,可选属性,默认值是 0,也就是可闲置时间无穷大。
       timeToLiveSeconds: 设置对象在失效前允许存活时间(单位:秒)。最大时间介于创建时间和失效时间之间。仅当 eternal=false 对象不是永久有效时使用,默认是 0.,也就是对象存活时间无穷大。
       diskPersistent:是否缓存虚拟机重启期数据 Whether the disk store persists between restarts of the Virtual Machine. The default value is false.
       diskSpoolBufferSizeMB:这个参数设置 DiskStore(磁盘缓存)的缓存区大小。默认是 30MB。每个 Cache 都应该有自己的一个缓冲区。
       diskExpiryThreadIntervalSeconds:磁盘失效线程运行时间间隔,默认是 120 秒。
       memoryStoreEvictionPolicy:当达到 maxElementsInMemory 限制时,Ehcache 将会根据指定的策略去清理内存。默认策略是 LRU(最近最少使用)。你可以设置为 FIFO(先进先出)或是 LFU(较少使用)。
       clearOnFlush:内存数量最大时是否清除。
         memoryStoreEvictionPolicy:
            Ehcache 的三种清空策略;
            FIFO,first in first out,这个是大家最熟的,先进先出。
            LFU, Less Frequently Used,就是上面例子中使用的策略,直白一点就是讲一直以来最少被使用的。如上面所讲,缓存的元素有一个 hit 属性,hit 值最小的将会被清出缓存。
            LRU,Least Recently Used,最近最少使用的,缓存的元素有一个时间戳,当缓存容量满了,而又需要腾出地方来缓存新的元素的时候,那么现有缓存元素中时间戳离当前时间最远的元素将被清出缓存。
    -->
    <defaultCache
            maxElementsInMemory="10000"
            eternal="false"
            timeToIdleSeconds="120"
            timeToLiveSeconds="120"
            overflowToDisk="false"
            diskPersistent="false"
            diskExpiryThreadIntervalSeconds="120"
    />
    <!-- 登录记录缓存锁定 10 分钟 -->
    <cache name="passwordRetryCache"
           maxEntriesLocalHeap="2000"
           eternal="false"
           timeToIdleSeconds="3600"
           timeToLiveSeconds="0"
           overflowToDisk="false"
           statistics="true">
    </cache>
</ehcache>

三.在登录验证控制器中使用shiro进行管理用户登录

  • 将原来的登录验证代码替换成以下代码
    	// 验证
        UsernamePasswordToken token = new UsernamePasswordToken(user.getUserName(), user.getUserPassword());
        Subject currentUser = SecurityUtils.getSubject();// 获取当前的 Subject
        try {
            // 在调用了 login 方法后, SecurityManager 会收到 AuthenticationToken, 并将其发送给已配置的 Realm 执行必须的认证检查
            // 每个 Realm 都能在必要时对提交的 AuthenticationTokens 作出反应
            // 所以这一步在调用 login(token) 方法时, 它会走到 MyRealm.doGetAuthenticationInfo() 方法中, 具体验证方式详见此方法
            currentUser.login(token);
        }catch(UnknownAccountException uae){
        	System.err.println("进行登录验证.. 验证未通过, 未知账户");
        }catch(IncorrectCredentialsException ice){
        	System.err.println("进行登录验证.. 验证未通过, 错误的凭证");
        }catch(LockedAccountException lae){
        	System.err.println("对用户  进行登录验证.. 验证未通过, 账户已锁定");
        }catch(ExcessiveAttemptsException eae){
        	System.err.println("对用户进行登录验证.. 验证未通过, 错误次数大于 5 次, 账户已锁定");
        }catch (DisabledAccountException sae){
        	System.err.println("对用户进行登录验证.. 验证未通过, 帐号已经禁止登录");
        }catch(AuthenticationException ae){
        	System.err.println("对用户  进行登录验证.. 验证未通过, 堆栈轨迹如下");
            ae.printStackTrace();
        }
        // 验证是否登录成功
        if(currentUser.isAuthenticated()){//登录成功
            return "jsp/sys/login";
        }else {//登录失败
            token.clear();
            return "jsp/error";
        }

博客仅做学习交流使用,并非课件,仁者见仁,不喜勿喷.如果您觉得有用,请点个赞,谢谢!

猜你喜欢

转载自blog.csdn.net/qq_37358860/article/details/89242495
今日推荐