You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

重写Shiro SessionDao记录实时登录用户信息时遇UnavailableSecurityManagerException

Fixing UnavailableSecurityManagerException with Custom RedisSessionDao in Shiro

Hey, I've dealt with this exact problem when building a Redis-backed session store for Shiro by extending EnterpriseCacheSessionDAO. Let's walk through the most likely causes and how to fix them:

1. SecurityManager isn't bound to the current thread

This exception almost always pops up when you try to call Shiro APIs that depend on the SecurityManager before it's been attached to the current thread's context. For example, if your custom RedisSessionDao methods (like session creation/update) trigger operations that need the SecurityManager, but there's no instance available in the thread context yet.

Fixes:

  • Make sure SecurityUtils.getSecurityManager() returns a valid instance before any session-related operations run. In a Spring environment, double-check that your SecurityManager bean is fully initialized and injected correctly.
  • If you need to, manually bind the SecurityManager to the thread context in your custom DAO methods:
// Get SecurityManager from Spring context (adjust based on your setup)
SecurityManager securityManager = redisTemplate.getApplicationContext().getBean(SecurityManager.class);
SecurityUtils.setSecurityManager(securityManager);

2. Verify RedisSessionDao initialization & dependencies

You've annotated your RedisSessionDao with @Repository, so confirm that Spring is scanning this class and creating the bean properly. Also, check that your RedisTemplate<String, Object> is being injected successfully—if this dependency fails, it can trigger cascading issues that indirectly lead to the SecurityManager exception.

Additionally, EnterpriseCacheSessionDAO relies on Shiro's caching mechanism. Ensure you've configured a valid cache manager (like a Redis-based one) for Shiro, as missing this can break the context setup.

3. Thread context gaps in overridden methods

Looking at your code snippet, you're overriding the session creation method. Be careful: some operations in the session lifecycle (like accessing Session.getPrincipal()) require an active SecurityManager context. If your custom logic runs before the context is bound, you'll hit this exception.

Fix example for doCreate:

@Override
protected Serializable doCreate(Session session) {
    // Ensure SecurityManager is available in the thread context
    if (SecurityUtils.getSecurityManager() == null) {
        SecurityManager securityManager = redisTemplate.getApplicationContext().getBean(SecurityManager.class);
        SecurityUtils.setSecurityManager(securityManager);
    }
    
    // Proceed with default session creation logic
    Serializable sessionId = super.doCreate(session);
    
    // Save to Redis
    String redisKey = KEY_PREFIX + sessionId;
    redisTemplate.opsForValue().set(redisKey, session);
    
    return sessionId;
}

4. Check your Shiro configuration wiring

The most critical step: make sure your custom RedisSessionDao is properly attached to Shiro's SessionManager, and that the SessionManager is linked to your SecurityManager. If this wiring is missing, Shiro can't find the SecurityManager when handling sessions.

Example Spring configuration:

@Bean
public DefaultWebSessionManager sessionManager(RedisSessionDao redisSessionDao) {
    DefaultWebSessionManager sessionManager = new DefaultWebSessionManager();
    sessionManager.setSessionDAO(redisSessionDao);
    // Add other session settings (timeout, cookie config, etc.)
    return sessionManager;
}

@Bean
public DefaultWebSecurityManager securityManager(DefaultWebSessionManager sessionManager, YourRealm realm) {
    DefaultWebSecurityManager securityManager = new DefaultWebSecurityManager();
    securityManager.setSessionManager(sessionManager);
    securityManager.setRealm(realm);
    // Add other security settings
    return securityManager;
}

内容的提问来源于stack exchange,提问作者Ry Lin

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.20 12:19:39