Set best matching pattern attribute in WebMvc.fn
Prior to this commit, the `RouterFunctionMapping` WebFlux.fn variant would set the `HandlerMapping.BEST_MATCHING_PATTERN_ATTRIBUTE` as an exchange attribute. This is useful for instrumentation purposes. The WebMvc.fn variant would not do the same; this would lead to "UNKNOWN" path metrics tags. This commit ensures that the `RouterFunctionMapping` WebMvc.fn variant does set the `BEST_MATCHING_PATTERN_ATTRIBUTE` and `BEST_MATCHING_HANDLER_ATTRIBUTE` request attributes. Closes gh-26963
This commit is contained in:
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2002-2020 the original author or authors.
|
||||
* Copyright 2002-2021 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -21,33 +21,37 @@ import reactor.core.publisher.Mono;
|
||||
import reactor.test.StepVerifier;
|
||||
|
||||
import org.springframework.http.codec.ServerCodecConfigurer;
|
||||
import org.springframework.web.reactive.HandlerMapping;
|
||||
import org.springframework.web.reactive.function.server.HandlerFunction;
|
||||
import org.springframework.web.reactive.function.server.RouterFunction;
|
||||
import org.springframework.web.reactive.function.server.RouterFunctions;
|
||||
import org.springframework.web.reactive.function.server.ServerRequest;
|
||||
import org.springframework.web.reactive.function.server.ServerResponse;
|
||||
import org.springframework.web.server.ServerWebExchange;
|
||||
import org.springframework.web.testfixture.http.server.reactive.MockServerHttpRequest;
|
||||
import org.springframework.web.testfixture.server.MockServerWebExchange;
|
||||
import org.springframework.web.util.pattern.PathPattern;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
|
||||
/**
|
||||
* @author Arjen Poutsma
|
||||
* @author Brian Clozel
|
||||
*/
|
||||
public class RouterFunctionMappingTests {
|
||||
|
||||
private final ServerWebExchange exchange = MockServerWebExchange.from(MockServerHttpRequest.get("https://example.com/match"));
|
||||
|
||||
private final ServerCodecConfigurer codecConfigurer = ServerCodecConfigurer.create();
|
||||
|
||||
|
||||
@Test
|
||||
public void normal() {
|
||||
void normal() {
|
||||
HandlerFunction<ServerResponse> handlerFunction = request -> ServerResponse.ok().build();
|
||||
RouterFunction<ServerResponse> routerFunction = request -> Mono.just(handlerFunction);
|
||||
|
||||
RouterFunctionMapping mapping = new RouterFunctionMapping(routerFunction);
|
||||
mapping.setMessageReaders(this.codecConfigurer.getReaders());
|
||||
|
||||
Mono<Object> result = mapping.getHandler(this.exchange);
|
||||
Mono<Object> result = mapping.getHandler(createExchange("https://example.com/match"));
|
||||
|
||||
StepVerifier.create(result)
|
||||
.expectNext(handlerFunction)
|
||||
@@ -56,12 +60,12 @@ public class RouterFunctionMappingTests {
|
||||
}
|
||||
|
||||
@Test
|
||||
public void noMatch() {
|
||||
void noMatch() {
|
||||
RouterFunction<ServerResponse> routerFunction = request -> Mono.empty();
|
||||
RouterFunctionMapping mapping = new RouterFunctionMapping(routerFunction);
|
||||
mapping.setMessageReaders(this.codecConfigurer.getReaders());
|
||||
|
||||
Mono<Object> result = mapping.getHandler(this.exchange);
|
||||
Mono<Object> result = mapping.getHandler(createExchange("https://example.com/match"));
|
||||
|
||||
StepVerifier.create(result)
|
||||
.expectComplete()
|
||||
@@ -69,7 +73,7 @@ public class RouterFunctionMappingTests {
|
||||
}
|
||||
|
||||
@Test
|
||||
public void changeParser() throws Exception {
|
||||
void changeParser() throws Exception {
|
||||
HandlerFunction<ServerResponse> handlerFunction = request -> ServerResponse.ok().build();
|
||||
RouterFunction<ServerResponse> routerFunction = RouterFunctions.route()
|
||||
.GET("/foo", handlerFunction)
|
||||
@@ -90,4 +94,36 @@ public class RouterFunctionMappingTests {
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
void mappedRequestShouldHoldAttributes() {
|
||||
HandlerFunction<ServerResponse> handlerFunction = request -> ServerResponse.ok().build();
|
||||
RouterFunction<ServerResponse> routerFunction = RouterFunctions.route()
|
||||
.GET("/match", handlerFunction).build();
|
||||
|
||||
RouterFunctionMapping mapping = new RouterFunctionMapping(routerFunction);
|
||||
mapping.setMessageReaders(this.codecConfigurer.getReaders());
|
||||
|
||||
ServerWebExchange exchange = createExchange("https://example.com/match");
|
||||
Mono<Object> result = mapping.getHandler(exchange);
|
||||
|
||||
StepVerifier.create(result)
|
||||
.expectNext(handlerFunction)
|
||||
.expectComplete()
|
||||
.verify();
|
||||
|
||||
PathPattern matchingPattern = exchange.getAttribute(HandlerMapping.BEST_MATCHING_PATTERN_ATTRIBUTE);
|
||||
assertThat(matchingPattern).isNotNull();
|
||||
assertThat(matchingPattern.getPatternString()).isEqualTo("/match");
|
||||
|
||||
ServerRequest serverRequest = exchange.getAttribute(RouterFunctions.REQUEST_ATTRIBUTE);
|
||||
assertThat(serverRequest).isNotNull();
|
||||
|
||||
HandlerFunction<?> handler = exchange.getAttribute(HandlerMapping.BEST_MATCHING_HANDLER_ATTRIBUTE);
|
||||
assertThat(handler).isEqualTo(handlerFunction);
|
||||
}
|
||||
|
||||
private ServerWebExchange createExchange(String urlTemplate) {
|
||||
return MockServerWebExchange.from(MockServerHttpRequest.get(urlTemplate));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user