shiro关于session id无效的问题 , 跪求大神解惑

最近重构之前的老系统springMVC转springBoot+shiro遇到了session id无效的问题
shiroConfig里面也已经配置了自定义sessionId
ShiroConfig代码如下

 @Configuration
public class ShiroConfig {

    @Value("${spring.redis.host}")
    private String host;

    @Value("${spring.redis.port}")
    private int port;

    @Value("${spring.redis.password}")
    private String password;

    @Value("${spring.redis.timeout}")
    private int timeout;

    @Value("${session.sessionTimeout}")
    private long sessionTimeout;

    @Value("${session.sessionTimeoutClean}")
    private long sessionTimeoutClean;

    @Value("${shiro.session.expire}")
    private Integer expire;

    @Bean
    public static LifecycleBeanPostProcessor getLifecycleBeanPostProcessor() {
        return new LifecycleBeanPostProcessor();
    }

    @Bean
    public ShiroFilterFactoryBean shirFilter(SecurityManager securityManager) {
        ShiroFilterFactoryBean shiroFilterFactoryBean = new ShiroFilterFactoryBean();
        // 必须设置 SecurityManager
        shiroFilterFactoryBean.setSecurityManager(securityManager);
        // 如果不设置默认会自动寻找Web工程根目录下的"/login"页面
        shiroFilterFactoryBean.setLoginUrl("/login");
        // 登录成功后要跳转的链接
        shiroFilterFactoryBean.setSuccessUrl("/loginSuccess");
        //未授权界面;
        shiroFilterFactoryBean.setUnauthorizedUrl("/error/403");

        //拦截器.
        Map<String, String> filterChainDefinitionMap = new LinkedHashMap<String, String>();
        filterChainDefinitionMap.put("/3rd/**", "anon");
        filterChainDefinitionMap.put("/framework/**", "anon");
        filterChainDefinitionMap.put("/js/**", "anon");
        filterChainDefinitionMap.put("/css/**", "anon");
        filterChainDefinitionMap.put("/img/**", "anon");
        filterChainDefinitionMap.put("/font/**", "anon");
        //配置退出 过滤器,其中的具体的退出代码Shiro已经替我们实现了
        filterChainDefinitionMap.put("/logout", "logout");
        filterChainDefinitionMap.put("/**", "authc");
        shiroFilterFactoryBean.setFilterChainDefinitionMap(filterChainDefinitionMap);
        return shiroFilterFactoryBean;
    }

    @Bean
    public SecurityManager securityManager() {
        DefaultWebSecurityManager securityManager = new DefaultWebSecurityManager();
        //设置realm.
        securityManager.setRealm(myShiroRealm());
        // 自定义缓存实现 使用redis
        // securityManager.setCacheManager(redisCacheManager());
        // 自定义session管理 使用redis
        securityManager.setSessionManager(sessionManager());
        return securityManager;
    }

    @Bean
    public MyShiroRealm myShiroRealm() {
        MyShiroRealm myShiroRealm = new MyShiroRealm();
        myShiroRealm.setCredentialsMatcher(hashedCredentialsMatcher());
        return myShiroRealm;
    }

    @Bean
    public HashedCredentialsMatcher hashedCredentialsMatcher() {
        HashedCredentialsMatcher hashedCredentialsMatcher = new HashedCredentialsMatcher();
        hashedCredentialsMatcher.setHashAlgorithmName("SHA-1");//散列算法:这里使用MD5算法;
        hashedCredentialsMatcher.setHashIterations(1024);//散列的次数,比如散列两次,相当于 md5(md5(""));
        return hashedCredentialsMatcher;
    }

    /**
     * 开启shiro aop注解支持.
     * 使用代理方式;所以需要开启代码支持;
     *
     * @param securityManager
     * @return
     */
    @Bean
    public AuthorizationAttributeSourceAdvisor authorizationAttributeSourceAdvisor(SecurityManager securityManager) {
        AuthorizationAttributeSourceAdvisor authorizationAttributeSourceAdvisor = new AuthorizationAttributeSourceAdvisor();
        authorizationAttributeSourceAdvisor.setSecurityManager(securityManager);
        return authorizationAttributeSourceAdvisor;
    }

    /**
     * 配置shiro redisManager
     * 使用的是shiro-redis开源插件
     *
     * @return
     */
    public RedisManager redisManager() {
        RedisManager redisManager = new RedisManager();
        redisManager.setHost(host);
        redisManager.setPort(port);
        redisManager.setExpire(1800);// 配置缓存过期时间 30分钟
        redisManager.setTimeout(timeout);
        redisManager.setPassword(password);
        return redisManager;
    }

    /**
     * RedisSessionDAO shiro sessionDao层的实现 通过redis
     * 使用的是shiro-redis开源插件
     */
    @Bean
    public RedisSessionDAO redisSessionDAO() {
        RedisSessionDAO redisSessionDAO = new RedisSessionDAO();
        redisSessionDAO.setRedisManager(redisManager());
        redisSessionDAO.setSessionIdGenerator(sessionIdGenerator());
        redisSessionDAO.setKeyPrefix("shiro_session_");
        return redisSessionDAO;
    }

    /**
     * shiro session的管理
     */
    @Bean
    public DefaultWebSessionManager sessionManager() {
        DefaultWebSessionManager sessionManager = new DefaultWebSessionManager();
        sessionManager.setSessionDAO(redisSessionDAO());
        // 会话超时时间,单位:毫秒
        sessionManager.setGlobalSessionTimeout(sessionTimeout);
        // 定时清理失效会话, 清理用户直接关闭浏览器造成的孤立会话
        sessionManager.setSessionValidationInterval(sessionTimeoutClean);
        sessionManager.setSessionValidationSchedulerEnabled(true);
        // 指定sessionid
        sessionManager.setSessionIdCookie(sessionIdCookie());
        sessionManager.setSessionIdCookieEnabled(true);
        // 去掉shiro登录时url里的JSESSIONID
        sessionManager.setSessionIdUrlRewritingEnabled(false);
        return sessionManager;
    }

