We looked at Spring Cloud Gateway as a powerful tool for implementing an API Gateway. Then we installed it, added the basic dependencies, and set up the first simple route.
In this lecture we'll create route configurations in Spring Cloud Gateway that forward requests to different microservices. We'll add filters to process requests and responses, implement request rate limiting, and enable CORS (cross-origin requests). We'll also test our setup to make sure everything works as expected.
1. Configuring advanced routes
Routes (routes) are the core of the Gateway. Each route defines:
- Predicates (predicates), which decide which requests to route (for example, filtering by path or HTTP method).
- Filters (filters), which modify or augment requests and responses.
- URI where to forward the requests.
Let's add a few routes for our microservice system.
Step 1: Project setup
Make sure your project already has dependencies for Spring Cloud Gateway. If not, add them to your pom.xml:
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-gateway</artifactId>
</dependency>
Of course, don't forget to update your dependencies (for example with mvn clean install).
Step 2: Configure routes in application.yml
Example application.yml with several routes:
spring:
cloud:
gateway:
routes:
- id: user-service-route
uri: http://localhost:8081
predicates:
- Path=/users/**
filters:
- StripPrefix=1
- id: order-service-route
uri: http://localhost:8082
predicates:
- Path=/orders/**
filters:
- AddResponseHeader=X-Custom-Header, OrderService
- id: product-service-route
uri: lb://product-service
predicates:
- Path=/products/**
Here:
id: Unique identifier for the route.uri: Address of the service where the request will be routed.- Here
http://localhost:8081means requests to/users/**will be forwarded to the User Service listening on port 8081. lb://product-servicemeans using the load balancer (Eureka integration if present).
- Here
predicates: Routing condition.- For example,
Path=/users/**means requests with that path go to the user service.
- For example,
filters: Additional request and response transformations.StripPrefix=1removes the first segment of the route (/users) before sending the request to the backend.AddResponseHeaderadds a custom HTTP header to the response.
Step 3: Run and test
After configuring routes, start the application and test how it works:
- For User Service: Send a request to
http://localhost:8080/users/1and make sure it gets forwarded tohttp://localhost:8081/1. - For Order Service: Make sure the response contains the header
X-Custom-Header: OrderService.
Use Postman or the curl command for testing:
curl -v http://localhost:8080/users/1
curl -v http://localhost:8080/orders/123
2. Adding filters
Filters let you modify requests and responses. You can add headers, change request content, and also perform authentication.
Example: request logging
Add a filter for logging requests:
spring:
cloud:
gateway:
routes:
- id: logging-route
uri: http://localhost:8081
predicates:
- Path=/logging/**
filters:
- name: RequestLoggingFilter
Create the filter:
import org.springframework.cloud.gateway.filter.GatewayFilter;
import org.springframework.cloud.gateway.filter.factory.AbstractGatewayFilterFactory;
import org.springframework.stereotype.Component;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
@Component
public class RequestLoggingFilter extends AbstractGatewayFilterFactory<RequestLoggingFilter.Config> {
private static final Logger logger = LoggerFactory.getLogger(RequestLoggingFilter.class);
public RequestLoggingFilter() {
super(Config.class);
}
@Override
public GatewayFilter apply(Config config) {
return (exchange, chain) -> {
logger.info("Request Path: " + exchange.getRequest().getPath());
return chain.filter(exchange);
};
}
public static class Config {
// Filter configuration (if needed)
}
}
3. Rate limiting
Rate limiting helps avoid overloading services. For this we use the RedisRateLimiter filter.
Step 1: Add Redis dependency
Add the dependency:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-redis-reactive</artifactId>
</dependency>
Step 2: Configure the Rate Limiter filter
Modify application.yml:
spring:
cloud:
gateway:
routes:
- id: rate-limited-route
uri: http://localhost:8081
predicates:
- Path=/rate-limited/**
filters:
- name: RequestRateLimiter
args:
redis-rate-limiter.replenishRate: 10
redis-rate-limiter.burstCapacity: 20
Here:
replenishRate: Number of requests that can be processed per second.burstCapacity: Maximum number of requests allowed in the "burst".
4. CORS (Cross-Origin Resource Sharing) support
If your frontend and backend are on different domains, enable CORS support.
Step 1: Configure CORS in the config
Add to application.yml:
spring:
cloud:
gateway:
globalcors:
corsConfigurations:
'[/**]':
allowedOrigins: "http://localhost:3000"
allowedMethods:
- GET
- POST
- PUT
- DELETE
Now requests from http://localhost:3000 to your Gateway will be allowed.
5. Testing and validation
- Check each route using Postman.
- Make sure headers are added correctly.
- Test rate limiting by sending many requests in a row and ensure excess requests get blocked.
6. Common mistakes and how to avoid them
- Error 404: the route isn't configured correctly. Check your predicate conditions.
- Missing filters: make sure filters are actually applied to the route.
- CORS issues: verify
allowedOriginsandallowedMethodsin the configuration.
Tip: always check the logs first to see how the API Gateway is processing requests.
Now you know how to configure complex routes with Spring Cloud Gateway, add filters, and manage requests. With these skills you'll be able to route traffic in a microservice application while keeping security and performance in mind.
GO TO FULL VERSION