Spring Cloud Gateway 踩坑实录:限流、鉴权与跨域问题全解析
欢迎阅读我的文章!更多精彩内容,欢迎关注:
• B站主页:🫱小枫Geek
• 微信公众号:Procode
在微服务架构中,Spring Cloud Gateway 作为流量入口扮演着至关重要的角色。它不仅承担了 路由转发,还往往需要负责 限流、防刷、鉴权、安全过滤 等工作。 然而,在实际开发和部署过程中,Gateway 常常会出现一些“让人怀疑人生”的坑,比如:
-
限流配置了却不生效,或者误伤了正常用户
-
鉴权逻辑没问题,本地调试正常,上线后却各种 401
-
跨域问题更是经典,调试时能用,部署后前端直接报错
这篇文章,我将结合踩坑经历,深入解析 Spring Cloud Gateway 中 限流、鉴权与跨域 三大问题,并提供 常见原因 + 解决方案,帮助你快速避坑。
1、限流:从“不限流”到“全拦截”的玄学问题
限流是 Gateway 的常见功能,用于防止接口被恶意刷流量或高并发打挂后端服务。Spring Cloud Gateway 常见的限流实现方式有:
-
RedisRateLimiter:基于 Redis 的令牌桶限流
-
自定义过滤器:通过 AOP 或自定义逻辑实现更灵活的限流
1.1 RedisRateLimiter 的常见坑
官方推荐的限流方式是 RedisRateLimiter,配置简单,例如:
spring:
cloud:
gateway:
routes:
- id: user_service
uri: lb://user-service
predicates:
- Path=/api/user/**
filters:
- name: RequestRateLimiter
args:
redis-rate-limiter.replenishRate: 5
redis-rate-limiter.burstCapacity: 10
key-resolver: "#{@ipKeyResolver}"
上面配置的意思是:每秒生成 5 个令牌,最多能瞬间处理 10 个请求。
但是,常见问题来了:
问题1:限流不生效
排查方向:
-
是否配置了 Redis 连接?
-
是否在配置类中注册了
KeyResolver? -
Spring Cloud 版本是否匹配?
一个常见坑是 没有注入 KeyResolver,导致限流逻辑压根没触发:
@Bean
public KeyResolver ipKeyResolver() {
return exchange -> Mono.just(exchange.getRequest().getRemoteAddress().getHostName());
}
问题2:限流过于严格,正常请求被拦截
原因可能是:
-
burstCapacity配置过小,瞬时高并发无法承受 -
多个网关节点共享 Redis key 时,key 粒度过粗(例如全局 IP)
解决方案:
-
对不同用户/接口设置不同限流规则,比如通过
userId而非 IP 来限流 -
合理调大
burstCapacity以应对流量波峰
2、鉴权:明明 Token 正确却报 401?
Gateway 通常会作为统一入口负责 鉴权。常见方式有:
-
JWT 鉴权
-
OAuth2 鉴权
-
自定义 Token 校验
2.1 本地调试正常,上线后全是 401
这个坑几乎所有人都踩过。常见原因:
-
Header 丢失某些情况下,Gateway 默认会丢弃
Authorization头部,导致后端服务拿不到 Token。解决方案:在 Gateway 的
application.yml中显式允许保留 Header:
spring:
cloud:
gateway:
default-filters:
- PreserveHostHeader
或者在 RouteDefinition 中配置 filters,确保 Authorization 不被移除。
-
Token 过期/时区问题
-
本地调试时间正确,但服务器时钟不同步,JWT 过期判定提前触发。
-
解决方案:确认服务器时间同步(NTP 服务)。
-
-
跨服务 Token 未传递如果网关把请求转发给服务 A,而服务 A 再调用服务 B,常常忘记把 Token 继续传递下去。 解决方案:在 Feign 或 RestTemplate 调用时手动传递
Authorization。
3、跨域(CORS):前端报错的万年大坑
跨域问题是前后端分离架构里最常见的“玄学 Bug”。表象通常是:
前端报错:
Access to XMLHttpRequest at 'http://api.xxx.com/user' from origin 'http://localhost:8080'
has been blocked by CORS policy
3.1 Gateway 配置跨域的正确姿势
Spring Cloud Gateway 自带的 CORS 配置如下:
spring:
cloud:
gateway:
globalcors:
corsConfigurations:
'[/**]':
allowedOrigins: "*"
allowedMethods:
- GET
- POST
- PUT
- DELETE
allowedHeaders: "*"
allowCredentials: true
几个容易忽略的点:
-
allowedOrigins如果配置为*,不能再配allowCredentials: true,否则直接报错。 -
部署时要区分前端域名,建议不要写
*,而是配置明确的白名单,例如https://www.xxx.com。
3.2 经典坑:OPTIONS 请求被拦截
浏览器的 CORS 预检请求是 OPTIONS,如果 Gateway 没有正确处理,跨域就失败了。
解决方案:
-
在路由里加上
allowedMethods: OPTIONS -
或者在自定义过滤器里直接放行 OPTIONS 请求
if (request.getMethod() == HttpMethod.OPTIONS) {
return chain.filter(exchange); // 直接通过
}
3.3 前端依旧报错?可能不是跨域
有时候前端报跨域错误,其实是 后端服务 500 或超时,浏览器直接以 CORS 错误兜底。 排查方法:抓包看看响应头,如果根本没有到达 Gateway,那就不是 CORS 问题,而是服务没起来。
4、如何少踩坑?
-
限流策略要区分维度不要一刀切按 IP 限流,可以根据用户 ID、API 级别限流,避免误伤。
-
鉴权要明确 Token 传递链路确认网关 → 微服务 A → 微服务 B 的 Token 是否都带过去了。
-
跨域配置建议精确到域名本地调试可以用
*,生产环境一定要配白名单域名,避免安全风险。 -
多环境测试跨域和鉴权在本地、测试环境、生产环境可能行为不同,务必全链路测试。
Spring Cloud Gateway 功能强大,但也暗藏不少坑。 限流、鉴权、跨域这三大模块,几乎每个团队都会踩坑,但一旦理清原理,就能快速排查问题。
如果你正在搭建微服务网关,建议在开发初期就写好 限流规则、鉴权过滤器、CORS 配置,并做压测与联调,避免上线后手忙脚乱。
更多推荐

所有评论(0)