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

Encoded slash in path variable causes error 400 in WebFlux - regression in Spring Boot 3.3.5 #42907

Closed
kdebski85 opened this issue Oct 28, 2024 · 4 comments
Labels
for: external-project For an external project and not something we can fix status: invalid An issue that we don't feel is valid

Comments

@kdebski85
Copy link

I develop a Spring WebFlux application with Netty.
After upgrade of Spring Boot from 3.3.4 to 3.3.5, http status 400 is returned when a path contains encoded slash.
The encoded slash is a part of path variable.

For example, the following endpoint returns status 400 for GET /api/a%2Fb/foo in 3.3.5.

    @GetMapping(path = "/api/{param}/foo", produces = APPLICATION_JSON_VALUE)
    public Mono<String> foo(@PathVariable String param) {
        return Mono.just(param);
    }

In 3.3.4, exactly same request returned 200 with a/b in the response.

@spring-projects-issues spring-projects-issues added the status: waiting-for-triage An issue we've not yet triaged label Oct 28, 2024
@bclozel
Copy link
Member

bclozel commented Oct 28, 2024

I assume there is something else going on.
I cannot reproduce this behavior.

import reactor.core.publisher.Mono;

import org.springframework.http.MediaType;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RestController;

@RestController
public class TestController {

	@GetMapping(path = "/api/{param}/foo", produces = MediaType.TEXT_PLAIN_VALUE)
	public Mono<String> foo(@PathVariable String param) {

		return Mono.just(param);
	}
}
curl -v http://localhost:8080/api/a%2Fb/foo
* Host localhost:8080 was resolved.
* IPv6: ::1
* IPv4: 127.0.0.1
*   Trying [::1]:8080...
* Connected to localhost (::1) port 8080
> GET /api/a%2Fb/foo HTTP/1.1
> Host: localhost:8080
> User-Agent: curl/8.7.1
> Accept: */*
>
* Request completely sent off
< HTTP/1.1 200 OK
< Content-Type: text/plain;charset=UTF-8
< Content-Length: 3
<
* Connection #0 to host localhost left intact
a/b%      

Maybe your application has Spring Security configured?
In this case, this is probably due to the recent introduction of ServerWebExchangeFirewall, see spring-projects/spring-security#15991. In this case, the reference documentation might help you with this or you can reach out to the Spring Security team.

@bclozel bclozel closed this as not planned Won't fix, can't repro, duplicate, stale Oct 28, 2024
@bclozel bclozel added status: invalid An issue that we don't feel is valid for: external-project For an external project and not something we can fix and removed status: waiting-for-triage An issue we've not yet triaged labels Oct 28, 2024
@kdebski85
Copy link
Author

I debugged that the issue is caused by org.springframework.security.web.server.firewall.StrictServerWebExchangeFirewall and downgrading to org.springframework.security:spring-security-web:6.3.3 resolves it.

I found that there is a method
https://docs.spring.io/spring-security/reference/6.4-SNAPSHOT/api/java/org/springframework/security/web/server/firewall/StrictServerWebExchangeFirewall.html#setAllowUrlEncodedSlash(boolean)

Why such breaking change was introduced in a hotfix version?
How to configure StrictServerWebExchangeFirewall in Spring Boot?

@bclozel
Copy link
Member

bclozel commented Oct 28, 2024

Why such breaking change was introduced in a hotfix version?
How to configure StrictServerWebExchangeFirewall in Spring Boot?

I guess those are questions for the Spring Security team. Maybe ask this question on StackOverflow?
Have you tried contributing your own StrictServerWebExchangeFirewall bean to the application context?

@kdebski85
Copy link
Author

I tried my custom StrictServerWebExchangeFirewall, but it was unused.

The issue was that setting the firewall was added after the release:
spring-projects/spring-security@3ba1263

For a time being, I will use BeanPostProcessor approach mentioned at:
spring-projects/spring-security#15974

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
for: external-project For an external project and not something we can fix status: invalid An issue that we don't feel is valid
Projects
None yet
Development

No branches or pull requests

3 participants