shiro实现session共享

Posted 店蛋蛋

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了shiro实现session共享相关的知识,希望对你有一定的参考价值。

session共享:在多应用系统中,如果使用了负载均衡,用户的请求会被分发到不同的应用中,A应用中的session数据在B应用中是获取不到的,就会带来共享的问题。

假设:用户第一次访问,连接的A服务器,进行了登录操作进入了系统,当用户再次操作时,请求被转发到了B服务器,用户并没有在B进行登录,此时用户又来到了登录页面,这是难以理解和接受的,这就引出了session共享。

对于shiro框架如何实现session的共享呢?shiro的共享分为两个方面,一个是session的共享,一个是cache的共享。接下来结合redis分别来实现这两个方面。

 

一.Session的共享

    

    shiro提供了自己的会话管理器sessionManager,其中有个属性叫sessionDao它来处理所有的会话信息。

    对于sessionDao,shiro也提供了自己的实现,常用的是ehcache的实现。Ehcache是jvm级别的,多个应用就会产生多个缓存示例,无法做到信息跨进程共享。要实现共享,就要重写sessionDao,通过实现我们自己的Dao,做到同一个会话信息的唯一性。

看下面一幅类图:

1.继承shiro提供的抽象sessionDao,重写create,read,delete等方法。

2.考虑系统的扩展性,我们抽象出一个数据仓储接口,并提供一个redis的实现方式。假如以后我们底层要换成数据库存储session数据,那只需扩展一个数据库的实现类并注入。

 

二.Cache的共享

 

同样的,shiro也提供了自己的缓存管理器:cacheManager,重写这个实现,来满足缓存的共享。

看下面的类图:

  1. 我们只需实现shiro的CacheManager和Cache接口即可。前者暴漏了获取Cache实例的方法,后者提供了Cache实例的增删改查操作。

  2. 中间一层的抽象是为了设计的良好,提供扩展性,后期有需要,只需增加ShiroCacheManager的实现类。

  3. JedisShiroCacheManager中的Cache实例通过ConCurrentHashMap进行缓存,防止对象的反复创建。

 

三.配置

 

3.1 Cache配置

<!-- redisManager-->

<bean id ="redisManager" class = "com.yingxinhuitong.shiro.util.RedisManager">
  <property name = "host"value = "127.0.0.1"/>
  <property name = "port"value = "6379"/>
  <property name = "expire"value = "1800"/>
  <!--<property name ="password" value=""/>-->
  <!--<property name ="timeout" value="0"/>-->
</bean>
<!-- shiro缓存 -->
<bean id = "shrioCacheManager" class ="com.yingxinhuitong.shiro.cache.JedisShiroCacheManager">

    <property name ="redisManager" ref = "redisManager"/>
</bean>
<bean id = "shiroJedisManager" class ="com.yingxinhuitong.shiro.cache.CustomShiroCacheManager">

    <property name ="shrioCacheManager" ref = "shrioCacheManager"/>
</bean>

 

3.2 sessionDao配置

<!-- 会话DAO -->

<bean id = "shiroSessionRepository"

  class = "com.yingxinhuitong.shiro.session.JedisShiroSessionRepository">

    <property name = "redisManager" ref = "redisManager"/></bean>

    <bean id = "sessionDAO" class = "com.yingxinhuitong.shiro.session.CustomShiroSessionDao"><property name = "sessionIdGenerator" ref = "sessionIdGenerator"/>

    <property name = "shiroSessionRepository" ref = "shiroSessionRepository"/>

</bean>

 

四.代码

参见:https://github.com/zljk0306/shiro-redis-share

 

关注老姜谈技术,微信号:helojava,或者扫描下面二维码。

以上是关于shiro实现session共享的主要内容,如果未能解决你的问题,请参考以下文章

Session(数据)共享的前后端分离Shiro实战

SpringBoot 整合Shiro实现动态权限加载更新+Session共享+单点登录

shiro前后台的session会共用一个,怎么分开?

shiro之redis频繁访问问题

转Apache shiro集群实现 shiro入门介绍

集成shiro 啥情况下会session丢失