In modern microservices architectures, an API Gateway is essential. It provides a single entry point for multiple services, allowing us to manage routing, security, rate limiting, load balancing, and more. In this article, we’ll explore how to set up a basic API Gateway using Spring Cloud Gateway and direct requests to different endpoints based on paths. We'll also demonstrate how to use filters to manipulate paths dynamically.
Let’s dive into the code!
To follow along, you’ll need:
Create a new Spring Boot project and include the Spring Cloud Gateway dependency. You can do this easily by setting up a new project on Spring Initializr, selecting Spring Boot and Reactive Spring Cloud Gateway under dependencies.
Here's the pom.xml snippet:
<dependencies> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-gateway</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-test</artifactId> <scope>test</scope> </dependency> <dependency> <groupId>io.projectreactor</groupId> <artifactId>reactor-test</artifactId> <scope>test</scope> </dependency> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-contract-stub-runner</artifactId> <scope>test</scope> </dependency> </dependencies>
Let’s configure our Gateway to handle requests for three different paths:
"We’ll use the REST Countries API to simulate the other microservices we have in our architecture."
I've created a folder called router near the application's main file. Inside it, we’ll create a file called Routes.java where we define our routes, configure each path, and apply filters to dynamically direct requests.
package dev.mspilari.api_gateway.router; 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; @Configuration public class Routes { @Bean public RouteLocator routeLocator(RouteLocatorBuilder builder) { return builder.routes() .route("country_route", p -> p .path("/get/country/{name}") .filters(f -> f.setPath("/v3.1/name/{name}")) .uri("https://restcountries.com")) .route("language_route", p -> p .path("/get/language/{name}") .filters(f -> f.setPath("/v3.1/lang/{name}")) .uri("https://restcountries.com")) .route("subregion_route", p -> p .path("/get/subregion/{name}") .filters(f -> f.setPath("/v3.1/subregion/{name}")) .uri("https://restcountries.com")) .build(); } }
Route Definitions: we define each route using the route method, which takes an identifier (e.g., country_route) and a lambda that defines the path.
Path Matching: .path("/get/country/{name}") is used to match the incoming URL pattern. {name} is a variable that can be dynamically replaced by any value, such as a country name like “Brazil”.
Filters: we use SetPath to modify the outgoing request path. For example, .setPath("/v3.1/name/{name}") rewrites /get/country/{name} to /v3.1/name/{name}, the endpoint required by the REST Countries API.
URI: we set the uri to https://restcountries.com, which serves as the base URL. Spring Cloud Gateway will send the modified path to this URI.
Start your Spring Boot application. Now, you can make requests to the Gateway, and it will forward them to the correct endpoint.
Try the following commands in your terminal to test the routes:
<dependencies> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-gateway</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-test</artifactId> <scope>test</scope> </dependency> <dependency> <groupId>io.projectreactor</groupId> <artifactId>reactor-test</artifactId> <scope>test</scope> </dependency> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-contract-stub-runner</artifactId> <scope>test</scope> </dependency> </dependencies>
Each request will be routed by the Gateway to the respective REST Countries API endpoint, based on the path and parameter.
If everything is configured correctly, you should see responses that match what you'd get from directly calling the REST Countries API.
For example:
package dev.mspilari.api_gateway.router; 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; @Configuration public class Routes { @Bean public RouteLocator routeLocator(RouteLocatorBuilder builder) { return builder.routes() .route("country_route", p -> p .path("/get/country/{name}") .filters(f -> f.setPath("/v3.1/name/{name}")) .uri("https://restcountries.com")) .route("language_route", p -> p .path("/get/language/{name}") .filters(f -> f.setPath("/v3.1/lang/{name}")) .uri("https://restcountries.com")) .route("subregion_route", p -> p .path("/get/subregion/{name}") .filters(f -> f.setPath("/v3.1/subregion/{name}")) .uri("https://restcountries.com")) .build(); } }
This setup covers the basics of routing with Spring Cloud Gateway. In the next posts, we'll explore additional features, like:
The above is the detailed content of Building a Simple API Gateway with Spring Cloud Gateway. For more information, please follow other related articles on the PHP Chinese website!