> 技术文档 > SpringCloud Gateway_spring-cloud-starter-gateway-server-webflux

SpringCloud Gateway_spring-cloud-starter-gateway-server-webflux


文章目录

  • 需求引出
  • 网络拓扑图
  • Gateway是什么
  • 官网
  • Gateway VS Zuul
  • Gateway基本原理
  • Gateway工作机制
  • 搭建Gateway微服务
    • 需求
    • 实现
    • 断言类型
    • gateway路由配置
    • 动态路由需求
    • 配置负载均衡算法
  • Predicate断言
    • 基本介绍
    • After Route Predicate
    • Before Route Predicate
    • Between Route Predicate
    • Cookie Route Predicate
    • Host Route Predicate
    • Method Route Predicate
    • Path Route Predicate
    • Query Route Predicate
    • RemoteAddr Route Predicate
    • Weight
  • Filter过滤器链
    • 基本介绍
    • 实例
    • 自定义GlobalFilter

需求引出

SpringCloud Gateway_spring-cloud-starter-gateway-server-webflux

SpringCloud Gateway_spring-cloud-starter-gateway-server-webflux

网络拓扑图

SpringCloud Gateway_spring-cloud-starter-gateway-server-webflux

Gateway是什么

技术基础: 基于Spring生态系统构建的API网关服务,核心技术包括Spring 5、Spring Boot 2和Project Reactor
设计目标: 提供简单有效的API路由方式,并内置强大的过滤器功能
核心特性:
路由功能: 支持灵活的API请求路由配置
过滤器链: 提供熔断、限流、重试等分布式系统关键功能
生态兼容: 天然支持Spring/Spring Boot技术栈,与Spring Cloud生态无缝集成

官网

官网:https://docs.spring.io/spring-cloud-gateway/reference/spring-cloud-gateway-server-webflux/how-it-works.html
快速集成:
依赖配置: 使用org.springframework.cloud:spring-cloud-starter-gateway作为starter
禁用方式: 通过spring.cloud.gateway.enabled=false可禁用网关功能
技术前提: 需要熟悉Spring Boot 2.x、Spring WebFlux和Project Reactor等响应式编程技术

3.Gateway核心功能
流量控制: 支持精细化的请求流量管理和限制
熔断机制: 提供系统级故障隔离和恢复能力
日志系统: 完整的请求日志记录和监控能力
反向代理: 作为系统入口统一处理请求转发
实践建议: 根据实际项目需求选择性地集成特定功能模块

Gateway VS Zuul

定位差异:SpringCloud Gateway是Spring Cloud生态系统中的网关组件,设计目标就是替代Zuul
技术架构:
基于Spring WebFlux框架实现
底层采用Reactor模式通信框架Netty
性能优势:相比Zuul具有更强大的性能表现

1Gateway的特性
框架基础:
基于Spring Framework构建
支持Spring WebFlux
整合Project Reactor和Spring Boot
核心功能:
动态路由:根据请求URL动态决定转发目标
断言机制:通过Predicate判断请求是否可处理
过滤器链:支持请求前/后的处理逻辑
服务发现:集成Spring Cloud服务注册发现
熔断保护:内置Hystrix断路器功能
流量控制:支持请求限流功能
路径重写:可按规则修改请求路径

二、使用网关服务架构重构
核心价值:
提供统一API入口,通过URL路由转发请求
集成负载均衡、限流、熔断、鉴权等能力
实现原理:
动态路由配置:通过断言+过滤器实现请求分发
服务发现集成:自动识别可调用的后端服务
路径重写机制:按业务需求修改请求路径

SpringCloud Gateway_spring-cloud-starter-gateway-server-webflux

Gateway基本原理

Route路由

组成要素:由ID、目标URI、断言集合和过滤器集合构成
匹配条件:当所有断言结果为true时,该路由才会被匹配
本质特征:代表一个完整的请求路径或接口配置

Predicate断言

