Master Spring Cloud Gateway: Build High‑Performance API Gateways Quickly
This article introduces Spring Cloud Gateway, explains its core concepts such as routes, predicates, and filters, demonstrates how to quickly set up a gateway with both Java‑based and configuration‑based routing, and shows how to create custom global and route‑specific filters for advanced request handling.
Understanding Spring Cloud Gateway
Spring Cloud Gateway is an API gateway built on Spring 5, Project Reactor, and Spring Boot 2. It routes requests, supports security validation, traffic monitoring, and rate limiting, and uses a non‑blocking I/O model for higher concurrency compared to traditional blocking gateways.
When to Use Spring Cloud Gateway
If your microservice architecture is based on Java and Spring, Spring Cloud Gateway provides load balancing, dynamic routing, access control, circuit breaking, and monitoring, making it a natural choice for aggregating and exposing multiple microservice APIs.
Key Concepts
Route : Identified by an ID, target URI, and a set of predicates and filters.
Predicate : A Predicate<ServerWebExchange> that matches request data (e.g., headers, body). If true, the route is selected.
Filter : Implements GatewayFilter to modify request or response, created via a GatewayFilterFactory.
After understanding these concepts, the request flow is: GatewayHandlerMapping receives the client request, matches a route via predicates, processes the request through associated filters, forwards it to the target service, receives the response, passes it through response filters, and finally returns it to the client. Filters execute in order of their order value (smaller = higher priority).
How to Implement API Aggregation
Using Spring Initializr, create a project spring-cloud-gateway-quick-start (Spring Boot 2.3.1, Spring Cloud Hoxton.SR6). Add two downstream services:
// demo-userservice project
@RestController
@RequestMapping("/user")
public class UserServiceController {
@RequestMapping("/get")
public User get() { return User.mock(); }
} // demo-orderservice project
@RestController
@RequestMapping("/order")
public class OrderServiceController {
@RequestMapping("/get")
public Order get() { return Order.mock(); }
}Define routes programmatically:
@SpringBootApplication
public class DemogatewayApplication {
public static void main(String[] args) {
SpringApplication.run(DemogatewayApplication.class, args);
}
@Bean
public RouteLocator customRouteLocator(RouteLocatorBuilder builder) {
return builder.routes()
.route("user-service", r -> r.path("/user/*").uri("http://localhost:8071"))
.route("order-service", r -> r.path("/order/*").uri("http://localhost:8061"))
.build();
}
}Running the gateway and the two services allows calls such as curl http://localhost:8080/user/get and curl http://localhost:8080/order/get to retrieve data from the respective services.
For better maintainability, move the routing definitions to application.properties:
spring.cloud.gateway.routes[0].id=order-service
spring.cloud.gateway.routes[0].uri=http://localhost:8061
spring.cloud.gateway.routes[0].predicates[0].name=Path
spring.cloud.gateway.routes[0].predicates[0].args[pattern]=/order/*
spring.cloud.gateway.routes[1].id=user-service
spring.cloud.gateway.routes[1].uri=http://localhost:8071
spring.cloud.gateway.routes[1].predicates[0].name=Path
spring.cloud.gateway.routes[1].predicates[0].args[pattern]=/user/*Configuration‑based routing simplifies management and enables dynamic updates.
How to Create Custom Filters
Spring Cloud Gateway provides eight built‑in global filters (e.g., ForwardRoutingFilter, ReactiveLoadBalancerClientFilter) and many route‑specific filters. You can also define your own.
Example of a global filter:
@Component
public class CustomGlobalFilter implements GlobalFilter, Ordered {
private Logger log = LoggerFactory.getLogger(CustomGlobalFilter.class);
@Override
public Mono<Void> filter(ServerWebExchange exchange, GatewayFilterChain chain) {
log.info("Executing custom global filter");
return chain.filter(exchange);
}
@Override
public int getOrder() { return -1; }
}Example of a route‑specific filter factory for simple authorization:
@Component
public class MyAuthGatewayFilterFactory extends AbstractGatewayFilterFactory<MyAuthGatewayFilterFactory.Config> {
public MyAuthGatewayFilterFactory() { super(Config.class); }
@Override
public GatewayFilter apply(Config config) {
return (exchange, chain) -> {
ServerHttpRequest request = exchange.getRequest();
String from = request.getQueryParams().getFirst(config.getAuthKey());
if (config.getAuthValue().equals(from)) {
return chain.filter(exchange);
} else {
exchange.getResponse().setStatusCode(HttpStatus.OK);
exchange.getResponse().getHeaders().setContentType(MediaType.valueOf("text/html;charset=utf-8"));
DataBuffer buffer = exchange.getResponse().bufferFactory()
.wrap(config.getAuthFailMsg().getBytes(StandardCharsets.UTF_8));
return exchange.getResponse().writeWith(Flux.just(buffer));
}
};
}
public static class Config {
private String authKey = "from";
private String authValue = "system";
private String authFailMsg = "授权失败";
// getters and setters omitted for brevity
}
}Register the filter for a route in application.properties:
spring.cloud.gateway.routes[1].filters[0].name=MyAuthAfter restarting, accessing http://localhost:8080/user/get?from=system succeeds, while requests without the correct query parameter return the authorization‑failure message.
The full source code is available on GitHub: https://github.com/wrcj12138aaa/spring-cloud-gateway-quick-start.
Signed-in readers can open the original source through BestHub's protected redirect.
This article has been distilled and summarized from source material, then republished for learning and reference. If you believe it infringes your rights, please contactand we will review it promptly.
Programmer DD
A tinkering programmer and author of "Spring Cloud Microservices in Action"
How this landed with the community
Was this worth your time?
0 Comments
Thoughtful readers leave field notes, pushback, and hard-won operational detail here.
