cookies 设置未成功情况分析

1,问题描述:

用户登录之后,页面一直刷新,页面呈现空白,jessionId一直在变

http://dev.cbs.abc.com/base/;JSESSIONID=07fa59d4-822e-43a7-ad7f-f0f5f5d2c347

后端显示错误

[2019-03-11 19:16:59,411] INFO  com.wiwj.abc.common.shiro.ShiroSession[32] - 调用ShiroSession方法
[2019-03-11 19:16:59,411] INFO  com.wiwj.abc.common.shiro.ShiroSession[51] - 调用setId方法
[2019-03-11 19:16:59,411] INFO  com.wiwj.abc.common.shiro.ShiroSession[72] - 调用setTimeout方法
[2019-03-11 19:16:59,412] INFO  com.wiwj.abc.common.shiro.ShiroSession[93] - 调用setAttribute方法
[2019-03-11 19:16:59,413] INFO  com.wiwj.abc.common.shiro.ShiroSession[86] - 调用setAttributes方法
[2019-03-11 19:16:59,415] INFO  com.wiwj.abc.common.shiro.ShiroSession[93] - 调用setAttribute方法
[2019-03-11 19:16:59,418] INFO  com.wiwj.abc.common.shiro.ShiroSession[93] - 调用setAttribute方法
[2019-03-11 19:16:59,421] INFO  com.wiwj.abc.common.shiro.ShiroSession[93] - 调用setAttribute方法
[2019-03-11 19:16:59,423] INFO  com.wiwj.abc.common.shiro.ShiroSession[93] - 调用setAttribute方法
[2019-03-11 19:16:59,426] INFO  com.wiwj.abc.common.shiro.ShiroSession[93] - 调用setAttribute方法
[2019-03-11 19:16:59,431] INFO  com.wiwj.abc.common.shiro.ShiroSession[93] - 调用setAttribute方法
[2019-03-11 19:16:59,434] INFO  com.wiwj.abc.common.shiro.ShiroSession[93] - 调用setAttribute方法
[2019-03-11 19:16:59,456] INFO  com.wiwj.abc.common.shiro.ShiroSession[32] - 调用ShiroSession方法
[2019-03-11 19:16:59,456] INFO  com.wiwj.abc.common.shiro.ShiroSession[51] - 调用setId方法
[2019-03-11 19:16:59,457] INFO  com.wiwj.abc.common.shiro.ShiroSession[72] - 调用setTimeout方法
[2019-03-11 19:16:59,458] INFO  com.wiwj.abc.common.shiro.ShiroSession[93] - 调用setAttribute方法
[2019-03-11 19:16:59,458] INFO  com.wiwj.abc.common.shiro.ShiroSession[86] - 调用setAttributes方法

2,问题分析,系统框架采用spring+shiro方式,其中shiro配置中jsessionid配置如下

<property name="sessionIdCookie">
            <bean class="org.apache.shiro.web.servlet.SimpleCookie">
                <constructor-arg value="sid" />
                <property name="domain" value=".cbs.abc.com" />
                <property name="path" value="/" />
                <property name="maxAge" value="-1" />
                <property name="httpOnly" value="true" />
            </bean>
        </property>

 而对应的注释为

sessionIdCookie是sessionManager创建会话Cookie的模板:
sessionIdCookie.name:设置Cookie 名字,默认为JSESSIONID;
sessionIdCookie.domain:设置Cookie的域名,默认空,即当前访问的域名;
sessionIdCookie.path:设置Cookie 的路径,默认空,即存储在域名根下;
sessionIdCookie.maxAge:设置Cookie 的过期时间,秒为单位,默认-1 表示关闭浏览器时
过期Cookie;
sessionIdCookie.httpOnly:如果设置为true,则客户端不会暴露给客户端脚本代码,使用
HttpOnly cookie有助于减少某些类型的跨站点脚本攻击;此特性需要实现了Servlet 2.5 MR6
及以上版本的规范的Servlet容器支持;
sessionManager.sessionIdCookieEnabled:是否启用/禁用Session Id Cookie,默认是启用的;
如果禁用后将不会设置Session Id Cookie,即默认使用了Servlet容器的JSESSIONID,且通
过URL重写(URL中的“;JSESSIONID=id”部分)保存Session Id。

看到JsessionId一直在刷新,而这个配置主要是为了设置浏览器的cookies值,由此猜测jsessionId一直刷新的原因是cookies值一直设置不了

另外通过浏览器开发者模式中观察到application-->Storage -->Cookies中的sid存在两个,一个域名为.cbs.xx.com,一个域名为.xx.com

我大胆的把第二个域名.xx.com的这个sid给去掉,然后刷新页面就可以了

3,根源分析

是由于domain域名设置重复的问题,由于之前设置过.abc.com这个域名的sid,再使用.cbs.abc.com这个域名访问时就出现sid设置失败的情况,这个可能跟chrome浏览器设置cookies的机制有关,

其实如果domain都改成.abc.com这种其实也是不行的

建议方案:1,domain这个值都设置成.cbs.abc.com这种访问

2,各个环境设置不同的domain,比如dev.cbs.abc.com,sit.cbs.abc.com;

另外参考往上的cookies的设置规则,以供学习

       1)二级域名能读取设置了domain为顶级域名或者自身的cookie,不能读取其他二级域名domain的cookie。所以要想cookie在多个二级域名中共享,需要设置domain为顶级域名,这样就可以在所有二级域名里面或者到这个cookie的值了。

2)顶级域名只能获取到domain设置为顶级域名的cookie,其他domain设置为二级域名的无法获取。

相关推荐