匹配对象:对HTTP请求头、请求参数等所有内容进行匹配
路径示例:配置$-Path=/member/get/^{​**​}$表示匹配所有以/member/get/开头的请求
匹配流程:请求路径必须完全符合配置模式才会进行路由转发
典型场景:如请求http://localhost/member/get/1能匹配,而http://localhost/member/xxx/1则不能匹配

Filter过滤

处理时机:可在请求被路由前或路由后进行额外处理
工作流程:在断言匹配成功后触发过滤机制
参数添加示例:配置filters:-AddRequestParameter=color,blue会在匹配请求中添加color=blue参数
处理效果:如原始请求http://localhost:10000/member/get/1会被处理为http://localhost:10000/member/get/1?color=blue
类比说明:类似Java Web中的过滤器机制,包含预处理和后处理阶段

SpringCloud Gateway_spring-cloud-starter-gateway-server-webflux
SpringCloud Gateway_spring-cloud-starter-gateway-server-webflux

Gateway工作机制

客户端为啥不能直接用 IP + 端口?
直接暴露微服务 IP + 端口,相当于 “把家门钥匙给陌生人”,容易被攻击。
网关作为中间层,隐藏了内部服务的真实地址,相当于 “家门有保安,陌生人进不来”。

核心工作流程:快递包裹的 “分拣 - 运输 - 签收” 三步曲

