Microservices: Request Routing with Zuul Proxy (Spring Boot + Spring Cloud + Netflix Zuul)

 

In this article, i am going to how to create two microservices and expose them through Netflix Zuul Proxy.  Here i will show you step by step guide on setting up the Zuul proxy and routing the client requests to the related microservices.

 

What is Zuul and  importance of reverse proxy?

Zuul is an api gateway (or rather Reverse Proxy) comes under the Netflix OSS stack. If you want to know the importance of reverse proxy in microservices architecture or know about Zuul,  Please click here  to refer my article on that.  It is recommended to go through that article, before moving forward with this article.

 

Source Code

The fully source code related to this article can be found at GitHub. Click here to get it.

 

Setting up Microservices

In order to demonstrate the capabilities of Zuul proxy, i will set up two spring boot applications as microservices.

  • student-service
  • course-service

For the simplicity of this article, i will just post only the important code segments of above micorservices here. If you want to go thorough full application code, please get the source from the GitHub.

Important: First of all, i need to emphasize that all the REST endpoints are not properly implemented and they just contain few hardcoded values. The purpose of this article is to demonstrate the capabilities of the Zuul proxy in the context of Routing.  If your real project implementation, you can follow the best practices and standards to implement the controller logic as your wish. Here i have just set up few controllers and RESTFul endpoints for the demonstration purpose. 

 

student-service

Lets look at the StudentControlller.

 

The REST endpoints exposed in the StudentController can be listed as below.

#getting the name of the controller
GET  http://localhost:8081/name

#getting the student by student Id
GET  http://localhost:8081/students/{student_id}

#getting a list of students by course id
GET  http://localhost:8081/courses/{course_id}/students

#getting a list of students who are registered for a particular course in the particular department. 
GET  http://localhost:8081/departments/{department_id}/courses/{course_id}/students

 

You can see that the  REST endpoints contains simple URI Path (Resource Path) to some complex URI path with set of path variables. I have added those endpoints intentionally to show you how to map the routes for the those endpoints  in Zuul Proxy.

The student-service can be up and run with following command.  It will run on port 8081.

mvn spring-boot:run

 

 

course-service

Lets look at the CourseController

 

The REST endpoints exposed in the CourseController can be listed as below.

#getting the all courses
GET  http://localhost:8082/courses

#getting the course by course_id
GET  http://localhost:8081/courses/{course_id}

 

The course-service can be up and run with following command.  It will run on port 8082.

mvn spring-boot:run

 

 

Setting up the Zuul Proxy

I know that most people are curiously waited until i start this section of the article. and lets start it now.

 

How to create the Zuul Proxy?

Just believe me that Zuul proxy is just another spring boot application. It has the Spring Cloud Netflix Zuul on its classpath dependencies and annotated the main SpringBootApplication configuration class with @EnableZuulProxy annotation.

 

Lets create our Zuul Proxy application.

Go to https://start.spring.io/ and generate a Spring Boot Application with dependency Zuul. Please refer the below screen shot.

Screen Shot 2018-03-11 at 1.51.58 PM.png

 

Then open the generated project and annotate the main spring boot application configuration with @EnableZuulProxy annotation.

 

Lets change the port of the Zuul Proxy application into any port that is not in use. Here i will change it to 7070.

The Zuul Proxy can be up and run with following command.

mvn spring-boot:run

 

 

Route mapping with Zuul.

We have set up two microservices in our local server. one is running on port 8081 and other one is running on port 8082.  We need to expose those two microservices through the Zuul proxy running on port 7070.  These route mapping can be done in the application.properties file in the Zuul Proxy Application.

 

Lets look at how the REST endpoints in the student-service will be exposed through the Zuul proxy.

 

1.  URI resource mapping for  http://localhost:8081/name (No Path Variable)

zuul.routes.website-name.url = http://localhost:8081/name

Here you can see that it is a simple URI mapping. There is no path variable associated with it.  According to the above route mapping, it will consider the website-name as the default route mapping. Therefore any request for the /website-name will be redirected to the http://localhost:8081/name.

e.g:-  http://localhost:7070/website-name  SEND TO http://localhost:8081/name

Since there is no path mapping, the path will be considered as “website-name

Screen Shot 2018-03-11 at 8.13.44 PM

 

 

2.  URI resource mapping for  http://localhost:8081/students/{student_id}

You can notice that there is a path variable exists in the URI resource path. Therefore we need to do the “path” mapping too.

zuul.routes.students.path = /students/*
zuul.routes.students.url = http://localhost:8081/students

According to the above route mapping, any request for the /students/* will be directed to http://localhost:8081/students. (This is applicable for any request that matches the above pattern)

Therefore http://localhost:7070/students/1  will be directed to http://localhost:8081/students/1

Screen Shot 2018-03-11 at 8.16.34 PM

 

 

3. URI resource mapping for http://localhost:8081/courses/{course_id}/students

zuul.routes.students-courses.path = /courses/*/students
zuul.routes.students-courses.url = http://localhost:8081/courses

According to the above mapping any request that matches the /courses/*/students pattern will be directed to the url declared along with path variables.

The request for http://localhost:7070/courses/1/students will be directed to the http://localhost:8081/courses/1/students.

I know that now you are confused and thinking of why the URL path doest not start with /students-courses? It is the name that we have used to declare the URL (zuul.routes.students-courses.url).

Keep it in your mind that if there is a path declared in the application.properties file, that path will be considered.  If there is no path declared, then it will consider the name defined in the url mapping as the path. (This is the default behavior)

Screen Shot 2018-03-11 at 8.33.41 PM

 

 

4. http://localhost:8081/departments/{department_id}/courses/{course_id}/students

Here you can see that there are two path variables are available.

zuul.routes.department-courses-students.path = /departments/*/courses/*/students
zuul.routes.department-courses-students.url = http://localhost:8081/departments

Any request that matches the /departments//courses//students pattern, will be redirected to the endpoint http://localhost:8081/departments//courses//students URL along with path variables.

e.g:- http://localhost:7070/departments/1/courses/2/students  WILL BE DIRECTED TO http://localhost:8081/departments/1/courses/2/students

Screen Shot 2018-03-11 at 8.35.28 PM

 

Now we have completed the route mapping for all the REST services published in the student-service. Now lets look at how the REST endpoints in the course-service will be  exposed through the Zuul proxy.

 

In the course-service, there are only two REST endpoints. we can do just one simple mapping for both of those endpoints.

# zuul route mapping for the course-service
zuul.routes.courses.url = http://localhost:8082/courses

According to the above route mapping, any request for the /courses will be directed to the http://localhost:8082/courses url

 

http://localhost:7070/courses will forward to http://localhost:8082/courses

Screen Shot 2018-03-11 at 8.37.46 PM

 

http://localhost:7070/courses/1 will forward to http://localhost:8082/courses/1

Screen Shot 2018-03-11 at 8.44.54 PM

 

In this article, i have guided you on exposing the micro services with through Zuul Proxy with Simple URI resource mapping (no path variables) to some complex URI resource mapping (with multiple path variables)

If you want to learn more about Spring Cloud Zuul Proxy,  please click following link to visit the official documentation.

Click here to visit the Spring Cloud Documentation on Routing and Filtering with Zuul

2 thoughts on “Microservices: Request Routing with Zuul Proxy (Spring Boot + Spring Cloud + Netflix Zuul)

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Google+ photo

You are commenting using your Google+ account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

w

Connecting to %s