前面一篇已经简单了讲了Eureka Zuul Ribbon Feign。这章只单独讲Gateway 以及Gateway 和Zuul的区别。
Spring Cloud Gateway是Spring官方基于Spring 5.0,Spring Boot 2.0和Project Reactor等技术开发的网关,Spring Cloud Gateway旨在为微服务架构提供一种简单而有效的统一的API路由管理方式。Spring Cloud Gateway作为Spring Cloud生态系中的网关,目标是替代ZUUL,其不仅提供统一的路由方式,并且基于Filter链的方式提供了网关基本的功能,例如:安全,监控/埋点,和限流等。
Spring Cloud Gateway 可以看做是一个 Zuul 1.x 的升级版和代替品,比 Zuul 2 更早的使用 Netty 实现异步 IO,从而实现了一个简单、比 Zuul 1.x 更高效的、与 Spring Cloud 紧密配合的 API 网关。
Spring Cloud Gateway 里明确的区分了 Router 和 Filter,并且一个很大的特点是内置了非常多的开箱即用功能,并且都可以通过 SpringBoot 配置或者手工编码链式调用来使用。
比如内置了 10 种 Router,使得我们可以直接配置一下就可以随心所欲的根据 Header、或者 Path、或者 Host、或者 Query 来做路由。
比如区分了一般的 Filter 和全局 Filter,内置了 20 种 Filter 和 9 种全局 Filter,也都可以直接用。当然自定义 Filter 也非常方便
Gateway:内部实现了限流,负载均衡的功能,扩展性更强
限制仅适合于spring cloud 套件
支持异步
Zuul: 可以扩展至其他微服务框架中
内部没有实现限流,负载均衡等功能
2.x系列非阻塞异步模式,1.x系列同步模式
1. 新建maven项目huaun-eugt
2. 新建eureka模块
新建eureka模块后,查看eureka模块的pom.xml的配置文件:
4.0.0 org.springframework.boot spring-boot-starter-parent 2.3.7.RELEASE com.huaun eureka 0.0.1-SNAPSHOT eureka eureka 1.8 Hoxton.SR9 org.springframework.cloud spring-cloud-starter-netflix-eureka-server org.springframework.boot spring-boot-starter-test test org.junit.vintage junit-vintage-engine org.springframework.cloud spring-cloud-dependencies ${spring-cloud.version} pom import org.springframework.boot spring-boot-maven-plugin
将eureka模块中的application.properties文件改成application.yml文件,并进行如下配置
server: port: 8000 spring: application: name: eureka-service eureka: instance: hostname: localhost client: fetch-registry: false register-with-eureka: false service-url: defaultZone: http://${eureka.instance.hostname}:${server.port}/eureka server: peer-node-connect-timeout-ms: 300
@EnableEurekaServer注解eureka块中的EurekaApplication启动类
package com.huaun.eureka; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.cloud.netflix.eureka.server.EnableEurekaServer; @SpringBootApplication @EnableEurekaServer public class EurekaApplication { public static void main(String[] args) { SpringApplication.run(EurekaApplication.class, args); } }
启动Eureka服务,浏览器输入http://localhost:8000/可以得到如下图结果
3. 新建微服务userapi模块(不含 Feign)
新建userapi模块后,查看userapi模块的pom.xml的配置文件:
4.0.0 org.springframework.boot spring-boot-starter-parent 2.3.7.RELEASE com.huaun userapi 0.0.1-SNAPSHOT userapi Demo project for Spring Boot 1.8 Hoxton.SR9 org.springframework.cloud spring-cloud-starter-netflix-eureka-client org.springframework.boot spring-boot-starter-web org.springframework.boot spring-boot-starter-test test org.junit.vintage junit-vintage-engine org.springframework.cloud spring-cloud-dependencies ${spring-cloud.version} pom import org.springframework.boot spring-boot-maven-plugin
将userapi模块中的application.properties文件改成application.yml文件,并进行如下配置:
server: port: 7000 spring: application: name: user-service eureka: client: service-url: defaultZone: http://localhost:8000/eureka #当有多个eureka server时,以逗号隔开 register-with-eureka: true fetch-registry: true registry-fetch-interval-seconds: 30 #每30s获取服务器列表间隔 instance: prefer-ip-address: true #将当前实例的ip注册到eureka server中,默认是false,注册主机名 lease-expiration-duration-in-seconds: 9 #如果9秒没有发心跳包,服务器就会干掉该服务 lease-renewal-interval-in-seconds: 3 #每隔3秒发一次那条
@EnableDiscoveryClient注解userapi块中的UserapiApplication启动类
package com.huaun.userapi; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.cloud.client.discovery.EnableDiscoveryClient; @SpringBootApplication @EnableDiscoveryClient public class UserapiApplication { public static void main(String[] args) { SpringApplication.run(UserapiApplication.class, args); } }
在userapi模块中创建restful接口
package com.huaun.userapi; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.cloud.client.discovery.EnableDiscoveryClient; @SpringBootApplication @EnableDiscoveryClient public class UserapiApplication { public static void main(String[] args) { SpringApplication.run(UserapiApplication.class, args); } }
3. 新建微服务模块:userapi01,userapi02
创建方式、resultful接口,以及配置 均和userapi一样。
配置不同的地方是:userapi01中application.yml中的server.port =7002
userapi02中application.yml中的server.port=7003
userapi01中的controller中的name:user01改为name:user02
userapi02中的controller中的name:user01改为name:user03
4. 新建微服务模块systemapi (包含fegin,用于调用userapi,userapi01,userapi02模块中的接口)
systemapi模块的pom.xml的配置文件:
4.0.0 org.springframework.boot spring-boot-starter-parent 2.3.7.RELEASE com.huaun systemapi 0.0.1-SNAPSHOT systemapi systemapi 1.8 Hoxton.SR9 org.springframework.cloud spring-cloud-starter-netflix-eureka-client org.springframework.boot spring-boot-starter-web org.springframework.cloud spring-cloud-starter-openfeign org.springframework.boot spring-boot-starter-test test org.junit.vintage junit-vintage-engine org.springframework.cloud spring-cloud-dependencies ${spring-cloud.version} pom import org.springframework.boot spring-boot-maven-plugin
将systemapi模块中的application.properties文件改成application.yml文件,并进行如下配置
server: port: 7009 spring: application: name: system-service eureka: instance: prefer-ip-address: true client: fetch-registry: true register-with-eureka: true service-url: defaultZone: http://localhost:8000/eureka feign: client: config: default: connectTimeout: 5000 readTimeout: 5000 loggerLevel: basic okhttp: enabled: true hystrix: enabled: true
@EnableDiscoveryClient @EnableFeignClients注解systemapi块中的SystemapiApplication启动类
package com.huaun.systemapi; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.cloud.client.discovery.EnableDiscoveryClient; import org.springframework.cloud.openfeign.EnableFeignClients; @SpringBootApplication @EnableDiscoveryClient @EnableFeignClients public class SystemapiApplication { public static void main(String[] args) { SpringApplication.run(SystemapiApplication.class, args); } }
创建controller类和Feign客户端类:
package com.huaun.systemapi; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.cloud.client.discovery.EnableDiscoveryClient; import org.springframework.cloud.openfeign.EnableFeignClients; @SpringBootApplication @EnableDiscoveryClient @EnableFeignClients public class SystemapiApplication { public static void main(String[] args) { SpringApplication.run(SystemapiApplication.class, args); } }
package com.huaun.systemapi.controller; import com.huaun.systemapi.feign.UserFeignClient; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.RestController; @RestController public class DeptController { @Autowired private UserFeignClient userFeignClient; @GetMapping("getDeptInfo") public String getDeptInfo(){ String userInfo= userFeignClient.getUserInfo(); return userInfo+",所属部门:研发部"; } }
4. 新建客户端路由模块gateway(包含Ribbon 负载均衡)
Gateway模块的pom.xml的配置文件:
4.0.0 org.springframework.boot spring-boot-starter-parent 2.3.7.RELEASE com.huaun gateway 0.0.1-SNAPSHOT gateway gateway 1.8 Hoxton.SR9 org.springframework.cloud spring-cloud-starter-netflix-eureka-client org.springframework.cloud spring-cloud-starter-gateway org.springframework.cloud spring-cloud-starter-netflix-ribbon org.springframework.boot spring-boot-starter-test test org.junit.vintage junit-vintage-engine org.springframework.cloud spring-cloud-dependencies ${spring-cloud.version} pom import org.springframework.boot spring-boot-maven-plugin
将Gatway模块中的application.properties文件改成application.yml文件,并进行如下配置:
server: port: 8080 spring: application: name: gate-service cloud: discovery: enabled: true gateway: default-filters: routes: - id: user-api-routs uri: lb://user-service #注册中心的serverId predicates: - Path=/user-service/** filters: # 定义过滤规则 - StripPrefix=1 # 转发后去掉一个前缀 /ms-provider - id: system-api-routs uri: lb://system-service #注册中心的serverId predicates: - Path=/system-service/** filters: # 定义过滤规则 - StripPrefix=1 # 转发后去掉一个前缀 /ms-provider user-service: #负载均衡 ribbon: listOfServers: localhost:7000, localhost:7001,localhost:7002 NFLoadBalancerRuleClassName: com.netflix.loadbalancer.RoundRobinRule eureka: instance: prefer-ip-address: true client: fetch-registry: true register-with-eureka: true service-url: defaultZone: http://localhost:8000/eureka
@EnableDiscoveryClient 注解gateway块中的GatewayApplication启动类
package com.huaun.gateway; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.cloud.client.discovery.EnableDiscoveryClient; @SpringBootApplication @EnableDiscoveryClient public class GatewayApplication { public static void main(String[] args) { SpringApplication.run(GatewayApplication.class, args); } }
依次启动gateway,userapi01,userapi02,systemapi模块服务:
刷新http://localhost:8000,如下图:
访问userapi:http://localhost:7001/getUserInfo
访问userapi01:http://localhost:7002/getUserInfo
访问userapi02:http://localhost:7003/getUserInfo
访问systemapi:http://localhost:7009/getDeptInfo
通过路由的负载均衡访问userapi模块:http://localhost:8080/user-service/getUserInfo
通过路由访问systemapi模块:http://localhost:8080/system-service/getDeptInfo