shiro 使用redis做session共享

2018-01-11  本文已影响0人  erika002

1.在securityManager中注入sessionManager配置如下:

      <bean id="securityManager" class="org.apache.shiro.web.mgt.DefaultWebSecurityManager">
      <property name="realm" ref="myShiroRealm"/>
      <property name="sessionManager" ref="sessionManager" />
  </bean>

2.配置sessionManager

  <!--session 管理器-->
    <bean id="sessionManager" class="org.apache.shiro.web.session.mgt.DefaultWebSessionManager">
        <!-- session存储的实现 -->
        <property name="sessionDAO" ref="shiroSessionRedisDAO" />

        <!-- 设置全局会话超时时间,默认30分钟(1800000) -->
        <property name="globalSessionTimeout" value="1800000" />

        <!-- 是否在会话过期后会调用SessionDAO的delete方法删除会话 默认true -->
        <property name="deleteInvalidSessions" value="true" />

        <!-- 会话验证器调度时间 -->
        <property name="sessionValidationInterval" value="1800000" />

        <!-- 定时检查失效的session -->
        <property name="sessionValidationSchedulerEnabled" value="true" />
    </bean>

其中的sessionDAO就是用来操作session的存取的,因此需要注入我们自定义的shiroSessionRedisDAO

3.初始化bean shiroSessionRedisDAO

   <bean id="shiroSessionRedisDAO" class="com.itpay.mp.base.shiro.dao.ShiroSessionRedisDAO">
        <property name="redisCache" ref="sessionRedisCache" />
    </bean>

其中ShiroSessionRedisDAO就是我们继承CachingSessionDAO的自定义实现类,在这个类里面 注入我们需要操作redis的cache类
4.ShiroSessionRedisDAO 代码如下:

public class ShiroSessionRedisDAO extends CachingSessionDAO {
    private Logger logger = LoggerFactory.getLogger(this.getClass());

    private RedisCache redisCache;

    public RedisCache getRedisCache() {
        return redisCache;
    }

    public void setRedisCache(RedisCache redisCache) {
        this.redisCache = redisCache;
    }


    @Override
    protected void doUpdate(Session session) {
        this.saveSession(session);
    }

    @Override
    protected void doDelete(Session session) {
        if (session == null || session.getId() == null) {
            logger.error("session or session id is null");
            return ;
        }
        //根据session id删除session
        redisCache.evict(session.getId());
    }

  
    @Override
    protected Serializable doCreate(Session session) {
        Serializable sessionId = this.generateSessionId(session);
        this.assignSessionId(session, sessionId);
        this.saveSession(session);
        return sessionId;
    }

 
    @Override
    protected Session doReadSession(Serializable sessionId) {
        if(sessionId == null){
            logger.error("传入的 session id is null");
            return null;
        }
        return redisCache.get(sessionId,Session.class);
    }

    /**
     * 将session 保存进redis 中
     * @param session 要保存的session
     */
    private void saveSession(Session session) {
        if (session == null || session.getId() == null) {
            logger.error("session or session id is null");
            return ;
        }
        redisCache.put(session.getId(),session);

    }
}

5.目前的问题是一个请求shiro会多次调用doUpdate,导致对redis的压力比较大,这个以后再想办法优化吧。

上一篇 下一篇

猜你喜欢

热点阅读