- To demonstrate using Zuul to route requests to services, we'll first create a basic Java application that will serve as our edge proxy service. The Java project Spring Cloud provides an embedded Zuul service, making it pretty simple to create a service that uses the zuul library. We'll start by creating a basic Java application. Create the build.gradle file with the following content:
group 'com.packtpub.microservices'
version '1.0-SNAPSHOT'
buildscript {
repositories {
mavenCentral()
}
dependencies {
classpath "org.springframework.boot:spring-boot-gradle-plugin:1.4.4.RELEASE"
classpath "io.spring.gradle:dependency-management-plugin:0.5.6.RELEASE"
}
}
apply plugin: 'java'
apply plugin: 'org.springframework.boot'
apply plugin: 'io.spring.dependency-management'
sourceCompatibility = 1.8
repositories {
mavenCentral()
}
dependencyManagement {
imports {
mavenBom 'org.springframework.cloud:spring-cloud-netflix:1.4.4.RELEASE'
}
}
dependencies {
compile group: 'org.springframework.boot', name: 'spring-boot-starter-web', version: '1.4.4.RELEASE'
compile group: 'org.springframework.cloud', name: 'spring-cloud-starter-zuul'
testCompile group: 'junit', name: 'junit', version: '4.12'
}
- Create a single class called EdgeProxyApplication. This will serve as the entry point to our application:
package com.packtpub.microservices.ch02.edgeproxy;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.netflix.zuul.EnableZuulProxy;
@EnableZuulProxy
@SpringBootApplication
public class EdgeProxyApplication {
public static void main(String[] args) {
SpringApplication.run(EdgeProxyApplication.class, args);
}
}
- Create a file called application.yml in the src/main/resources directory of your application. This file will specify your route configurations. In this example, we'll imagine that our monolith application can be accessed on the monolith.pichat-int.me internal host and we want to expose the /signup and /auth/login paths to the public internet:
zuul:
routes:
signup:
path: /signup
url: http://monolith.pichat-int.me
auth:
path: /auth/login
url: http://monolith.pichat-int.me
- Start the project with ./gradlew bootRun and you should be able to access the /signup and /auth/login URLs, which will be proxied to our monolith application.
- We want to expose the attachment-service URLs to the internet. The attachment service exposes the following endpoints:
POST / # Creates an attachment
GET / # Fetch attachments, can filter by message_id
DELETE /:attachment_id # Deletes the specified attachment
GET /:id # Get the specific attachment
- We'll need to decide which paths we want to use in our public API. Modify application.properties to add the following entries:
zuul:
routes:
signup:
path: /signup
url: http://monolith.pichat-int.me
auth:
path: /auth/login
url: http://monolith.pichat-int.me
attachments:
path: /attachments/**
url: http://attachment-service.pichat-int.me
- Now all requests to /attachments/* will be forwarded to the attachment service and signup, and auth/login will continue to be served by our monolith application.
- We can test this by running our service locally and sending requests to localhost:8080/signup, localhost:8080/auth/login, and localhost:8080/attachments/foo. You should be able to see that requests are routed to the respected services. Of course, the service will respond with an error because attachment-service.pichat-int.me cannot be resolved, but this shows that the routing is working as expected:
$ curl -D - http://localhost:8080/attachments/foo
HTTP/1.1 500
X-Application-Context: application
Content-Type: application/json;charset=UTF-8
Transfer-Encoding: chunked
Date: Tue, 27 Mar 2018 12:52:21 GMT
Connection: close
{"timestamp":1522155141889,"status":500,"error":"Internal Server Error","exception":"com.netflix.zuul.exception.ZuulException","message":"attachment-service.pichat-int.me"}%