    /**
     * 指定本系统sessionid, 问题: 与servlet容器名冲突, 如jetty, tomcat 等默认jsessionid,
     * 当跳出shiro servlet时如error-page容器会为jsessionid重新分配值导致登录会话丢失!
     *
     * @return
     */
    @Bean
    public SimpleCookie sessionIdCookie() {
        SimpleCookie simpleCookie = new SimpleCookie();
        simpleCookie.setName("shiro.session");
        return simpleCookie;
    }

    @Bean
    public SessionIdGenerator sessionIdGenerator() {
        SessionIdGenerator sessionIdGenerator = new SessionIdGenerator() {
            @Override
            public Serializable generateId(Session session) {
                return IdGen.uuid();
            }
        };
        return sessionIdGenerator;
    }


}

LoginController代码如下

 @Controller
public class LoginController {

    @Value("${login.adauth}")
    private String adAuth;

    /**
     * 管理登录 浏览器访问 系统
     */
    @RequestMapping(value = "/login", method = RequestMethod.GET)
    public String login(HttpServletRequest request, HttpServletResponse response, Model model) {
        User user = UserUtils.getUser();
        // 如果已经登录,则跳转到管理首页
        if (!StringUtils.isNullOrEmpty(user.getId())) {
            return "redirect:/loginSuccess";
        }
        model.addAttribute("login_adauth", adAuth);
        model.addAttribute("domain", 0);

        return "sys/sysLogin";
    }

    /**
     * 登录失败,真正登录的POST请求由Filter完成
     */
    @RequestMapping(value = "/login", method = RequestMethod.POST)
    public String login(@RequestParam(FormAuthenticationFilter.DEFAULT_USERNAME_PARAM) String username, String password, HttpServletRequest request, HttpServletResponse response, Model model) {
        User user = UserUtils.getUser();
        // 如果已经登录,则跳转到管理首页
        if (!StringUtils.isNullOrEmpty(user.getId())) {
            return "redirect:/loginSuccess";
        }
        model.addAttribute(FormAuthenticationFilter.DEFAULT_USERNAME_PARAM, username);
        model.addAttribute("login_adauth", adAuth);
        model.addAttribute("domain", 1);
        return "sys/sysLogin";
    }

    /**
     * 登录成功,进入管理首页
     */
    @RequestMapping(value = "/loginSuccess")
    public String index(HttpServletRequest request, HttpServletResponse response, Model model) {
        User user = UserUtils.getUser();
        // 未登录,则跳转到登录页
        if (StringUtils.isNullOrEmpty(user.getId())) {
            return "redirect:/login";
        }
        model.addAttribute("user", user);
        model.addAttribute("login_adauth", adAuth);
        return "sys/sysIndex";
    }

}

sysLogin代码如下

 <div class="login">
            <div class="loginlogo"></div>
            <form id="login" action="/login" method="post">
                <input type="text" id="username" name="username" class="name" placeholder="User name" />
                <input type="password" id="password" name="password" class="pwd" placeholder="Password" />
                <div class="w_info" id="error_info">The user name error, please try again</div>
                <input type="submit" value="Login" class="submit" />
                <div class="tipsDiv" style="text-align: center;">
                <a style="color: #fff;" href="http://workplace.lenovo.com/SoftwareDetail?id=93">Chrome Download</a>
                </div>
            </form>
        </div>

问题是浏览器输入http://127.0.0.1/login访问正常 , 登录也正常
访问正常的

如果我浏览器里面直接输入http://127.0.0.1访问就废了 , 看图
图片说明
LoginController里面的login get方法也正常走 一到返回页面就是上面的错
图片说明

跪求大神解惑

LoginController里面的login get方法也正常走 一到返回页面就是上面的错

1、我自己实现的sessionListener为什么onExpiration一直都不触发?
2、怎么判断session已经失效。
3、是session.setLastAccessTime()先开始执行还是fiter开始执行?

XML/HTML code
?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25

<bean id="sessionManager" class="org.apache.shiro.web.session.mgt.DefaultWebSessionManager"> 
    <property name="sessionDAO" ref="sessionDAO"/>
    <!-- 会话超时时间,单位:毫秒  -->
    <property name="globalSessionTimeout" value="300000"/>
    <property name="deleteInvalidSessions" value="true" />
    <!-- 定时清理失效会话, 清理用户直接关闭浏览器造成的孤立会话   -->
    <property name="sessionValidationSchedulerEnabled" value="true"/>
    <property name="sessionValidationInterval" value="1800000"/>
     <!-- <property name="sessionValidationScheduler" ref="sessionValidationScheduler" /> -->
    <property name="sessionIdCookieEnabled" value="true"/>
    <property name="sessionIdCookie" ref="sessionIdCookie"/>
    <property name="sessionListeners" ref="mySessionListener" />
</bean>

<bean id="sessionValidationScheduler" class="org.apache.shiro.session.mgt.ExecutorServiceSessionValidationScheduler">
 <property name="interval" value="1800000" />
</bean>

<bean id="sessionDAO" class="org.apache.shiro.session.mgt.eis.EnterpriseCacheSessionDAO">
    <property name="sessionIdGenerator" ref="sessionIdGenerator" />
    <property name="activeSessionsCacheName" value="activeSessionsCache" />
    <property name="cacheManager" ref="cacheManager" />
</bean>

24天学会电路板维修,3年免费技术支持