微服务调用过程中访问令牌过期的应对方案咨询
这确实是微服务架构里非常常见的痛点,我来分享几个经过实践验证的处理方案,你可以结合自己的架构场景来选择:
1. 自动刷新令牌(推荐用于有刷新令牌的场景)
如果你的认证体系支持刷新令牌(Refresh Token),这应该是最省心的方案。具体做法是:
- 服务在发起下游调用前,先检查所持有的用户access token是否即将过期(比如提前30秒判断过期时间)
- 如果调用后收到下游返回的
401 Unauthorized且提示令牌过期,就自动用预先存储的刷新令牌向认证服务请求新的access token - 获取到新token后,更新本地缓存的令牌,然后重试原请求(一定要限制重试次数,比如最多2次,避免死循环)
我在几个项目里都实践过这种方式,最好把令牌刷新逻辑封装成通用的HTTP客户端拦截器,比如Spring的ClientHttpRequestInterceptor或者Node.js的Axios拦截器,这样所有服务调用都能自动处理,不用重复写代码。
2. API网关层面统一拦截与重试
如果你的架构里有API网关,可以把令牌刷新的逻辑统一放在网关层:
- 网关在转发请求到下游服务前,先校验用户token的有效性
- 如果下游返回令牌过期的401响应,网关直接用存储的刷新令牌去获取新的access token
- 更新请求头中的token后,自动重试请求,最后把结果返回给调用方
这种方式的好处是服务本身不用关心令牌过期的问题,减少了业务代码的复杂度。但要注意网关需要安全存储用户的刷新令牌,并且要处理并发请求的场景——比如同一个用户的多个请求同时触发令牌刷新,要避免重复调用认证服务,可以用分布式锁或者原子操作来控制。
3. 短令牌+令牌黑名单(适合无法使用刷新令牌的场景)
如果出于安全考虑不想用刷新令牌,可以采用短有效期的access token(比如5-15分钟),同时维护一个全局的令牌黑名单:
- 当服务调用下游时遇到令牌过期的401,直接返回错误给上游调用方
- 上游服务收到错误后,引导用户重新登录(或者用静默方式从认证服务获取新token),然后重试请求
这种方式的优点是令牌泄露的风险极低,但缺点是需要维护黑名单系统(比如用Redis存储),而且频繁获取token可能会增加认证服务的压力,适合对安全性要求极高的业务场景。
4. 服务间使用内部专用令牌
有时候不需要在服务间传递用户的access token,可以为服务间调用单独配置内部认证令牌:
- 每个服务用自己的服务账户向认证服务申请专用的JWT令牌,有效期可以设置得更长(比如1小时甚至更久)
- 服务调用下游时,携带这个内部令牌,而不是用户的token
这种方式彻底避免了用户令牌过期的问题,同时也能保证服务间调用的安全性。但要注意内部令牌的权限要严格控制,只能允许调用指定的服务接口,避免出现越权访问的情况。
额外注意事项
- 不管用哪种方案,重试机制一定要加上指数退避策略(比如第一次等1秒,第二次等2秒,第三次等4秒),避免大量重试请求导致系统雪崩
- 所有令牌(尤其是刷新令牌)都要加密存储,绝对不能明文存在代码或者配置文件里
- 要做好日志监控,跟踪令牌过期、刷新和重试的情况,方便后续排查问题
内容的提问来源于stack exchange,提问作者Igor
相关产品推荐
相关产品推荐

