一、前言
gateway是spring cloud全家桶的一員,主要用作微服務的網關,是spring官方基於spring5.0,spring boot 2.0和project reactor等技術開發的網關服務,旨在爲微服務提供一種簡單有效的統一api路由管理方式,基於filter鏈的方式提供了網關的基本功能如安全、監控、埋點、限流等。
項目地址:https://spring.io/projects/spring-cloud-gateway
二、使用
1、依賴
spring cloud已集成gateway,只需要引入spring cloud的父pom,就能直接使用。
<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>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-gateway</artifactId>
</dependency>
</dependencies>
2、路由配置
spring cloud gateway支持兩種路由配置:yaml文件配置和代碼配置。
(1)代碼配置
在主程序中使用代碼配置路由,官方示例如下:
@SpringBootApplication
public class DemogatewayApplication {
@Bean
public RouteLocator customRouteLocator(RouteLocatorBuilder builder) {
return builder.routes()
.route("path_route", r -> r.path("/get")
.uri("http://httpbin.org"))
.route("host_route", r -> r.host("*.myhost.org")
.uri("http://httpbin.org"))
.route("rewrite_route", r -> r.host("*.rewrite.org")
.filters(f -> f.rewritePath("/foo/(?<segment>.*)", "/${segment}"))
.uri("http://httpbin.org"))
.route("hystrix_route", r -> r.host("*.hystrix.org")
.filters(f -> f.hystrix(c -> c.setName("slowcmd")))
.uri("http://httpbin.org"))
.route("hystrix_fallback_route", r -> r.host("*.hystrixfallback.org")
.filters(f -> f.hystrix(c -> c.setName("slowcmd").setFallbackUri("forward:/hystrixfallback")))
.uri("http://httpbin.org"))
.route("limit_route", r -> r
.host("*.limited.org").and().path("/anything/**")
.filters(f -> f.requestRateLimiter(c -> c.setRateLimiter(redisRateLimiter())))
.uri("http://httpbin.org"))
.build();
}
}
(2)yaml文件配置
yaml文件是spring推薦使用的方式,使用上比較直觀,以下是我們項目中的配置:
project:
name: my-gateway
# endpoint配置
management:
endpoints:
web:
exposure:
include: "*"
server:
port: 7002
# http服務器端口
server:
port: 7001
spring:
application:
name: ${project.name}
profiles:
active: testing
hsf:
group: my
version: 1.0.0.DAILY
timeout: 2000
cloud:
gateway:
discovery:
locator:
enabled: true
lower-case-service-id: true
# 跨域
globalcors:
corsConfigurations:
'[/**]':
allowedHeaders: "*"
allowedOrigins: "*"
allowedMethods:
- GET
POST
DELETE
PUT
OPTION
routes:
# 數據應用
- id: my-data-app
uri: lb://my-data-app
predicates:
- Path=/my-data-app/**
filters:
- StripPrefix=1
# 數據應用websocket接口
- id: my-data-app-websocket
uri: lb:ws://my-data-app
predicates:
- Path=/my-data-app/**
filters:
- StripPrefix=1
# 任務調度
- id: my-task-scheduler
uri: lb://my-task-scheduler
predicates:
- Path=/my-task-scheduler/**
filters:
- StripPrefix=1
# 流程跟蹤
- id: my-process-tracking
uri: lb://my-process-tracking
predicates:
- Path=/my-process-tracking/**
filters:
- StripPrefix=1
# 軟件產品質量
- id: my-app-quality
uri: lb://my-app-quality
predicates:
- Path=/my-app-quality/**
filters:
- StripPrefix=1
# 工程效率質量
- id: my-project-quality
uri: lb://my-project-quality
predicates:
- Path=/my-project-quality/**
filters:
- StripPrefix=1
# 在線產品質量
- id: my-online-quality
uri: lb://my-online-quality
predicates:
- Path=/my-online-quality/**
filters:
- StripPrefix=1
# 數據存儲
- id: my-data-storage
uri: lb://my-data-storage
predicates:
- Path=/my-data-storage/**
filters:
- StripPrefix=1
# 數據收容
- id: dcpp-query
uri: lb://dcpp-query
predicates:
- Path=/dcpp-query/**
filters:
- StripPrefix=1
logging:
level:
org.springframework.cloud.gateway: DEBUG
org.springframework.http.server.reactive: DEBUG
org.springframework.web.reactive: DEBUG
id:每個route的唯一標識,如果不填寫則爲uuid
uri:轉發的url,即最終訪問的後端服務地址,如果lb開頭則爲服務註冊中心上的服務地址
predicates:斷言匹配器,根據規則進行匹配。
參考:https://cloud.spring.io/spring-cloud-gateway/spring-cloud-gateway.html#gateway-request-predicates-factories
三、實踐
1、Nacos作爲服務註冊中心
(1)添加nacos依賴,並在啓動類中開啓服務發現配置
@EnableDiscoveryClient
@SpringBootApplication(scanBasePackages = {"com.amap.qinling"})
public class Application {
public static void main(String[] args) {
SpringApplication.run(Application.class, args);
}
}
(2)路由規則按照lb://my-data-app方式進行配置,lb將會按照LoadBalancerClientFilter類進行處理,即根據my-data-app註冊中心查找對應的服務host和端口並替換。
2、跨域支持
gateway跨域支持比較方便,只需要在application.yaml配置跨域相關配置即可:
spring:
cloud:
gateway:
discovery:
# 跨域
globalcors:
corsConfigurations:
'[/**]':
allowedHeaders: "*"
allowedOrigins: "*"
allowedMethods:
- GET
POST
DELETE
PUT
OPTION
3、websocket協議轉發
需要轉發的服務爲websocket協議時,只需要在路由規則裏面添加相應的配置即可:
routes:
# 數據應用
- id: my-data-app
uri: lb://my-data-app
predicates:
- Path=/my-data-app/**
filters:
- StripPrefix=1
# 數據應用websocket接口
- id: my-data-app-websocket
uri: lb:ws://my-data-app
predicates:
- Path=/my-data-app/**
filters:
- StripPrefix=1
uri:lb:ws://my-data-app,ws代表websocket協議,gateway匹配到ws開頭的地址會自動匹配到這一條路由並轉發。
如果gateway前面有nginx代理,或者轉發的後端服務前面也有nginx,需要在每個nginx中添加websocket協議配置,如下:
location / {
# support webSocket
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
if ($request_uri ~ .*\.(txt|gif|jpg|jpeg|png|bmp|swf|js|css)$) {
access_log off;
}
proxy_pass http://127.0.0.1:7001;
}