综述
问题原理解析
首先“;jsessionid”参数是服务器端生成的,生成逻辑参考下图:
1、client向server发送请求http://localhost:8081
2、server端经由shiro进行内部内部URL重定向至http://localhost:8081/login
3、server收到http://localhost:8081/login请求后,发现请求头中没有cookie(因为这次请求是server内部重定向的),那么server就认为client端禁用了cookie,并且为这次会话产生唯一标示即SESSIONID,并将SESSIONID追加到http://localhost:8081/login,作为response响应给client。如图:
4、client收到server的响应后,以http://localhost:8081/login;JSESSIONID=XXX 为URL进行请求重定向(上图中302是重定向的状态码),最后展示出登陆页,如图:
5、提交登陆信息后,server从请求信息中发现了cookie(因为这次请求是client发出的而非server内部重定向),会认为client没有禁用cookie,就不会进行URL重定向,而是将SESSIONID放入cookie之中,所以之后的请求URL就无需追加URL,如果此时手动删除client端的cookie,重新请求http://localhost:8081,就会发现SESSIONID再一次被追加到了URL后面。
————————————————
版权声明:本文为CSDN博主「木子樾」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/qq_32891219/article/details/83024559
解决方案
方法一 application.yml 里设置
springBoot2.0之前版本
server:
port: 80
servlet:
session:
tracking-modes: cookie
cookie:
http-only: true
方法二 启动类继承SpringBootServletInitializer 类,重写 onStartup 方法
(此方法在springBoot2.0之前版本没有起作用,暂时做记录)
@SpringBootApplication(exclude = DataSourceAutoConfiguration.class)
public class NdaDemoApplication extends SpringBootServletInitializer {
public static void main(String[] args) {
SpringApplication.run(NdaDemoApplication.class, args);
}
public void onStartup(ServletContext servletContext)throws ServletException {
super.onStartup(servletContext);
servletContext.setSessionTrackingModes(Collections.singleton(SessionTrackingMode.COOKIE));
SessionCookieConfig sessionCookieConfig = servletContext.getSessionCookieConfig();
sessionCookieConfig.setHttpOnly(true);
}
}
参考:https://blog.csdn.net/weixin_37380784/article/details/84953808
其他未尝试
public static final String cleanupUrl(final String url) {
if (url == null) {
return null;
}
final int jsessionPosition = url.indexOf(";jsession");
if (jsessionPosition == -1) {
return url;
}
final int questionMarkPosition = url.indexOf("?");
if (questionMarkPosition < jsessionPosition) {
return url.substring(0, url.indexOf(";jsession"));
}
return url.substring(0, jsessionPosition)
+ url.substring(questionMarkPosition);
}