DZone
Thanks for visiting DZone today,
Edit Profile
  • Manage Email Subscriptions
  • How to Post to DZone
  • Article Submission Guidelines
Sign Out View Profile
  • Post an Article
  • Manage My Drafts
Over 2 million developers have joined DZone.
Log In / Join
Refcards Trend Reports
Events Video Library
Refcards
Trend Reports

Events

View Events Video Library

Related

  • Spring Cloud Gateway With Service Discovery Using HashiCorp Consul
  • Micronaut vs Spring Boot: A Detailed Comparison
  • Custom Rate Limiting for Microservices
  • Building Threat Intelligence Pipelines Using Python, APIs, and Elasticsearch

Trending

  • The Missing `bandit` for AI Agents: How I Built a Static Analyzer for Prompt Injection
  • Slopsquatting: Building a Scanner That Catches AI-Hallucinated Packages Before They Reach Production
  • Building a Spring AI Assistant With MCP Servers: A Step-by-Step Tutorial
  • Your AI Agent Tests Are Passing, But Your Agent Is Still Broken
  1. DZone
  2. Software Design and Architecture
  3. Integration
  4. How to Build a Real API Gateway With Spring Cloud Gateway and Eureka

How to Build a Real API Gateway With Spring Cloud Gateway and Eureka

Build a real-world API gateway using Spring Cloud Gateway and Eureka Server. Perfect for beginners looking to understand microservices architecture with working code.

By 
Vivek Rajyaguru user avatar
Vivek Rajyaguru
·
Jul. 15, 25 · Tutorial
Likes (2)
Comment
Save
Tweet
Share
6.3K Views

Join the DZone community and get the full member experience.

Join For Free

API gateways are essential in a microservices architecture. 

But building one that's real-world-ready, secure, scalable, and service-aware will require more than just wiring a few annotations.

Let’s be real for a second: Microservices sound exciting, but once you start building them, things get complicated fast.

  • Ever wondered how big systems route traffic between dozens of microservices? 
  • How does the front end know where to call?
  • How do services find each other?
  • How do you avoid exposing every internal service directly?
  • Do we really want to expose every internal service URL to the outside world?
  • How do we centralize things like security, logging, and throttling?

The answer to all of that is an API Gateway + Service Discovery.

This tutorial walks you through building a fully working API Gateway using Spring Cloud Gateway and Eureka. We'll cover not just the code but also the why behind each piece, and you'll walk away with a clean, scalable foundation you can build real apps on 

Why You Need an API Gateway

Here’s the thing: when your app grows, your front end shouldn’t be worrying about which internal service does what or where it is hosted.

An API gateway helps by:

  1. Hiding your internal microservice URLs
  2. Doing service discovery (so things scale and move freely)
  3. Routing requests to the right service
  4. Centralizing security, logging, throttling, etc.

It’s like the receptionist of your microservices office. Everything flows through it,  and it knows where to direct each call.

What We’re Using

Part Tech
API Gateway Spring Cloud Gateway
Service Discovery Netflix Eureka
Backend Services Spring Boot (microservices)
Build Tool Maven


How It’s Going to Work

Each service registers with Eureka, and the gateway fetches the routing info dynamically. That means zero hardcoded URLs.

What Are We Building?

  • Eureka: Our service registry (like Yellow Pages for services)
  • API Gateway: The central entry point that knows where to send traffic
  • Microservices A and B: Two dummy services that return “hello”

Steps

Step 1: Build the Eureka Server

First, create a Spring Boot project called eureka-server.

This is the directory of all your microservices. Services will register here and discover each other. 

Add dependency:

YAML
 
<dependency>
   <groupId>org.springframework.cloud</groupId>
   <artifactId>spring-cloud-starter-netflix-eureka-server</artifactId>
</dependency>


Add annotations:

Java
 
@SpringBootApplication
@EnableEurekaServer
public class ServerApplication {

 public static void main(String[] args) {
  SpringApplication.run(ServerApplication.class, args);
 }

}


@EnableEurekaServer – Turns your app into an Eureka registry 

Config 

Properties files
 
spring.application.name=server
server.port=8761
eureka.client.register-with-eureka=false
eureka.client.fetch-registry=false

Config



Now run the app and open http://localhost:8761, and your registry is live. Congratulations!

Step 2: Create Two Microservices

Let’s create Service 1 and Service 2. Each one will:

  • Register to Eureka
  • Expose one endpoint

 Add dependencies: 

YAML
 
<dependency>
  <groupId>org.springframework.cloud</groupId>
  <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
</dependency>
<dependency>
   <groupId>org.springframework.boot</groupId>
   <artifactId>spring-boot-starter-web</artifactId>
</dependency>


Code for Service 1: 

Java
 
