Skip to content

Commit 020f556

Browse files
committed
Support custom attribute with a value in MockCookie.parse()
Prior to this commit, MockCookie.parse() failed with an IllegalArgumentException when attempting to parse a custom attribute with a value, such as "Version=1". This is a regression that was inadvertently introduced in 7fc4937 when adding support for the "Partitioned" attribute which does not support a value. This commit addresses this regression by parsing both the name and the value from an optional, custom attribute. See gh-31454 Closes gh-34575
1 parent 6ea3b5a commit 020f556

File tree

3 files changed

+27
-9
lines changed

3 files changed

+27
-9
lines changed

spring-test/src/main/java/org/springframework/mock/web/MockCookie.java

+5-4
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2002-2024 the original author or authors.
2+
* Copyright 2002-2025 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -178,7 +178,8 @@ else if (StringUtils.startsWithIgnoreCase(attribute, COMMENT)) {
178178
cookie.setComment(extractAttributeValue(attribute, setCookieHeader));
179179
}
180180
else if (!attribute.isEmpty()) {
181-
cookie.setAttribute(attribute, extractOptionalAttributeValue(attribute, setCookieHeader));
181+
String[] nameAndValue = extractOptionalAttributeNameAndValue(attribute, setCookieHeader);
182+
cookie.setAttribute(nameAndValue[0], nameAndValue[1]);
182183
}
183184
}
184185
return cookie;
@@ -191,9 +192,9 @@ private static String extractAttributeValue(String attribute, String header) {
191192
return nameAndValue[1];
192193
}
193194

194-
private static String extractOptionalAttributeValue(String attribute, String header) {
195+
private static String[] extractOptionalAttributeNameAndValue(String attribute, String header) {
195196
String[] nameAndValue = attribute.split("=");
196-
return nameAndValue.length == 2 ? nameAndValue[1] : "";
197+
return (nameAndValue.length == 2 ? nameAndValue : new String[] {attribute, ""});
197198
}
198199

199200
@Override

spring-test/src/test/java/org/springframework/mock/web/MockCookieTests.java

+18-2
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2002-2024 the original author or authors.
2+
* Copyright 2002-2025 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -68,8 +68,8 @@ void parseHeaderWithoutAttributes() {
6868
assertCookie(cookie, "SESSION", "123");
6969
}
7070

71-
@SuppressWarnings("removal")
7271
@Test
72+
@SuppressWarnings("removal")
7373
void parseHeaderWithAttributes() {
7474
MockCookie cookie = MockCookie.parse("SESSION=123; Domain=example.com; Max-Age=60; " +
7575
"Expires=Tue, 8 Oct 2019 19:50:00 GMT; Path=/; Secure; HttpOnly; Partitioned; SameSite=Lax");
@@ -87,6 +87,19 @@ void parseHeaderWithAttributes() {
8787
assertThat(cookie.getComment()).isNull();
8888
}
8989

90+
@Test // gh-34575
91+
void parseHeaderWithOptionalAttributes() {
92+
MockCookie cookie = MockCookie.parse("SESSION=123; HttpOnly; Version=1; Partitioned; Secure");
93+
94+
assertCookie(cookie, "SESSION", "123");
95+
assertThat(cookie.isHttpOnly()).isTrue();
96+
assertThat(cookie.getSecure()).isTrue();
97+
assertThat(cookie.isPartitioned()).isTrue();
98+
assertThat(cookie.getAttribute("Partitioned")).isEmpty();
99+
assertThat(cookie.getAttribute("Version")).isEqualTo("1");
100+
assertThat(cookie.getAttribute("BOGUS")).isNull();
101+
}
102+
90103
@ParameterizedTest
91104
@ValueSource(strings = {"0", "bogus"})
92105
void parseHeaderWithInvalidExpiresAttribute(String expiresValue) {
@@ -209,10 +222,13 @@ void setInvalidAttributeExpiresShouldThrow() {
209222
void setPartitioned() {
210223
MockCookie cookie = new MockCookie("SESSION", "123");
211224
assertThat(cookie.isPartitioned()).isFalse();
225+
assertThat(cookie.getAttribute("Partitioned")).isNull();
212226
cookie.setPartitioned(true);
213227
assertThat(cookie.isPartitioned()).isTrue();
228+
assertThat(cookie.getAttribute("Partitioned")).isEmpty();
214229
cookie.setPartitioned(false);
215230
assertThat(cookie.isPartitioned()).isFalse();
231+
assertThat(cookie.getAttribute("Partitioned")).isNull();
216232
}
217233

218234
}

spring-web/src/testFixtures/java/org/springframework/web/testfixture/servlet/MockCookie.java

+4-3
Original file line numberDiff line numberDiff line change
@@ -178,7 +178,8 @@ else if (StringUtils.startsWithIgnoreCase(attribute, COMMENT)) {
178178
cookie.setComment(extractAttributeValue(attribute, setCookieHeader));
179179
}
180180
else if (!attribute.isEmpty()) {
181-
cookie.setAttribute(attribute, extractOptionalAttributeValue(attribute, setCookieHeader));
181+
String[] nameAndValue = extractOptionalAttributeNameAndValue(attribute, setCookieHeader);
182+
cookie.setAttribute(nameAndValue[0], nameAndValue[1]);
182183
}
183184
}
184185
return cookie;
@@ -191,9 +192,9 @@ private static String extractAttributeValue(String attribute, String header) {
191192
return nameAndValue[1];
192193
}
193194

194-
private static String extractOptionalAttributeValue(String attribute, String header) {
195+
private static String[] extractOptionalAttributeNameAndValue(String attribute, String header) {
195196
String[] nameAndValue = attribute.split("=");
196-
return nameAndValue.length == 2 ? nameAndValue[1] : "";
197+
return (nameAndValue.length == 2 ? nameAndValue : new String[] {attribute, ""});
197198
}
198199

199200
@Override

0 commit comments

Comments
 (0)