快递到达分拣中心(用户点击网页按钮, 根据域名[通过查找DNS服务器]找到网关所在的IP地址, 请求达到网关)
->根据快递单地址确定要送到哪个小区(根据快递单URL找到匹配的断言规则,确定目标服务名
->分拣中心给包裹贴标签, 检查包装是否完好, 确认你有没有寄件资格(Pre过滤器添加请求参数, 参数检验, 权限校验)
->分拣中心安排快递员把包裹送到小区(Gateway 通过 Ribbon 从 Eureka 找服务地址,负载均衡选一个实例转发请求。)
->包裹送到后,分拣中心记录签收时间(日志)、更新物流状态(修改响应头)。

二、过滤器链:快递处理的 “流水线工人
Pre 过滤器:发货前的 “质检团队”

做这些事: 检查地址是否正确(参数校验):比如你写的 “北京市朝阳区” 是否真实存在。 查你有没有寄件权限(JWT 令牌验证):像寄国际快递需要护照,没护照不让寄。 统计今天寄了多少包裹(流量监控):防止一天寄太多包裹,分拣中心忙不过来(限流)。 贴统一标签(AddRequestParameter):比如所有包裹都贴 “易碎品” 标签。

Post 过滤器:签收后的 “售后团队”

做这些事: 把物流信息统一写成 “已签收” 格式(修改响应内容):不管哪个快递员送的,格式都一样。 给包裹加 “好评” 标签(添加响应头):比如跨域请求时加Access-Control-Allow-Origin头。 记录包裹送了多久(响应耗时统计):比如从分拣中心到你家花了 30 分钟。

SpringCloud Gateway_spring-cloud-starter-gateway-server-webflux

客户端向SpringCloud Gateway发出请求,然后在Gateway Handler Mapping 断言 中找到与请求相匹配的路由,将其发送到Gate Web Handler。

Handler通过指定的过滤器链将请求发送到实际的目标服务。

Filter在“pre”类型的过滤器中可以做参数校验,权限校验,流量监控,日志输出,协议转换。

在“post”类型的过滤器中可以做响应内容,响应头修改,日志输出,流量监控。,

SpringCloud Gateway_spring-cloud-starter-gateway-server-webflux

搭建Gateway微服务

需求

网关本身也是一个微服务模块,可视为Eureka Client
SpringCloud Gateway_spring-cloud-starter-gateway-server-webflux

实现

1.对80服务消费方的一个升级,粘过来。

创建依据:参照member-service-consumer-80创建e-commerce-gateway-20000微服务
原因:网关服务本质上是服务调用方的升级版本,具有更强的功能特性
POM文件修改:从member-service-consumer-80的pom.xml拷贝部分内容
关键依赖:必须引入spring-cloud-starter-gateway场景启动器

模块命名:e-commerce-gateway-20000
目录结构:需与父工程e-commerce保持统一
版本管理:使用父工程声明的版本仲裁机制(Hoxton.SR1)
依赖刷新:创建完成后必须刷新Maven以确保依赖正确加载
版本验证:通过Maven管理器可查看实际加载版本为2.2.1.RELEASE

application.yml配置
版本控制机制:通过spring-cloud-dependencies统一管理网关版本
依赖继承关系:网关属于Spring Cloud原生组件,非Alibaba体系
工程结构验证:创建后需确认模块已被父工程正确聚合管理
配置要点:路由ID需保持唯一,最终访问URL由uri+Path组合而成

关键依赖:必须引入spring-cloud-starter-netflix-eureka-client实现服务发现
版本继承:通过父项目spring-cloud-dependencies-Hoxton.SR1进行版本仲裁
冲突说明:若同时引入web相关依赖会导致启动失败,必须特别注意

Gateway服务不需要Web Starter
禁止引入项:
spring-boot-starter-web
spring-boot-starter-actuator
冲突原因:Gateway作为服务网关,其底层实现与Web容器存在不兼容
典型错误:初学者常误加这些依赖导致启动失败
解决方案:在pom.xml中严格检查并移除相关依赖

Lombok依赖的添加
推荐配置:可添加optional true限定作用域
作用范围:仅限当前项目使用,避免传递依赖
格式化要求:添加后需执行Maven刷新操作

必要依赖:需要保留e_commerce_center-common-api模块
版本管理:使用${project.version}保持版本一致
模块作用:提供跨服务公共接口定义
SpringCloud Gateway_spring-cloud-starter-gateway-server-webflux

网关微服务搭建:把 “前台接待” 升级成 “智能导览机器人”

1.新建微服务模块e-commerce-gateway-20000

2.pom依赖
只有 Eureka Server 自己需要eureka-server依赖,其他微服务只需要eureka-client

<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/maven-v4_0_0.xsd\"> <modelVersion>4.0.0</modelVersion> <parent> <groupId>com.zzw</groupId> <artifactId>e-commerce</artifactId> <version>1.0-SNAPSHOT</version> </parent> <artifactId>e-commerce-gateway-20000</artifactId>  <dependencies> <dependency> <groupId>org.projectlombok</groupId> <artifactId>lombok</artifactId> <optional>true</optional> </dependency>  <dependency> <groupId>com.zzw</groupId> <artifactId>e-ecommerce-center-common-api</artifactId> <version>${project.version}</version> </dependency>  <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId> </dependency>  <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-gateway</artifactId> </dependency> </dependencies></project>

3.配置文件

server: port: 20000spring: application: name: e-commerce-gateway cloud: gateway: routes: # 配置路由,可以配置多个路由。List routes 数组 # 最终的路径 uri+Path,这里暂时用不到 eureka server(意思就是 网关直接把请求转发到http://localhost:10000,不通过 Eureka 动态发现服务。) - id: member-gateway-route-01 uri: http://localhost:10000 predicates: - Path=/member/provider/**eureka: instance: hostname: e-commerce-service # 服务别名 client: service-url: register-with-eureka: true fetch-registry: true # Eureka 注册中心是一栋楼 # http://eureka9001.com:9001是注册中心的地址 # /eureka/就是这栋楼里 “通讯录办公室” 的具体房间号。 # 将本服务注册到eureka集群 defaultZone: http://eureka9001.com:9001/eureka/, http://eureka9002.com:9002/eureka/

4.启动类

@EnableEurekaClient@SpringBootApplicationpublic class MemberGatewayApplication20000 { public static void main(String[] args) { ConfigurableApplicationContext ioc = SpringApplication.run(MemberGatewayApplication20000.class, args); }}

5.测试
先用原来的测一下
SpringCloud Gateway_spring-cloud-starter-gateway-server-webflux

测试一下服务网关

SpringCloud Gateway_spring-cloud-starter-gateway-server-webflux
SpringCloud Gateway_spring-cloud-starter-gateway-server-webflux

spring: application: name: e-commerce-gateway cloud: gateway: routes: # 配置路由,可以配置多个路由。List routes 数组 - id: member-gateway-route-01 #gateway 最终访问的url是 url=uri+Path #匹配后提供服务的路由地址: 也可以是外网 http://www.baidu.com #比如: 如果客户端/浏览器 访问gateway 的 url http://localhost:20000/member/provider/selectById/1 #匹配Path成功, 最终访问的url 就是 http://localhost:10000/member/provider/selectById/1 #如果匹配失败, gateway返回404信息 #(这里配置的uri是固定的, 意思就是 网关直接把请求转发到http://localhost:10000,不通过 Eureka 动态发现服务。) uri: http://localhost:10000 predicates: - Path=/member/provider/selectById/** - id: member-gateway-route-02 uri: http://localhost:10000 predicates: #这时如果客户端/浏览器 访问gateway 的 url http://localhost:20000/member/provider/insert #匹配Path成功, 最终访问的url 就是 http://localhost:10000/member/provider/insert - Path=/member/provider/insert - id: member-gateway-route-03 #路由id,自己配置,要求唯一 uri: http://www.baidu.com predicates: # 断言,可以有多种形式 - Path=/

SpringCloud Gateway_spring-cloud-starter-gateway-server-webflux

断言类型

- Path=/member/provider/selectById/** 属于yaml语法哪一种类型

Gateway 路由断言:快递分拣中心的「10 种分拣规则」

gateway路由配置

文档:https://docs.spring.io/spring-cloud-gateway/reference/spring-cloud-gateway-server-webflux/gatewayfilter-factories/circuitbreaker-filter-factory.html

新建src/main/java/com/zzw/springcloud/config/GatewayRoutesConfig.java

@Configurationpublic class GatewayRoutesConfig { /* 用配置类的方式配置路由 - id: member-gateway-route-01 uri: http://localhost:10000 predicates: - Path=/member/provider/selectById/** */ @Bean public RouteLocator routes(RouteLocatorBuilder builder) { RouteLocatorBuilder.Builder routes = builder.routes(); /* public Builder route(String id, Function fn) {Route.AsyncBuilder routeBuilder = fn.apply(new RouteSpec(this).id(id));add(routeBuilder);return this;} 1.java中函数式接口的典型用法, 传统的匿名类实现 2.一个函数式接口(Function),用于定义路由规则。 3.接受的是 PredicateSpec,返回的是 Route.AsyncBuilder 4.predicateSpec -> predicateSpec.path(\"/member/provider/selectById/**\").uri(\"http://localhost:10000\"); 就是lambda表达式(1)PredicateSpec是Gateway提供的路由断言配置接口 (2)Route.AsyncBuilder是Gateway提供的路由构建器, 用于设置路由断言和路由地址 ========================================================================================Function fn = new Function() { @Override public Route.AsyncBuilder apply(PredicateSpec predicateSpec) { return predicateSpec.path(\"/member/provider/selectById/**\").uri(\"http://localhost:10000\"); } }; ======================================================================================== //对上面进行简化,lambda表达式的第一种写法 Function fn2 = (predicateSpec) -> {return predicateSpec.path(\"/member/provider/selectById/**\").uri(\"http://localhost:10000\");}; //对上面进行简化,lambda表达式的第二种写法 Function fn3 = predicateSpec -> predicateSpec.path(\"/member/provider/selectById/**\").uri(\"http://localhost:10000\"); */ Function<PredicateSpec, Route.AsyncBuilder> fn = (predicateSpec) -> {return predicateSpec.path(\"/member/provider/selectById/**\").uri(\"http://localhost:10000\");}; Function<PredicateSpec, Route.AsyncBuilder> fn2 = (predicateSpec) -> {return predicateSpec.path(\"/member/provider/insert\").uri(\"http://localhost:10000\");}; Function<PredicateSpec, Route.AsyncBuilder> fn3 = (predicateSpec) -> {return predicateSpec.path(\"/\").uri(\"http://www.baidu.com\");}; RouteLocatorBuilder.Builder route = routes .route(\"member-gateway-route-01\", predicateSpec -> predicateSpec.path(\"/member/provider/selectById/**\").uri(\"http://localhost:10000\")) .route(\"member-gateway-route-02\", predicateSpec -> predicateSpec.path(\"/member/provider/insert\").uri(\"http://localhost:10000\")) .route(\"member-gateway-route-03\", predicateSpec -> predicateSpec.path(\"/\").uri(\"http://localhost:10000\")); return route.build(); }}

lambda表达式理解,新建src/test/java/com/zzw/springcloud/TestFunction.java

public class TestFunction { public static void main(String[] args) { //第一种写法 传统匿名类实现 //Dog dog = hi(\"小花猫,喵喵喵~\", new Function() { // @Override // public Cat apply(String str) { // Cat cat = new Cat(); // cat.setName(str); // return cat; // } //}); //lambda表达式的第一种写法 //Dog dog = hi(\"小花猫,喵喵喵~\", (str) -> { // Cat cat = new Cat(); // cat.setName(str); // return cat; // } //); //对上面的lambda表达式进行简化 //Dog dog = hi(\"小花猫,喵喵喵~\", str -> { // Cat cat = new Cat(); // cat.setName(str); // return cat; // } //); //对上面的lambda表达式进行简化 //Dog dog = hi(\"小花猫,喵喵喵~\", str -> { // return new Cat(str); // } //); //对上面的lambda表达式进行简化 Dog dog = hi(\"小黄猫,喵喵喵~\", r -> new Cat(r)); System.out.println(dog.getName()); } /* public Builder route(String id, Function fn) { Route.AsyncBuilder routeBuilder = fn.apply(new RouteSpec(this).id(id)); add(routeBuilder); return this; } */ public static Dog hi(String str, Function<String, Cat> fn) { Cat cat = fn.apply(str); Dog dog = new Dog(); dog.setName(cat.getName() + \" 返回了一只小狗~\"); return dog; }}class Dog { private String name; public void setName(String name) { this.name = name; } public String getName() { return name; }}class Cat { private String name; public Cat() { } public Cat(String name) { this.name = name; } public void setName(String name) { this.name = name; } public String getName() { return name; }}

动态路由需求

SpringCloud Gateway_spring-cloud-starter-gateway-server-webflux

动态路由 lb://member-service-provider, 通过底层负载均衡调用

需要注意服务名应使用小写字母,大写字母会导致配置失败。lb是协议名,代表负载均衡协议,后面的内容是对应路径的服务名称,也是小写字母。

spring: application: name: e-commerce-gateway cloud: gateway: routes: # 配置路由,可以配置多个路由。List routes 数组 - id: member-gateway-route-04 uri: lb://member-service-provider predicates: - name: Path  args: pattern: /member/provider/** discovery: locator: enabled: true

配置负载均衡算法

BestAvailableRule: 选择并发请求最小的server。会逐个考察Server,如果Server被tripped(跳闸)则忽略,最终选择ActiveRequestsCount最小的server。

AvailabilityFilteringRule: 过滤掉因连接失败被标记为circuit tripped的后端server,同时过滤高并发server(active connections超过配置阈值)。

WeightedResponseTimeRule: 根据响应时间分配权重,响应时间越长weight越小,被选中的可能性越低。

RetryRule: 在选定负载均衡策略基础上增加重试机制。配置时间段内若选择server不成功,会持续尝试使用subRule选择可用server。

RoundRobinRule: 轮询index选择对应位置的server(Ribbon默认算法)。

RandomRule: 随机选择server,在index上随机选取对应位置。

ZoneAvoidanceRule: 复合判断server所在区域的性能和可用性来选择server。

@Configurationpublic class RibbonRule { //配置和注⼊⾃定义的负载均衡算法 //可以选择多种负载均衡算法,如RandomRule(随机选择)、RoundRobinRule(轮询)等。 // @Bean public IRule getRibbonRule() { return new RandomRule(); }}

配置启动类

@RibbonClient(name = \"member-service-provider\", configuration = RibbonRule.class)

Predicate断言

基本介绍

工厂类型:
After:基于请求时间的\"之后\"断言
Before:基于请求时间的\"之前\"断言
Between:时间区间断言
Cookie:检查请求Cookie
Header:检查请求头
Host:检查请求主机
Method:检查请求方法(GET/POST等)
Path:检查请求路径
Query:检查查询参数
RemoteAddr:检查远程地址
Weight:权重路由

核心特性:
内置多种工厂类型:共11种标准断言工厂
多属性匹配:每种工厂匹配HTTP请求的不同属性
组合使用:支持通过逻辑与(and)组合多个断言条件
实现原理:
Spring Cloud Gateway创建Route对象时
使用RoutePredicateFactory创建Predicate对象
Predicate对象赋值给Route进行路由匹配

创建过程:
使用RoutePredicateFactory创建Predicate对象
将Predicate对象赋值给Route对象

After Route Predicate

一、After 断言:给路由加个「定时开关」

时间断言:After Route Predicate根据时间进行断言,只有指定时间之后的请求才会被处理
典型需求:要求只有2022-11-18 12:35:50之后的请求才进行匹配转发,不满足时间条件的请求不予处理

时间格式:必须使用特定格式,包含年月日时分秒毫秒和时区,如:
- After=2022-11-18T12:35:50.000+08:00[Asia/Shanghai]

- id: member-gateway-route-03 uri: lb://member-service-provider predicates: - name: After args: date-time: 2025-06-29T16:59:00.493+08:00[Asia/Shanghai]

Before Route Predicate

二、Before 断言:服务的「倒计时器」

核心功能:只处理指定时间点之前的请求,不满足时间条件的请求将被拒绝
时间格式:采用标准ISO时间格式,如
- Before=2022-11-18T12:35:50.000+08:00[Asia/Shanghai]
应用场景:适用于需要限制特定时间后停止服务的业务场景

- id: member-gateway-route-03 uri: lb://member-service-provider predicates: - name: Before args: date-time: 2025-06-29T16:59:00.493+08:00[Asia/Shanghai]

Between Route Predicate

三、Between 断言:服务的「时间段门禁」

- id: member-gateway-route-04 uri: lb://member-service-provider predicates: - name: Between args: datetime1: 2025-06-29T17:02:00.493+08:00[Asia/Shanghai] datetime2: 2025-06-29T17:15:00.493+08:00[Asia/Shanghai]

Cookie Route Predicate

四、Cookie 断言:网关的「门禁卡检查器」

- id: member-gateway-route-04 uri: lb://member-service-provider predicates: - name: Cookie args: name: auth regexp: token=.*

Host Route Predicate

Host 字段是 HTTP 请求的核心标识之一

Host Route Predicate 网关的「域名安检员」指南

- id: member-gateway-route-04 uri: lb://member-service-provider predicates: - name: Host args: patterns: [localhost, 127.0.0.1, www.zzw.com]

Method Route Predicate

Method Route Predicate:网关的「请求方式守门人」

- id: member-gateway-route-04 uri: lb://member-service-provider predicates: - name: Method args: methods: [GET, POST]

Path Route Predicate

Path Route Predicate:网关的「路径导航员」

- id: member-gateway-route-04 uri: http://localhost:10000 predicates: - name: Path args: pattern: /member/provider/**

Query Route Predicate

Query Route Predicate:网关的「参数安检仪」指南

- id: member-gateway-route-04 uri: http://localhost:10000 predicates: - name: Query args: param: name regexp: zzw

Query Route Predicate 示例集合

RemoteAddr Route Predicate

RemoteAddr 路由断言:网关的「IP 门禁系统」

- id: member-gateway-route-04 uri: http://localhost:10000 predicates: - name: RemoteAddr args: sources: [127.0.0.1, 192.168.1.100]

RemoteAddr和Referer区别

Weight

权重路由断言工厂:流量分配的 “概率控制器”

不测试, 太麻烦

Filter过滤器链

Spring Cloud Gateway 过滤器:请求处理的 “全能管家”

基本介绍

官网: https://docs.spring.io/spring-cloud-gateway/reference/spring-cloud-gateway-server-webflux/gatewayfilter-factories.html

实例

GatewayFilter 类型详解:请求与响应的定制化处理工具

一、AddRequestParameter GatewayFilter Factory:给请求加 “小纸条”
功能作用:在匹配请求的查询字符串中添加指定参数
参数格式:采用name-value对形式,如AddRequestParameter=red, blue
URI变量支持:支持使用路径匹配中的URI变量,运行时自动展开

层级关系:与routes下的id、uri、predicates同级
多参数配置:可通过多个AddRequestParameter配置多个参数,如同时添加color和address参数

二、AddRequestHeader GatewayFilter Factory:给请求 “戴帽子”
功能区别:与AddRequestParameter类似,但操作的是请求头而非查询参数
配置格式:AddRequestHeader=X-Request-Red, Blue
典型应用:用于添加认证头、追踪ID等HTTP头信息

三、AddResponseHeader GatewayFilter Factory:给响应 “贴封印”
响应处理:在返回给客户端的响应中添加指定头信息
使用场景:常用于添加缓存控制、安全策略等响应头

- id: member-gateway-route-04 uri: lb://member-service-provider predicates: - name: Path args: patterns: [/member/provider/**] filters: - name: AddRequestParameter args: name: name value: zzw - name: AddRequestHeader args: name: token value: 123456 - name: AddResponseHeader args: name: Cache-Control value: no-cache

自定义GlobalFilter

需求
1.自定义全局GlobalFilter过滤器
2.如果有请求参数 user=zzw,password=123456就放行,否则不能通过验证。

实现
1.创建自定义GlobalFiltersrc/main/java/com/zzw/springcloud/filter/CustomGatewayFilter.java
实现接口:需要同时实现GlobalFilter和Ordered两个接口
核心方法:
filter():包含主要过滤逻辑
getOrder():控制过滤器执行顺序
执行顺序:数字越小优先级越高,设置为0表示最高优先级
参数处理:使用getFirst()方法获取参数第一个值,适用于单值参数场景
示例URL:http://localhost:20000/member/get/1?user=hspedu&pwd=123456

@Slf4j@Componentpublic class CustomGatewayFilter implements GlobalFilter, Ordered { @Override public Mono<Void> filter(ServerWebExchange exchange, GatewayFilterChain chain) { //http://localhost:20000/member/provider/selectById/1?user=zzw&pwd=123456 //使用ServerWebExchange获取请求参数,通过getQueryParameters()和getFirst()方法提取特定参数 String user = exchange.getRequest().getQueryParams().getFirst(\"user\"); String pwd = exchange.getRequest().getQueryParams().getFirst(\"pwd\"); log.info(\"user: {}, pwd: {}\", user, pwd); if (!\"zzw\".equals(user) || !\"123456\".equals(pwd)) { //不满足条件返回406状态码,该状态码表示客户端发送的请求不被服务器接受,用于告知客户端请求存在问题。 //设置状态码:HttpStatus.NOT_ACCEPTABLE //结束响应:exchange.getResponse().setComplete() exchange.getResponse().setStatusCode(HttpStatus.NOT_ACCEPTABLE); return exchange.getResponse().setComplete(); } //放行条件:当参数验证通过时 //实现方式:调用chain.filter(exchange)将请求传递到下一个过滤器或服务 //链式处理:Gateway支持多个过滤器形成执行链,通过Ordered接口控制执行顺序 return chain.filter(exchange); } @Override public int getOrder() { return 0; }}

2.测试…

自定义 GlobalFilter:请求验证与拦截实践指南
《Spring Cloud Gateway 全局过滤器与内置过滤器的对比》