当消费者调用提供者时由于各种原因出现无法调用的情况时,消费者可以进行服务降级。那么,若客户端通过网关调用消费者无法调用时,zuul具有服务降级功能。
一、基本环境搭建
- 一个eureka项目
- 一个zuul项目
二、创建网关zuul
(1)创建项目00-zuul-fallback-9000
(2)依赖
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.abc</groupId>
<artifactId>00-zuul-fallback-9000</artifactId>
<version>0.0.1-SNAPSHOT</version>
<packaging>jar</packaging>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.1.3.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<properties>
<java.version>1.8</java.version>
<spring-cloud.version>Greenwich.SR1</spring-cloud.version>
</properties>
<dependencies>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-actuator</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
</dependency>
<!--zuul依赖-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-zuul</artifactId>
</dependency>
</dependencies>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>${spring-cloud.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
(3)application.yml配置
server:
port: 9000
eureka:
client:
service-url:
defaultZone: http://localhost:8000/eureka
spring:
application:
name: abcmsc-zuul-depart
zuul:
routes:
# 指定微服务的路由规则
abcmsc-consumer-depart-8080: /abc8080/**
abcmsc-consumer-depart-8090: /abc8090/**
(4)降级类
package com.abc.zuul.fallback;
import org.springframework.cloud.netflix.zuul.filters.route.FallbackProvider;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpStatus;
import org.springframework.http.MediaType;
import org.springframework.http.client.ClientHttpResponse;
import org.springframework.stereotype.Component;
import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;
@Component
public class ConsumerFallback implements FallbackProvider {
// 指定要降级的微服务名称
@Override
public String getRoute() {
// 对所有微服务降级
return "*";
// 仅对指定的微服务进行降级
// return "abcmsc-consumer-depart-8080";
}
// 定制降级响应
// route参数:当前请求所访问的微服务名称
@Override
public ClientHttpResponse fallbackResponse(String route, Throwable cause) {
System.out.println("route = " + route);
return new ClientHttpResponse() {
@Override
public HttpStatus getStatusCode() throws IOException {
// 返回状态常量
return HttpStatus.SERVICE_UNAVAILABLE;
}
@Override
public int getRawStatusCode() throws IOException {
// 返回状态码,这里为503
return HttpStatus.SERVICE_UNAVAILABLE.value();
}
@Override
public String getStatusText() throws IOException {
// 返回状态码对应的状态短语,这里为"Service Unavailable"
return HttpStatus.SERVICE_UNAVAILABLE.getReasonPhrase();
}
@Override
public void close() { }
@Override
public InputStream getBody() throws IOException {
// 设置降级信息
// String msg = "fallback:" + ConsumerFallback.this.getRoute();
String msg = "fallback:" + route;
return new ByteArrayInputStream(msg.getBytes());
}
@Override
public HttpHeaders getHeaders() {
// 设置降级响应头信息
HttpHeaders headers = new HttpHeaders();
headers.setContentType(MediaType.APPLICATION_JSON);
return headers;
}
};
}
}
(5)启动类
package com.abc.zuul;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.netflix.zuul.EnableZuulProxy;
@EnableZuulProxy // 开启zuul代理模式
@SpringBootApplication
public class ZuulApplication {
public static void main(String[] args) {
SpringApplication.run(ZuulApplication.class, args);
}
}
三、创建eureka
(1)创建00-eurekaserver-8000项目
(2)依赖
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.abc</groupId>
<artifactId>00-eurekaserver-8000</artifactId>
<version>0.0.1-SNAPSHOT</version>
<packaging>jar</packaging>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.1.7.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<properties>
<java.version>1.8</java.version>
<spring-cloud.version>Greenwich.SR2</spring-cloud.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-server</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
</dependencies>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>${spring-cloud.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
(3)application.yml配置
server:
port: 8000
eureka:
instance:
hostname: localhost # 指定Eureka主机
client:
register-with-eureka: false # 指定当前主机是否向Eureka服务器进行注册
fetch-registry: false # 指定当前主机是否要从Eurka服务器下载服务注册列表
service-url: # 服务暴露地址
defaultZone: http://localhost:8000/eureka
# defaultZone: http://${eureka.instance.hostname}:${server.port}/eureka
# server:
# enable-self-preservation: false # 关闭自我保护
(4)启动类
package com.abc.eureka;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.netflix.eureka.server.EnableEurekaServer;
@SpringBootApplication
@EnableEurekaServer // 开启Eureka服务
public class EurekaServerApplication {
public static void main(String[] args) {
SpringApplication.run(EurekaServerApplication.class, args);
}
}
四、测试
(1)启动eureka
(2)启动zuul网关
(3)效果
访问 :http://localhost:9000//abc8080/consumer/depart/get/1被降级处理
访问 :http://localhost:9000//abc8090/consumer/depart/get/1被降级处理