Bael 5259 (#11832)
* [BAEL-4849] Article code * [BAEL-4968] Article code * [BAEL-4968] Article code * [BAEL-4968] Article code * [BAEL-4968] Remove extra comments * [BAEL-5259] simple test case * [BAEL-5259] DSL-based rewrite * [BAEL-5259] Code formatting * [BAEL-5259] Test case naming
This commit is contained in:
parent
ab6c6034d4
commit
505a983ae5
|
@ -177,5 +177,21 @@
|
||||||
</plugins>
|
</plugins>
|
||||||
</build>
|
</build>
|
||||||
</profile>
|
</profile>
|
||||||
|
|
||||||
|
<profile>
|
||||||
|
<id>gateway-url-rewrite</id>
|
||||||
|
<build>
|
||||||
|
<plugins>
|
||||||
|
<plugin>
|
||||||
|
<groupId>org.springframework.boot</groupId>
|
||||||
|
<artifactId>spring-boot-maven-plugin</artifactId>
|
||||||
|
<configuration>
|
||||||
|
<mainClass>com.baeldung.springcloudgateway.rewrite.URLRewriteGatewayApplication</mainClass>
|
||||||
|
<jvmArguments>-Dspring.profiles.active=url-rewrite</jvmArguments>
|
||||||
|
</configuration>
|
||||||
|
</plugin>
|
||||||
|
</plugins>
|
||||||
|
</build>
|
||||||
|
</profile>
|
||||||
</profiles>
|
</profiles>
|
||||||
</project>
|
</project>
|
|
@ -0,0 +1,25 @@
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
package com.baeldung.springcloudgateway.rewrite;
|
||||||
|
|
||||||
|
import org.springframework.boot.autoconfigure.SpringBootApplication;
|
||||||
|
import org.springframework.boot.builder.SpringApplicationBuilder;
|
||||||
|
import org.springframework.cloud.gateway.filter.GatewayFilter;
|
||||||
|
|
||||||
|
import reactor.core.publisher.Mono;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @author Baeldung
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
@SpringBootApplication
|
||||||
|
public class URLRewriteGatewayApplication {
|
||||||
|
|
||||||
|
public static void main(String[] args) {
|
||||||
|
new SpringApplicationBuilder(URLRewriteGatewayApplication.class)
|
||||||
|
.profiles("url-rewrite")
|
||||||
|
.run(args);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,43 @@
|
||||||
|
package com.baeldung.springcloudgateway.rewrite.routes;
|
||||||
|
|
||||||
|
import org.springframework.beans.factory.annotation.Value;
|
||||||
|
import org.springframework.cloud.gateway.route.RouteLocator;
|
||||||
|
import org.springframework.cloud.gateway.route.builder.RouteLocatorBuilder;
|
||||||
|
import org.springframework.context.annotation.Bean;
|
||||||
|
import org.springframework.context.annotation.Configuration;
|
||||||
|
import org.springframework.context.annotation.Profile;
|
||||||
|
import org.springframework.http.server.reactive.ServerHttpRequest;
|
||||||
|
|
||||||
|
import static org.springframework.cloud.gateway.support.ServerWebExchangeUtils.GATEWAY_REQUEST_URL_ATTR;
|
||||||
|
import static org.springframework.cloud.gateway.support.ServerWebExchangeUtils.addOriginalRequestUrl;
|
||||||
|
|
||||||
|
import java.util.Random;
|
||||||
|
|
||||||
|
@Configuration
|
||||||
|
@Profile("url-rewrite")
|
||||||
|
public class DynamicRewriteRoute {
|
||||||
|
|
||||||
|
@Value("${rewrite.backend.uri}")
|
||||||
|
private String backendUri;
|
||||||
|
private static Random rnd = new Random();
|
||||||
|
|
||||||
|
@Bean
|
||||||
|
public RouteLocator dynamicZipCodeRoute(RouteLocatorBuilder builder) {
|
||||||
|
return builder.routes()
|
||||||
|
.route("dynamicRewrite", r ->
|
||||||
|
r.path("/v2/zip/**")
|
||||||
|
.filters(f -> f.filter((exchange, chain) -> {
|
||||||
|
ServerHttpRequest req = exchange.getRequest();
|
||||||
|
addOriginalRequestUrl(exchange, req.getURI());
|
||||||
|
String path = req.getURI().getRawPath();
|
||||||
|
String newPath = path.replaceAll(
|
||||||
|
"/v2/zip/(?<zipcode>.*)",
|
||||||
|
"/api/zip/${zipcode}-" + String.format("%03d", rnd.nextInt(1000)));
|
||||||
|
ServerHttpRequest request = req.mutate().path(newPath).build();
|
||||||
|
exchange.getAttributes().put(GATEWAY_REQUEST_URL_ATTR, request.getURI());
|
||||||
|
return chain.filter(exchange.mutate().request(request).build());
|
||||||
|
}))
|
||||||
|
.uri(backendUri))
|
||||||
|
.build();
|
||||||
|
}
|
||||||
|
}
|
|
@ -8,7 +8,7 @@ public class WebFilterGatewayApplication {
|
||||||
|
|
||||||
public static void main(String[] args) {
|
public static void main(String[] args) {
|
||||||
new SpringApplicationBuilder(WebFilterGatewayApplication.class)
|
new SpringApplicationBuilder(WebFilterGatewayApplication.class)
|
||||||
.profiles("webfilters")
|
.profiles("url-rewrite")
|
||||||
.run(args);
|
.run(args);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,8 @@
|
||||||
|
# Enable this profile to disable security
|
||||||
|
spring:
|
||||||
|
autoconfigure:
|
||||||
|
exclude:
|
||||||
|
- org.springframework.boot.autoconfigure.security.servlet.SecurityAutoConfiguration
|
||||||
|
- org.springframework.boot.actuate.autoconfigure.ManagementSecurityAutoConfiguration
|
||||||
|
- org.springframework.boot.autoconfigure.security.reactive.ReactiveSecurityAutoConfiguration
|
||||||
|
- org.springframework.boot.actuate.autoconfigure.security.reactive.ReactiveManagementWebSecurityAutoConfiguration
|
|
@ -0,0 +1,11 @@
|
||||||
|
spring:
|
||||||
|
cloud:
|
||||||
|
gateway:
|
||||||
|
routes:
|
||||||
|
- id: rewrite_v1
|
||||||
|
uri: ${rewrite.backend.uri:http://example.com}
|
||||||
|
predicates:
|
||||||
|
- Path=/v1/customer/**
|
||||||
|
filters:
|
||||||
|
- RewritePath=/v1/customer/(?<segment>.*),/api/$\{segment}
|
||||||
|
|
|
@ -0,0 +1,109 @@
|
||||||
|
package com.baeldung.springcloudgateway.rewrite;
|
||||||
|
|
||||||
|
import static org.junit.Assert.assertTrue;
|
||||||
|
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||||
|
|
||||||
|
import java.io.OutputStream;
|
||||||
|
import java.net.InetSocketAddress;
|
||||||
|
|
||||||
|
import org.junit.AfterClass;
|
||||||
|
import org.junit.jupiter.api.Test;
|
||||||
|
import org.slf4j.Logger;
|
||||||
|
import org.slf4j.LoggerFactory;
|
||||||
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
|
import org.springframework.boot.test.context.SpringBootTest;
|
||||||
|
import org.springframework.boot.test.context.SpringBootTest.WebEnvironment;
|
||||||
|
import org.springframework.boot.web.server.LocalServerPort;
|
||||||
|
import org.springframework.test.context.ActiveProfiles;
|
||||||
|
import org.springframework.test.context.DynamicPropertyRegistry;
|
||||||
|
import org.springframework.test.context.DynamicPropertySource;
|
||||||
|
import org.springframework.test.web.reactive.server.WebTestClient;
|
||||||
|
|
||||||
|
import com.sun.net.httpserver.HttpServer;
|
||||||
|
|
||||||
|
@SpringBootTest(webEnvironment = WebEnvironment.RANDOM_PORT)
|
||||||
|
@ActiveProfiles({ "nosecurity", "url-rewrite" })
|
||||||
|
class URLRewriteGatewayApplicationLiveTest {
|
||||||
|
|
||||||
|
// NOTE for Eclipse users: By default, Eclipse will complain about com.sun.** classes.
|
||||||
|
// To solve this issue, follow instructions available at the :
|
||||||
|
// https://stackoverflow.com/questions/13155734/eclipse-cant-recognize-com-sun-net-httpserver-httpserver-package
|
||||||
|
private static HttpServer mockServer;
|
||||||
|
private static Logger log = LoggerFactory.getLogger(URLRewriteGatewayApplicationLiveTest.class);
|
||||||
|
|
||||||
|
// Create a running HttpServer that echoes back the request URL.
|
||||||
|
private static HttpServer startTestServer() {
|
||||||
|
|
||||||
|
try {
|
||||||
|
log.info("[I26] Starting mock server");
|
||||||
|
mockServer = HttpServer.create();
|
||||||
|
mockServer.bind(new InetSocketAddress(0), 0);
|
||||||
|
mockServer.createContext("/api", (xchg) -> {
|
||||||
|
String uri = xchg.getRequestURI()
|
||||||
|
.toString();
|
||||||
|
log.info("[I23] Backend called: uri={}", uri);
|
||||||
|
xchg.getResponseHeaders()
|
||||||
|
.add("Content-Type", "text/plain");
|
||||||
|
xchg.sendResponseHeaders(200, 0);
|
||||||
|
OutputStream os = xchg.getResponseBody();
|
||||||
|
os.write(uri.getBytes());
|
||||||
|
os.flush();
|
||||||
|
os.close();
|
||||||
|
});
|
||||||
|
|
||||||
|
mockServer.start();
|
||||||
|
InetSocketAddress localAddr = mockServer.getAddress();
|
||||||
|
log.info("[I36] mock server started: local address={}", localAddr);
|
||||||
|
|
||||||
|
return mockServer;
|
||||||
|
} catch (Exception ex) {
|
||||||
|
throw new RuntimeException(ex);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
// TIP: https://www.baeldung.com/spring-dynamicpropertysource
|
||||||
|
@DynamicPropertySource
|
||||||
|
static void registerBackendServer(DynamicPropertyRegistry registry) {
|
||||||
|
registry.add("rewrite.backend.uri", () -> {
|
||||||
|
HttpServer s = startTestServer();
|
||||||
|
return "http://localhost:" + s.getAddress().getPort();
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
@AfterClass
|
||||||
|
public static void stopMockBackend() throws Exception {
|
||||||
|
log.info("[I40] Shutdown mock http server");
|
||||||
|
mockServer.stop(5);
|
||||||
|
}
|
||||||
|
|
||||||
|
@LocalServerPort
|
||||||
|
private int localPort;
|
||||||
|
|
||||||
|
@Test
|
||||||
|
void testWhenApiCall_thenRewriteSuccess(@Autowired WebTestClient webClient) {
|
||||||
|
webClient.get()
|
||||||
|
.uri("http://localhost:" + localPort + "/v1/customer/customer1")
|
||||||
|
.exchange()
|
||||||
|
.expectBody()
|
||||||
|
.consumeWith((result) -> {
|
||||||
|
String body = new String(result.getResponseBody());
|
||||||
|
log.info("[I99] body={}", body);
|
||||||
|
assertEquals("/api/customer1", body);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
void testWhenDslCall_thenRewriteSuccess(@Autowired WebTestClient webClient) {
|
||||||
|
webClient.get()
|
||||||
|
.uri("http://localhost:" + localPort + "/v2/zip/123456")
|
||||||
|
.exchange()
|
||||||
|
.expectBody()
|
||||||
|
.consumeWith((result) -> {
|
||||||
|
String body = new String(result.getResponseBody());
|
||||||
|
log.info("[I99] body={}", body);
|
||||||
|
assertTrue(body.matches("/api/zip/123456-\\d{3}"));
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
Loading…
Reference in New Issue