From 6121a385c84067753d40007411414375a10bdc5f Mon Sep 17 00:00:00 2001 From: Garvit Joshi Date: Sat, 1 Aug 2026 04:07:59 +0530 Subject: [PATCH] Allow null contextPath in ServerHttpRequest.Builder The builder method required a non-null contextPath while the underlying field, MutatedServerHttpRequest constructor, and RequestPath.parse all accept null and treat it the same as an empty string. Relax the method parameter to @Nullable so callers can clear the context path directly. closes #37098 Signed-off-by: Garvit Joshi --- .../reactive/DefaultServerHttpRequestBuilder.java | 2 +- .../http/server/reactive/ServerHttpRequest.java | 4 +++- .../http/server/reactive/ServerHttpRequestTests.java | 10 ++++++++++ 3 files changed, 14 insertions(+), 2 deletions(-) diff --git a/spring-web/src/main/java/org/springframework/http/server/reactive/DefaultServerHttpRequestBuilder.java b/spring-web/src/main/java/org/springframework/http/server/reactive/DefaultServerHttpRequestBuilder.java index a09bc19e2d22..f316bc510544 100644 --- a/spring-web/src/main/java/org/springframework/http/server/reactive/DefaultServerHttpRequestBuilder.java +++ b/spring-web/src/main/java/org/springframework/http/server/reactive/DefaultServerHttpRequestBuilder.java @@ -103,7 +103,7 @@ public ServerHttpRequest.Builder path(String path) { } @Override - public ServerHttpRequest.Builder contextPath(String contextPath) { + public ServerHttpRequest.Builder contextPath(@Nullable String contextPath) { this.contextPath = contextPath; return this; } diff --git a/spring-web/src/main/java/org/springframework/http/server/reactive/ServerHttpRequest.java b/spring-web/src/main/java/org/springframework/http/server/reactive/ServerHttpRequest.java index 420087a439fe..5156c299f23f 100644 --- a/spring-web/src/main/java/org/springframework/http/server/reactive/ServerHttpRequest.java +++ b/spring-web/src/main/java/org/springframework/http/server/reactive/ServerHttpRequest.java @@ -146,8 +146,10 @@ interface Builder { * contextPath} and it must match the start of the path of the URI of * the request. That means changing the contextPath, implies also * changing the path via {@link #path(String)}. + *

The given value may be {@code null} or empty to indicate there + * is no context path. */ - Builder contextPath(String contextPath); + Builder contextPath(@Nullable String contextPath); /** * Set or override the specified header values under the given name. diff --git a/spring-web/src/test/java/org/springframework/http/server/reactive/ServerHttpRequestTests.java b/spring-web/src/test/java/org/springframework/http/server/reactive/ServerHttpRequestTests.java index bfa4817483e7..73867f34eb3f 100644 --- a/spring-web/src/test/java/org/springframework/http/server/reactive/ServerHttpRequestTests.java +++ b/spring-web/src/test/java/org/springframework/http/server/reactive/ServerHttpRequestTests.java @@ -194,6 +194,16 @@ void mutateWithExistingContextPath() throws Exception { assertThat(mutated.getURI().getRawPath()).isEqualTo("/other/path"); } + @Test + void mutateContextPathToNull() throws Exception { + ServerHttpRequest request = createRequest("/context/path", "/context"); + + ServerHttpRequest mutated = request.mutate().contextPath(null).build(); + assertThat(mutated.getPath().contextPath().value()).isEmpty(); + assertThat(mutated.getPath().pathWithinApplication().value()).isEqualTo("/context/path"); + assertThat(mutated.getURI().getRawPath()).isEqualTo("/context/path"); + } + @Test void mutateContextPathWithoutUpdatingPathShouldFail() throws Exception { ServerHttpRequest request = createRequest("/context/path", "/context");