相关配置
整合一下新版本的配置,spring-session主要配置是下面这两个,另外redis、hiberhate、spring的配置底部有源码
applicationContext-session.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"> <!-- 打开RedisOperationsSessionRepository这个bean,RedisHttpSessionConfiguration上的maxInactiveIntervalInSeconds属性会失效。 defaultMaxInactiveInterval有值就按它的秒数来回收空闲的session,有没有值就是默认的1800秒 --> <!-- <bean id="sessionRepository" class="org.springframework.session.data.redis.RedisOperationsSessionRepository"> <constructor-arg ref="redisTemplate" /> <property name="defaultMaxInactiveInterval" value="60" /> </bean> --> <bean class="org.springframework.session.data.redis.config.annotation.web.http.RedisHttpSessionConfiguration"> <property name="maxInactiveIntervalInSeconds" value="60" /> </bean> </beans>
web.xml
<!-- spring session的过滤器代理--> <filter> <filter-name>springSessionRepositoryFilter</filter-name> <filter-class>org.springframework.web.filter.DelegatingFilterProxy</filter-class> </filter> <filter-mapping> <filter-name>springSessionRepositoryFilter</filter-name> <url-pattern>/*</url-pattern> </filter-mapping>
依赖关系
spring-session-data-redis和spring-session-core这两个包在阿里云没有,版本不对会
创建和清除session
1、请求进入,调用httpSessionRepositoryFilter过滤器的doFilterInternal方法@Override protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain filterChain) throws ServletException, IOException { request.setAttribute(SESSION_REPOSITORY_ATTR, this.sessionRepository); SessionRepositoryRequestWrapper wrappedRequest = new SessionRepositoryRequestWrapper( request, response, this.servletContext); SessionRepositoryResponseWrapper wrappedResponse = new SessionRepositoryResponseWrapper( wrappedRequest, response); try { filterChain.doFilter(wrappedRequest, wrappedResponse); } finally { //这个还没有执行 wrappedRequest.commitSession(); } }
2、在redis中创建session:调用httprequest(即SessionRepositoryRequestWrapper)的getSession方法,进而调用RedisOperationsSessionRepository的createSession方法创建session,最后执行上面的wrappedRequest.commitSession()。创建效果如下,TTL显示为360秒,也就是生存时间为我们配置的1分钟再加了5分钟
3、清理redis中的session:RedisHttpSessionConfiguration(继承自SpringHttpSessionConfiguration)如下,该类配置了每分钟都会调用一下清理session的方法。cleanExpiredSessions每次调用都通过读数据(这里时间也加了5分钟)的方式通知redis,redis内部在读时会判断一下数据TTL是否过期再清除static final String DEFAULT_CLEANUP_CRON = "0 * * * * *"; private String cleanupCron = DEFAULT_CLEANUP_CRON; @Override public void configureTasks(ScheduledTaskRegistrar taskRegistrar) { taskRegistrar.addCronTask(() -> sessionRepository().cleanupExpiredSessions(), this.cleanupCron); }
public void cleanExpiredSessions() { long now = System.currentTimeMillis(); long prevMin = roundDownMinute(now); if (logger.isDebugEnabled()) { logger.debug("Cleaning up sessions expiring at " + new Date(prevMin)); } String expirationKey = getExpirationKey(prevMin); Set<Object> sessionsToExpire = this.redis.boundSetOps(expirationKey).members(); this.redis.delete(expirationKey); for (Object session : sessionsToExpire) { String sessionKey = getSessionKey((String) session); touch(sessionKey); } } /** * By trying to access the session we only trigger a deletion if it the TTL is * expired. This is done to handle * https://github.com/spring-projects/spring-session/issues/93 * * @param key the key */ private void touch(String key) { this.redis.hasKey(key); }
源码
- http://download.csdn.net/download/u011189939/10162689