Add CORS support for Private Network Access
This commit adds CORS support for Private Network Access
by adding an Access-Control-Allow-Private-Network response
header when the preflight request is sent with an
Access-Control-Request-Private-Network header and that
Private Network Access has been enabled in the CORS
configuration.
See https://developer.chrome.com/blog/private-network-access-preflight/
for more details.
Closes gh-31974
(cherry picked from commit 318d460256)
This commit is contained in:
@@ -131,6 +131,17 @@ public class CorsRegistration {
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Whether private network access is supported.
|
||||
* <p>Please, see {@link CorsConfiguration#setAllowPrivateNetwork(Boolean)} for details.
|
||||
* <p>By default this is not set (i.e. private network access is not supported).
|
||||
* @since 6.1.3
|
||||
*/
|
||||
public CorsRegistration allowPrivateNetwork(boolean allowPrivateNetwork) {
|
||||
this.config.setAllowPrivateNetwork(allowPrivateNetwork);
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Configure how long in seconds the response from a pre-flight request
|
||||
* can be cached by clients.
|
||||
|
||||
@@ -196,6 +196,7 @@ public abstract class AbstractHandlerMapping extends ApplicationObjectSupport
|
||||
config = (config != null ? config.combine(handlerConfig) : handlerConfig);
|
||||
if (config != null) {
|
||||
config.validateAllowCredentials();
|
||||
config.validateAllowPrivateNetwork();
|
||||
}
|
||||
if (!this.corsProcessor.process(config, exchange) || CorsUtils.isPreFlightRequest(request)) {
|
||||
return NO_OP_HANDLER;
|
||||
|
||||
@@ -534,6 +534,7 @@ public abstract class AbstractHandlerMethodMapping<T> extends AbstractHandlerMap
|
||||
CorsConfiguration corsConfig = initCorsConfiguration(handler, method, mapping);
|
||||
if (corsConfig != null) {
|
||||
corsConfig.validateAllowCredentials();
|
||||
corsConfig.validateAllowPrivateNetwork();
|
||||
this.corsLookup.put(handlerMethod, corsConfig);
|
||||
}
|
||||
|
||||
|
||||
@@ -341,6 +341,18 @@ public class RequestMappingHandlerMapping extends RequestMappingInfoHandlerMappi
|
||||
"or an empty string (\"\"): current value is [" + allowCredentials + "]");
|
||||
}
|
||||
|
||||
String allowPrivateNetwork = resolveCorsAnnotationValue(annotation.allowPrivateNetwork());
|
||||
if ("true".equalsIgnoreCase(allowPrivateNetwork)) {
|
||||
config.setAllowPrivateNetwork(true);
|
||||
}
|
||||
else if ("false".equalsIgnoreCase(allowPrivateNetwork)) {
|
||||
config.setAllowPrivateNetwork(false);
|
||||
}
|
||||
else if (!allowPrivateNetwork.isEmpty()) {
|
||||
throw new IllegalStateException("@CrossOrigin's allowPrivateNetwork value must be \"true\", \"false\", " +
|
||||
"or an empty string (\"\"): current value is [" + allowPrivateNetwork + "]");
|
||||
}
|
||||
|
||||
if (annotation.maxAge() >= 0) {
|
||||
config.setMaxAge(annotation.maxAge());
|
||||
}
|
||||
|
||||
@@ -51,8 +51,8 @@ public class CorsRegistryTests {
|
||||
@Test
|
||||
public void customizedMapping() {
|
||||
this.registry.addMapping("/foo").allowedOrigins("https://domain2.com", "https://domain2.com")
|
||||
.allowedMethods("DELETE").allowCredentials(false).allowedHeaders("header1", "header2")
|
||||
.exposedHeaders("header3", "header4").maxAge(3600);
|
||||
.allowedMethods("DELETE").allowCredentials(true).allowPrivateNetwork(true)
|
||||
.allowedHeaders("header1", "header2").exposedHeaders("header3", "header4").maxAge(3600);
|
||||
Map<String, CorsConfiguration> configs = this.registry.getCorsConfigurations();
|
||||
assertThat(configs.size()).isEqualTo(1);
|
||||
CorsConfiguration config = configs.get("/foo");
|
||||
@@ -60,7 +60,8 @@ public class CorsRegistryTests {
|
||||
assertThat(config.getAllowedMethods()).isEqualTo(Collections.singletonList("DELETE"));
|
||||
assertThat(config.getAllowedHeaders()).isEqualTo(Arrays.asList("header1", "header2"));
|
||||
assertThat(config.getExposedHeaders()).isEqualTo(Arrays.asList("header3", "header4"));
|
||||
assertThat(config.getAllowCredentials()).isFalse();
|
||||
assertThat(config.getAllowCredentials()).isTrue();
|
||||
assertThat(config.getAllowPrivateNetwork()).isTrue();
|
||||
assertThat(config.getMaxAge()).isEqualTo(Long.valueOf(3600));
|
||||
}
|
||||
|
||||
@@ -90,6 +91,7 @@ public class CorsRegistryTests {
|
||||
assertThat(config.getAllowedHeaders()).isEqualTo(Collections.singletonList("*"));
|
||||
assertThat(config.getExposedHeaders()).isEmpty();
|
||||
assertThat(config.getAllowCredentials()).isNull();
|
||||
assertThat(config.getAllowPrivateNetwork()).isNull();
|
||||
assertThat(config.getMaxAge()).isEqualTo(Long.valueOf(1800));
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user