在第七篇文章说了一下如何实现shiro的共享。那个共享并不只是session的共享,也包括了Authorization的共享。如果读者还没看过文章七,建议先看看。
在文章七的ShiroCacheManager类继承了AbstractCacheManager,我们来看看AbstractCacheManager类的源码:
1 | public abstract class AbstractCacheManager implements CacheManager, Destroyable { |
其中有个很重要的方法就是getCache方法,有个很重要的属性就是private final ConcurrentMap<String, Cache> caches;caches是一个线程安全的ConcurrentMap类型,用是存放Cache的,在这里,至少存放两个Cache,一个是用来存放session的,一个是用来存放权限(Authorization)的。从getCache方法我们可以知道,shiro先从caches里拿,如果拿不到相应的Cache,就调用createCache创建一个,createCache是抽象方法,由子类实现。创建完之后,放到Map中。
如果我们在getCache方法debug就可以知道,shiro创建两个Cache放到ConcurrentMap中,一个name中ShiroCasRealm.authorizationCache(这个名字的命名规则是自定义的realm的名字加”.authorizationCache”,realm的定义可以参考我的shiro之旅: 二 让Shiro保护你的应用),这个是shiro启动的时候创建的,用来保存认证信息,一个叫shiro-activeSessionCache,这个是第一次创建session的时候创建的,用来保存session。当用户登录的时候,将会把用户的权限信息保存到name为ShiroCasRealm.authorizationCache的Cache中,以后需要再使用权限信息,直接从Cache中拿而不需要再从数据库中查询。这样也有一个问题,就是当用户权限改变时,就需要用户重新登录把权限信息从新load到Cache中。不过既然我们知道Cache的名字,我们就可以拿到这个Cache,然后把用户的权限信息删除,让shiro在授权时找不到权限而shiro自己从新去load,甚至我们可以删除了,然后再从新load到Cache中。这些将在以后的文章有介绍。
session我们是放到了缓存中(memcached),那自然我们就可以在多个应用去使用它。只要从个应用的ShiroMemcachedCache连的都是一个memcached,就可以把session保存到一个memcached中,就可以从同一个memcached去得到session。