在 SpringBoot 中使用拦截器。
我正在寻找添加 SameSite 的解决方案,我只想将属性添加到现有的“Set-Cookie”,而不是创建新的“Set-Cookie”。
我尝试了几种方法来满足这个要求,包括:
- 如@unwichtich 所说,添加自定义过滤器,
- 以及更多我覆盖了 basicAuthenticationFilter。它确实添加了 SameSite 属性。虽然 Spring 添加“Set-Cookie”的时机很难把握。我认为在 onAuthenticationSuccess() 方法中,响应必须有这个头,但它没有。我不确定这是否是我的自定义 basicAuthenticationFilter 顺序的错。
- 使用cookieSerializer,但spring-session版本出现问题。似乎只有最新版本支持它,但我仍然无法弄清楚应该将版本号添加到依赖列表中。
不幸的是,上面没有一个可以像预期的那样很好地添加相同的站点。
最后,我发现spring中的interceptor可以帮我实现。
我花了一个星期才拿到它。如果有人遇到同样的问题,希望这可以帮助您。
@Component
public class CookieServiceInterceptor extends HandlerInterceptorAdapter {
@Override
public boolean preHandle(
HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
return true;
}
@Override
public void postHandle(
HttpServletRequest request, HttpServletResponse response, Object handler,
ModelAndView modelAndView) throws Exception {
//check whether it has "set-cookie" in the response, if it has, then add "SameSite" attribute
//it should be found in the response of the first successful login
Collection<String> headers = response.getHeaders(HttpHeaders.SET_COOKIE);
boolean firstHeader = true;
for (String header : headers) { // there can be multiple Set-Cookie attributes
if (firstHeader) {
response.setHeader(HttpHeaders.SET_COOKIE, String.format("%s; %s", header, "SameSite=strict"));
firstHeader = false;
continue;
}
response.addHeader(HttpHeaders.SET_COOKIE, String.format("%s; %s", header, "SameSite=strict"));
}
}
@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response,
Object handler, Exception exception) throws Exception {
}
}
你还需要让这个拦截器在你的应用程序中工作,这意味着你应该添加一个bean,如下所示:
@Autowired
CookieServiceInterceptor cookieServiceInterceptor;
@Bean
public MappedInterceptor myInterceptor() {
return new MappedInterceptor(null, cookieServiceInterceptor);
}
这个拦截器有一个缺陷,当请求被重定向(ex.return 302)或失败(ex.return 401)时,它无法添加samesite,而当SSO时它使我的应用程序失败。最终,我必须使用 Tomcat cookie,因为我没有在我的 springboot 应用程序中嵌入 tomcat。我加了
<Context>
<CookieProcessor sameSiteCookies="none" />
</Context>
在我的应用程序的 /META-INF 下的 context.xml 中。它将在每个响应的 set-cookie 标头中添加 SameSite 属性。请注意,从 Tomcat 9.0.21 和 8.5.42 开始,这种行为是可能的。根据https://stackoverflow.com/a/57622508/4033979