@SpringBootApplication
public class Service1Application {

 public static void main(String[] args) {
  SpringApplication.run(Service1Application.class, args);
 }

}

@RestController
class Service1Controller {
 @GetMapping("/app1/hello")
 public String hello() {
  return "Hello From Service 1";
 }
}


Config

Properties files
 
spring.application.name=service1
server.port=8081
eureka.client.service-url.defaultZone=http://localhost:8761/eureka


Repeat this process for Service 2 (change port to 8082 and name to service2).

Make sure each service exposes a simple endpoint like /hello just so we can test.

Now start them both — you should see both registered on the Eureka dashboard.

Step 3: Create the API Gateway

Create another Spring Boot app called api-gateway.

This is the front door of your system. 

Add dependencies:

YAML
 
<dependency>
  <groupId>org.springframework.cloud</groupId>
  <artifactId>spring-cloud-starter-gateway</artifactId>
</dependency>
<dependency>
  <groupId>org.springframework.cloud</groupId>
  <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
</dependency>


Main class: 

Java
 
@SpringBootApplication
public class GatewayApplication {

 public static void main(String[] args) {
  SpringApplication.run(GatewayApplication.class, args);
 }

}


Config

Properties files
 
server.port=8080

spring.application.name=api-gateway

spring.cloud.gateway.server.webflux.discovery.locator.enabled=true
spring.cloud.gateway.server.webflux.discovery.locator.lower-case-service-id=true


spring.cloud.gateway.routes[0].id=service1
spring.cloud.gateway.routes[0].uri=lb://SERVICE1
spring.cloud.gateway.routes[0].predicates[0]=Path=/app1/**

spring.cloud.gateway.routes[1].id=service2
spring.cloud.gateway.routes[1].uri=http://SERVICE2
spring.cloud.gateway.routes[1].predicates[0]=Path=/app2/**

eureka.client.service-url.defaultZone=http://localhost:8761/eureka/


Here’s what’s happening:

  • You’re telling the gateway to use service discovery via Eureka.
  • The lb://service1 means it’ll use Ribbon-style load balancing.
  • All traffic hitting /service1/** gets routed to the real service.

Start the gateway and test:

  • http://localhost:8080/service1/app1/hello
  • http://localhost:8080/service2/app2/hello

You’ve got routing through an actual gateway, backed by service discovery

And that’s it — you’ve built a discovery-aware, dynamic API Gateway using Spring Cloud Gateway and Eureka.

Most tutorials show you static route setups. But this version is:

  1. Discovery-aware
  2.  Load-balanced (via service ID)
  3. Scalable – deploy more instances, Eureka handles it
  4. Dynamic – add/remove services without code changes

This setup is ideal for real-world projects where services evolve frequently and infrastructure must keep pace without requiring constant redeployment or hard-coded links.

Some Common Errors to Watch Out For

Problem Fix
Service not found Check that it’s registered with the right name
Wrong path pattern Use /service-name/**, not /service-name/*
Case mismatch in service ID Use lower-case-service-id: true in the gateway
Infinite retries or 500s Make sure your services are actually running locally


Possible Next Steps to Go From Here

You now have a working gateway that’s aware of your services and route requests intelligently. 

Now, in the following posts, I will expand this tutorial to add the following points to make it a production-grade application:

  • Add Spring Security + JWT authentication
  • Add circuit breakers using Resilience4j
  • Use Docker and Docker Compose for easy setup
  • Add config server for centralized properties

If you're building microservices seriously, having a smart, flexible API Gateway isn't a nice-to-have, but it’s a must.

Bonus: Want the full code and a downloadable starter project?

Here is the GitHub link: VivekRajyaguru/spring-api-gateway-eureka-demo.

API Spring Cloud

Opinions expressed by DZone contributors are their own.

Related

  • Spring Cloud Gateway With Service Discovery Using HashiCorp Consul
  • Micronaut vs Spring Boot: A Detailed Comparison
  • Custom Rate Limiting for Microservices
  • Building Threat Intelligence Pipelines Using Python, APIs, and Elasticsearch

Partner Resources

×

Comments

The likes didn't load as expected. Please refresh the page and try again.

  • RSS
  • X
  • Facebook

ABOUT US

  • About DZone
  • Support and feedback
  • Community research

ADVERTISE

  • Advertise with DZone

CONTRIBUTE ON DZONE

  • Article Submission Guidelines
  • Become a Contributor
  • Core Program
  • Visit the Writers' Zone

LEGAL

  • Terms of Service
  • Privacy Policy

CONTACT US

  • 3343 Perimeter Hill Drive
  • Suite 215
  • Nashville, TN 37211
  • [email protected]

Let's be friends:

  • RSS
  • X
  • Facebook