Adds the ability to set the CSRF Token cookie max age value

Closes gh-11432
This commit is contained in:
Alonso Araya Calvo 2022-06-24 14:40:14 -06:00 committed by Josh Cummings
parent 6971638e16
commit 7841827169
No known key found for this signature in database
GPG Key ID: A306A51F43B8E5A5
2 changed files with 45 additions and 3 deletions

View File

@ -1,5 +1,5 @@
/*
* Copyright 2002-2021 the original author or authors.
* Copyright 2002-2022 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@ -35,6 +35,7 @@ import org.springframework.web.server.ServerWebExchange;
*
* @author Eric Deandrea
* @author Thomas Vitale
* @author Alonso Araya
* @since 5.1
*/
public final class CookieServerCsrfTokenRepository implements ServerCsrfTokenRepository {
@ -57,6 +58,8 @@ public final class CookieServerCsrfTokenRepository implements ServerCsrfTokenRep
private Boolean secure;
private int cookieMaxAge = -1;
/**
* Factory method to conveniently create an instance that has
* {@link #setCookieHttpOnly(boolean)} set to false.
@ -83,7 +86,7 @@ public final class CookieServerCsrfTokenRepository implements ServerCsrfTokenRep
.from(this.cookieName, tokenValue)
.domain(this.cookieDomain)
.httpOnly(this.cookieHttpOnly)
.maxAge(!tokenValue.isEmpty() ? -1 : 0)
.maxAge(!tokenValue.isEmpty() ? this.cookieMaxAge : 0)
.path((this.cookiePath != null) ? this.cookiePath : getRequestContext(exchange.getRequest()))
.secure((this.secure != null) ? this.secure : (exchange.getRequest().getSslInfo() != null))
.build();
@ -164,6 +167,32 @@ public final class CookieServerCsrfTokenRepository implements ServerCsrfTokenRep
this.secure = secure;
}
/**
* Sets maximum age in seconds for the cookie that the expected CSRF token is saved to
* and read from. By default maximum age value is -1.
*
* <p>
* A positive value indicates that the cookie will expire after that many seconds have
* passed. Note that the value is the <i>maximum</i> age when the cookie will expire,
* not the cookie's current age.
*
* <p>
* A negative value means that the cookie is not stored persistently and will be
* deleted when the Web browser exits.
*
* <p>
* A zero value causes the cookie to be deleted immediately therefore it is not a
* valid value and in that case an {@link IllegalArgumentException} will be thrown.
* @param cookieMaxAge an integer specifying the maximum age of the cookie in seconds;
* if negative, means the cookie is not stored; if zero, the method throws an
* {@link IllegalArgumentException}
* @since 5.8
*/
public void setCookieMaxAge(int cookieMaxAge) {
Assert.isTrue(cookieMaxAge != 0, "cookieMaxAge cannot be zero");
this.cookieMaxAge = cookieMaxAge;
}
private CsrfToken createCsrfToken() {
return createCsrfToken(createNewToken());
}

View File

@ -1,5 +1,5 @@
/*
* Copyright 2002-2021 the original author or authors.
* Copyright 2002-2022 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@ -34,6 +34,7 @@ import static org.assertj.core.api.Assertions.assertThat;
/**
* @author Eric Deandrea
* @author Thomas Vitale
* @author Alonso Araya
* @since 5.1
*/
public class CookieServerCsrfTokenRepositoryTests {
@ -113,6 +114,12 @@ public class CookieServerCsrfTokenRepositoryTests {
saveAndAssertExpectedValues(createToken());
}
@Test
public void saveTokenWhenCookieMaxAgeThenCookieMaxAge() {
setExpectedCookieMaxAge(3600);
saveAndAssertExpectedValues(createToken());
}
@Test
public void saveTokenWhenCustomPropertiesThenCustomProperties() {
setExpectedDomain("spring.io");
@ -120,6 +127,7 @@ public class CookieServerCsrfTokenRepositoryTests {
setExpectedPath("/some/path");
setExpectedHeaderName("headerName");
setExpectedParameterName("paramName");
setExpectedCookieMaxAge(3600);
saveAndAssertExpectedValues(createToken());
}
@ -235,6 +243,11 @@ public class CookieServerCsrfTokenRepositoryTests {
this.csrfTokenRepository.setCookieName(expectedCookieName);
}
private void setExpectedCookieMaxAge(int expectedCookieMaxAge) {
this.csrfTokenRepository.setCookieMaxAge(expectedCookieMaxAge);
this.expectedMaxAge = Duration.ofSeconds(expectedCookieMaxAge);
}
private void setExpectedCookieValue(String expectedCookieValue) {
this.expectedCookieValue = expectedCookieValue;
}