diff --git a/spring-cloud-gateway-core/src/main/java/org/springframework/cloud/gateway/actuate/GatewayEndpoint.java b/spring-cloud-gateway-core/src/main/java/org/springframework/cloud/gateway/actuate/GatewayEndpoint.java index 4363ed76..eca32166 100644 --- a/spring-cloud-gateway-core/src/main/java/org/springframework/cloud/gateway/actuate/GatewayEndpoint.java +++ b/spring-cloud-gateway-core/src/main/java/org/springframework/cloud/gateway/actuate/GatewayEndpoint.java @@ -128,21 +128,22 @@ public class GatewayEndpoint implements ApplicationEventPublisherAware {/*extend http POST :8080/admin/gateway/routes/apiaddreqhead uri=http://httpbin.org:80 predicates:='["Host=**.apiaddrequestheader.org", "Path=/headers"]' filters:='["AddRequestHeader=X-Request-ApiFoo, ApiBar"]' */ @PostMapping("/routes/{id}") + @SuppressWarnings("unchecked") public Mono> save(@PathVariable String id, @RequestBody Mono route) { return this.routeDefinitionWriter.save(route.map(r -> { r.setId(id); log.debug("Saving route: " + route); return r; - })).then(() -> + })).then(Mono.defer(() -> Mono.just(ResponseEntity.created(URI.create("/routes/"+id)).build()) - ); + )); } @DeleteMapping("/routes/{id}") public Mono> delete(@PathVariable String id) { return this.routeDefinitionWriter.delete(Mono.just(id)) - .then(() -> Mono.just(ResponseEntity.ok().build())) - .otherwise(t -> t instanceof NotFoundException, t -> Mono.just(ResponseEntity.notFound().build())); + .then(Mono.defer(() -> Mono.just(ResponseEntity.ok().build()))) + .onErrorResume(t -> t instanceof NotFoundException, t -> Mono.just(ResponseEntity.notFound().build())); } @GetMapping("/routes/{id}") @@ -151,7 +152,7 @@ http POST :8080/admin/gateway/routes/apiaddreqhead uri=http://httpbin.org:80 pre .filter(route -> route.getId().equals(id)) .singleOrEmpty() .map(route -> ResponseEntity.ok(route)) - .otherwiseIfEmpty(Mono.just(ResponseEntity.notFound().build())); + .switchIfEmpty(Mono.just(ResponseEntity.notFound().build())); } @GetMapping("/routes/{id}/combinedfilters") diff --git a/spring-cloud-gateway-core/src/main/java/org/springframework/cloud/gateway/filter/WriteResponseFilter.java b/spring-cloud-gateway-core/src/main/java/org/springframework/cloud/gateway/filter/WriteResponseFilter.java index 0f88ada1..985671d6 100644 --- a/spring-cloud-gateway-core/src/main/java/org/springframework/cloud/gateway/filter/WriteResponseFilter.java +++ b/spring-cloud-gateway-core/src/main/java/org/springframework/cloud/gateway/filter/WriteResponseFilter.java @@ -51,7 +51,7 @@ public class WriteResponseFilter implements GlobalFilter, Ordered { public Mono filter(ServerWebExchange exchange, WebFilterChain chain) { // NOTICE: nothing in "pre" filter stage as CLIENT_RESPONSE_ATTR is not added // until the WebHandler is run - return chain.filter(exchange).then(() -> { + return chain.filter(exchange).then(Mono.defer(() -> { HttpClientResponse clientResponse = getAttribute(exchange, CLIENT_RESPONSE_ATTR, HttpClientResponse.class); if (clientResponse == null) { return Mono.empty(); @@ -67,7 +67,7 @@ public class WriteResponseFilter implements GlobalFilter, Ordered { .map(factory::wrap); return response.writeWith(body); - }); + })); } } diff --git a/spring-cloud-gateway-core/src/main/java/org/springframework/cloud/gateway/filter/factory/RedirectToWebFilterFactory.java b/spring-cloud-gateway-core/src/main/java/org/springframework/cloud/gateway/filter/factory/RedirectToWebFilterFactory.java index a88bc824..b394f235 100644 --- a/spring-cloud-gateway-core/src/main/java/org/springframework/cloud/gateway/filter/factory/RedirectToWebFilterFactory.java +++ b/spring-cloud-gateway-core/src/main/java/org/springframework/cloud/gateway/filter/factory/RedirectToWebFilterFactory.java @@ -61,7 +61,7 @@ public class RedirectToWebFilterFactory implements WebFilterFactory { } return (exchange, chain) -> - chain.filter(exchange).then(() -> { + chain.filter(exchange).then(Mono.defer(() -> { if (!exchange.getResponse().isCommitted()) { setResponseStatus(exchange, httpStatus); @@ -70,7 +70,7 @@ public class RedirectToWebFilterFactory implements WebFilterFactory { return response.setComplete(); } return Mono.empty(); - }); + })); } } diff --git a/spring-cloud-gateway-core/src/main/java/org/springframework/cloud/gateway/filter/factory/SetStatusWebFilterFactory.java b/spring-cloud-gateway-core/src/main/java/org/springframework/cloud/gateway/filter/factory/SetStatusWebFilterFactory.java index c4efefce..570a3ed5 100644 --- a/spring-cloud-gateway-core/src/main/java/org/springframework/cloud/gateway/filter/factory/SetStatusWebFilterFactory.java +++ b/spring-cloud-gateway-core/src/main/java/org/springframework/cloud/gateway/filter/factory/SetStatusWebFilterFactory.java @@ -56,13 +56,13 @@ public class SetStatusWebFilterFactory implements WebFilterFactory { return chain.filter(exchange);*/ // option 2 (runs in reverse filter order) - return chain.filter(exchange).then(() -> { + return chain.filter(exchange).then(Mono.defer(() -> { // check not really needed, since it is guarded in setStatusCode, but it's a good example if (!exchange.getResponse().isCommitted()) { setResponseStatus(exchange, httpStatus); } return Mono.empty(); - }); + })); }; } diff --git a/spring-cloud-gateway-core/src/main/java/org/springframework/cloud/gateway/handler/RoutePredicateHandlerMapping.java b/spring-cloud-gateway-core/src/main/java/org/springframework/cloud/gateway/handler/RoutePredicateHandlerMapping.java index 8e2c4de1..8d70cfe5 100644 --- a/spring-cloud-gateway-core/src/main/java/org/springframework/cloud/gateway/handler/RoutePredicateHandlerMapping.java +++ b/spring-cloud-gateway-core/src/main/java/org/springframework/cloud/gateway/handler/RoutePredicateHandlerMapping.java @@ -58,12 +58,12 @@ public class RoutePredicateHandlerMapping extends AbstractHandlerMapping { exchange.getAttributes().put(GATEWAY_ROUTE_ATTR, r); return Mono.just(webHandler); - }).otherwiseIfEmpty(Mono.empty().then(() -> { + }).switchIfEmpty(Mono.empty().then(Mono.defer(() -> { if (logger.isTraceEnabled()) { logger.trace("No RouteDefinition found for [" + getExchangeDesc(exchange) + "]"); } return Mono.empty(); - })); + }))); } //TODO: get desc from factory? diff --git a/spring-cloud-gateway-core/src/test/java/org/springframework/cloud/gateway/test/GatewayIntegrationTests.java b/spring-cloud-gateway-core/src/test/java/org/springframework/cloud/gateway/test/GatewayIntegrationTests.java index aabb9cfe..a5e10fc0 100644 --- a/spring-cloud-gateway-core/src/test/java/org/springframework/cloud/gateway/test/GatewayIntegrationTests.java +++ b/spring-cloud-gateway-core/src/test/java/org/springframework/cloud/gateway/test/GatewayIntegrationTests.java @@ -64,7 +64,7 @@ public class GatewayIntegrationTests extends BaseWebClientTests { Mono result = webClient.post() .uri("/headers") .contentType(MediaType.APPLICATION_JSON_UTF8) - .body("testdata") + .syncBody("testdata") .header("Host", "www.complexcontenttype.org") .exchange() .flatMap(response -> response.body(toMono(Map.class))); diff --git a/spring-cloud-gateway-core/src/test/java/org/springframework/cloud/gateway/test/PostTests.java b/spring-cloud-gateway-core/src/test/java/org/springframework/cloud/gateway/test/PostTests.java index 1f180ddd..15b4d35a 100644 --- a/spring-cloud-gateway-core/src/test/java/org/springframework/cloud/gateway/test/PostTests.java +++ b/spring-cloud-gateway-core/src/test/java/org/springframework/cloud/gateway/test/PostTests.java @@ -47,7 +47,7 @@ public class PostTests extends BaseWebClientTests { Mono result = webClient.post() .uri("/post") .header("Host", "www.example.org") - .body("testdata") + .syncBody("testdata") .exchange() .flatMap(response -> response.body(toMono(Map.class)));