Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Mutating a ServerHttpRequest breaks the existing context path #25279

Closed
ltfourrier opened this issue Jun 18, 2020 · 0 comments
Closed

Mutating a ServerHttpRequest breaks the existing context path #25279

ltfourrier opened this issue Jun 18, 2020 · 0 comments
Assignees
Labels
in: web Issues in web modules (web, webmvc, webflux, websocket) type: bug A general bug
Milestone

Comments

@ltfourrier
Copy link

ltfourrier commented Jun 18, 2020

Affects: Spring Framework 5.2.7

Context

I have a WebFlux application with many controllers, and the particular need of having to pre-process and inject additional data in some cases.

In order to do so, a WebFilter is used, and the ServerHttpRequest as well as its containing ServerWebExchange is mutated through their .mutate() methods.

Additionally, I use Spring Boot 2.3.1+, which comes with a new spring.webflux.base-path configuration property that seemingly sets up a ContextPathCompositeHandler to emulate how the context path is handled in, e.g., servlets.

Issue

The problem here is that setting a WebFilter that mutates the incoming ServerHttpRequest seems to break WebFlux applications that are using the new Spring Boot spring.webflux.base-path. Requests end up never being routed to their respective controllers, and the affected URLs will always return a 404 Not Found HTTP response.

While this is a Spring Boot configuration property, I believe that it is caused by an underlying Spring Web bug:

While I'm not 100% sure that this is a bug (this might be intended?), I think that it is fair to expect no information to be lost or changed when a ServerHttpRequest is mutated - except of course the parts that are explicitly written otherwise.

Resolution

I think that changing the mutate() method mentioned above to create a carbon copy of the initial ServerHttpRequest is the way to go - or at least using its getPath().contextPath() as the default context path in DefaultServerHttpRequestBuilder. It would definitely fix the problem, although I'm not entirely sure about backwards compatibility.

As such, and since I wasn't even sure whether it was a bug or not, I wanted to open a discussion first and didn't try to fix it myself - although I would gladly open a pull request if this is confirmed to be a bug and the proposed resolution seems acceptable.

Example

I quickly built a small, straightforward Spring Boot project that reproduces and demonstrates the issue.

demo.zip

Related issues

I only found one similar issue that might be related to this underlying "bug":

@spring-projects-issues spring-projects-issues added the status: waiting-for-triage An issue we've not yet triaged or decided on label Jun 18, 2020
@bclozel bclozel self-assigned this Jun 22, 2020
@bclozel bclozel added type: bug A general bug in: web Issues in web modules (web, webmvc, webflux, websocket) and removed status: waiting-for-triage An issue we've not yet triaged or decided on labels Jun 22, 2020
@bclozel bclozel added this to the 5.2.8 milestone Jun 22, 2020
FelixFly pushed a commit to FelixFly/spring-framework that referenced this issue Aug 16, 2020
This commit ensures that when mutating `ServerHttpRequest` instances,
the original contextPath information is copied to the request being
built.

Note that mutation on the `contextPath(String)` or `path(String)` should
be reflected to the other. (See their Javadoc for more information).

Fixes spring-projectsgh-25279
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
in: web Issues in web modules (web, webmvc, webflux, websocket) type: bug A general bug
Projects
None yet
Development

No branches or pull requests

3 participants