3-服務網關Gateway
_網關過濾器學習筆記(2020.3.31)
前言:
過濾器允許以某種方式修改傳入的HTTP請求或返回的HTTP響應。過濾器的作用域是某些特定路由。Spring Cloud Gateway包括許多內置的 Filter工廠。
1. 網關過濾器
按需求使用那些過濾器。
有關如何使用以下任何過濾器的更多詳細示例,請查看單元測試。
1.1 AddRequestHeader
(添加請求頭)
採用一對名稱和值作爲參數。
cloud:
gateway:
discovery:
routes:
- id: my_route #自定義路由ID, 保持唯一
uri: lb://eureka-client #目標註冊中心服務名, lb表示從註冊中心獲取服務
predicates:
- Path=/Test/**
filters: #過濾規則
- AddRequestHeader=X-Request-myname, zhihao
對於所有匹配的請求,這將向下遊請求的頭中添加
x-request-myname:zhihao
頭
1.2 AddRequestParameter
(添加請求參數)
採用一對名稱和值作爲參數。
filters:
- AddRequestParameter=name, zhihao #對於所有匹配的請求,這將向下遊請求添加name=zhihao查詢字符串
1.3 AddResponseHeader
(添加響應頭)
採用一對名稱和值作爲參數。
filters:
- AddResponseHeader=X-Response-myname, zhihao
#對於所有匹配的請求,這將向下遊響應的頭中添加 x-Response-myname:zhihao 頭
1.4 DedupeResponseHeader
(刪除響應頭重複數據)
採用一個
name
參數和一個可選strategy
參數。name
可以包含以空格分隔的標題名稱列表
filters:
- DedupeResponseHeader=Access-Control-Allow-Credentials Access-Control-Allow-Origin
當網關CORS邏輯和下游邏輯都將它們添加時,這將刪除
Access-Control-Allow-Credentials
和Access-Control-Allow-Origin
響應頭的重複值。該
DedupeResponseHeader
過濾器還接受一個可選的strategy
參數。可接受的值爲RETAIN_FIRST
(默認值)RETAIN_LAST
,和RETAIN_UNIQUE
。
1.5 Hystrix
(熔斷器)
Hystrix 是Netflix開源的斷路器組件。Hystrix GatewayFilter允許你向網關路由引入斷路器,保護你的服務不受級聯故障的影響,並允許你在下游故障時提供fallback響應。
要在項目中啓用Hystrix網關過濾器,需要添加對
spring-cloud-starter-netflix-hystrix
的依賴 Spring Cloud Netflix.Hystrix GatewayFilter Factory 需要一個name參數,即
HystrixCommand
的名稱。
filters:
- Hystrix=myCommandName #這將剩餘的過濾器包裝在命令名爲“myCommandName”的HystrixCommand中。
hystrix過濾器還可以接受可選的
fallbackUri
參數。目前,僅支持forward:
預設的URI,如果調用fallback,則請求將轉發到與URI匹配的控制器。
application.yml
spring:
cloud:
gateway:
routes:
- id: hystrix_route
uri: lb://backing-service:8088
predicates:
- Path=/consumingserviceendpoint
filters:
- name: Hystrix
args:
name: fallbackcmd
fallbackUri: forward:/incaseoffailureusethis
- RewritePath=/consumingserviceendpoint, /backingserviceendpoint
當調用hystrix fallback時,這將轉發到
/incaseoffailureusethis
uri。注意,這個示例還演示了(可選)通過目標URI上的’lb`前綴,使用Spring Cloud Netflix Ribbon 客戶端負載均衡。
主要場景是使用
fallbackUri
到網關應用程序中的內部控制器或處理程序。但是,也可以將請求重新路由到外部應用程序中的控制器或處理程序,如:
application.yml.
spring:
cloud:
gateway:
routes:
- id: ingredients
uri: lb://ingredients
predicates:
- Path=//ingredients/**
filters:
- name: Hystrix
args:
name: fetchIngredients
fallbackUri: forward:/fallback
- id: ingredients-fallback
uri: http://localhost:9994
predicates:
- Path=/fallback
在本例中,gateway應用程序中沒有 fallback
實現,但是另一個應用程序中有一個接口實現,註冊爲“http://localhost:9994”。
在將請求轉發到fallback的情況下,Hystrix Gateway過濾還支持直接拋出Throwable
。它被作爲ServerWebExchangeUtils.HYSTRIX_EXECUTION_EXCEPTION_ATTR
屬性添加到ServerWebExchange
中,可以在處理網關應用程序中的fallback時使用。
對於外部控制器/處理程序方案,可以添加帶有異常詳細信息的header。可以在 FallbackHeaders GatewayFilter Factory section.中找到有關它的更多信息。
hystrix配置參數(如 timeouts)可以使用全局默認值配置,也可以使用Hystrix wiki中所述屬性進行配置。
要爲上面的示例路由設置5秒超時,將使用以下配置:
hystrix:
command:
fallbackcmd:
execution:
isolation:
thread:
timeoutInMilliseconds: 5000
1.6 FallbackHeaders (回退請求頭)
FallbackHeaders
允許在轉發到外部應用程序中的FallbackUri
的請求的header中添加Hystrix異常詳細信息,如下所示:
application.yml.
spring:
cloud:
gateway:
routes:
- id: ingredients
uri: lb://ingredients
predicates:
- Path=//ingredients/**
filters:
- name: Hystrix
args:
name: fetchIngredients
fallbackUri: forward:/fallback
- id: ingredients-fallback
uri: http://localhost:9994
predicates:
- Path=/fallback
filters:
- name: FallbackHeaders
args:
executionExceptionTypeHeaderName: Test-Header
在本例中,在運行HystrixCommand
發生執行異常後,請求將被轉發到 localhost:9994
應用程序中的 fallback
終端或程序。異常類型、消息(如果可用)cause exception類型和消息的頭,將由FallbackHeaders
filter添加到該請求中。
通過設置下面列出的參數值及其默認值,可以在配置中覆蓋headers的名稱:
executionExceptionTypeHeaderName
("Execution-Exception-Type"
)executionExceptionMessageHeaderName
("Execution-Exception-Message"
)rootCauseExceptionTypeHeaderName
("Root-Cause-Exception-Type"
)rootCauseExceptionMessageHeaderName
("Root-Cause-Exception-Message"
)
Hystrix 如何實現的更多細節可以參考 Hystrix GatewayFilter Factory section.
1.7 PrefixPath
(前綴路徑)
只有一個
prefix
參數.給所有匹配請求的路徑加前綴
/mypath
。因此,向/hello
發送的請求將發送到/mypath/hello
。
filters:
- PrefixPath=/mypath
1.8 SaveSession
SaveSession GatewayFilter Factory將調用轉發到下游之前強制執行
WebSession::save
操作。這在使用 Spring Session 之類時特別有用,需要確保會話狀態在進行轉發調用之前已保存。
filters:
- SaveSession
如果你希望要將[Spring Security](https://projects.spring.io/Spring Security/)與Spring Session集成,並確保安全詳細信息已轉發到遠程的進程,這一點至關重要。
1.9 SetResponseHeader
(修改響應請求頭)
SetResponseHeader GatewayFilter Factory 包括
name
和value
參數.
filters:
- SetResponseHeader=X-Response-name, zhihao
此GatewayFilter使用給定的名稱替換所有header,而不是添加。因此,如果下游服務器響應爲
X-Response-Foo:1234
,則會將其替換爲X-Response-Foo:zhihao
,這是網關客戶端將接收的內容。
2.0SetRequestHeader
(修改請求頭)
SetRequestHeader GatewayFilter Factory 包括
name
和value
參數.
filters:
- SetRequestHeader=X-Request-name, zhihao
此GatewayFilter使用給定的名稱替換所有header,而不是添加。因此,如果下游服務器響應爲
X-Request-name:1234
,則會將其替換爲X-Request-name:zhihao
,這是網關客戶端將接收的內容。
2.1 StripPrefix
(請求中去除的路徑中的節數)
StripPrefix GatewayFilter Factory 包括一個
parts
參數。parts
參數指示在將請求發送到下游之前,要從請求中去除的路徑中的節數。
predicates:
- Path=/name/**
filters:
- StripPrefix=2
#通過網關發出/name/bar/foo請求時,向nameservice發出的請求將是http://nameservice/foo。
#一般去掉一節就ok 發出/name/bar/foo 變成 /bar/foo
2.2 Retry
(重試)
Retry GatewayFilter Factory 支持以下參數:
-
retries
: 應嘗試的重試次數 -
statuses
: 應該重試的HTTP狀態代碼,用org.springframework.http.HttpStatus
標識 -
methods
: 應該重試的HTTP方法,用org.springframework.http.HttpMethod
標識 -
series
: 要重試的一系列狀態碼,用org.springframework.http.HttpStatus.Series
標識 -
exceptions
:應重試的引發異常的列表。 -
backoff
:爲重試配置的指數補償。重試在的退避間隔後執行firstBackoff * (factor ^ n)
,其中n
爲迭代。如果maxBackoff
已配置,則應用的最大退避限制爲maxBackoff
。如果basedOnPreviousValue
爲true,則使用計算退避prevBackoff * factor
。
Retry
如果啓用了以下默認過濾器配置:
retries
:3次series
:5XX系列methods
:GET方法exceptions
:IOException
和TimeoutException
backoff
:禁用
filters:
- name: Retry
args:
retries: 3
statuses: BAD_GATEWAY
methods: GET,POST
backoff:
firstBackoff: 10ms
maxBackoff: 50ms
factor: 2
basedOnPreviousValue: false
當使用帶有
forward:
前綴URL 的重試過濾器時,應仔細編寫目標端點,以便在發生錯誤的情況下,它不會做任何可能導致響應發送到客戶端並提交的操作。例如,如果目標端點是帶註釋的控制器,則目標控制器方法不應返回ResponseEntity
錯誤狀態代碼。相反,它應該拋出一個Exception
錯誤或發出一個錯誤信號(例如,通過Mono.error(ex)
返回值),該錯誤可以配置爲重試過濾器通過重試進行處理。當將重試過濾器與任何具有主體的HTTP方法一起使用時,主體將被緩存,並且網關將受到內存的限制。正文被緩存在由定義的請求屬性中
ServerWebExchangeUtils.CACHED_REQUEST_BODY_ATTR
。對象的類型是org.springframework.core.io.buffer.DataBuffer
。
2.3 RequestSize
(請求大小)
當請求大小大於允許的限制時,RequestSize GatewayFilter Factory可以限制請求不到達下游服務。過濾器以
RequestSize
作爲參數,這是定義請求的允許大小限制(以字節爲單位)。
跟一個可選的
DataUnit後綴,例如“KB”或“MB”。字節的默認值爲“ B”。
如果未在路由定義中作爲過濾器參數提供,則默認請求大小將設置爲5 MB。
predicates:
- Path=/upload
filters:
- name: RequestSize
args:
maxSize: 5000000
當請求因大小而被拒絕時, RequestSize GatewayFilter Factory 將響應狀態設置爲
413 Payload Too Large
,並帶有額外的headererrorMessage
。下面是一個errorMessage
的例子。
errorMessage` : `Request size is larger than permissible limit. Request size is 6.0 MB where permissible limit is 5.0 MB
2.4 默認過濾器 (用於所有路由)
要添加過濾器並將其應用於所有路由,可以使用
spring.cloud.gateway.default-filters
。此屬性採用過濾器列表。以下清單定義了一組默認過濾器:
spring:
cloud:
gateway:
default-filters:
- AddResponseHeader=X-Response-Default-Red, Default-Blue
- PrefixPath=/httpbin
上面就是個人覺得常用的網關提供過濾器。 其他過濾器可以在官網詳細瞭解。
https://cloud.spring.io/spring-cloud-static/spring-cloud-gateway/2.2.2.RELEASE/reference/html/#gatewayfilter-factories
1