首页 / 知识库 / python服务端进阶 / 服务端高并发优化

07 - 限流、降级、熔断(稳定性三板斧)

前面几章都在讲「怎么处理更多请求」。这一章反过来:当请求实在太多、处理不过来时,怎么保证系统不被彻底压垮。这就是稳定性三板斧:限流、降级、熔断

一句话先记住:扛不住的时候,宁可「拒绝一部分、牺牲一部分」,也要保住系统整体活着。


7.1 为什么需要「自我保护」

系统的处理能力有上限。当流量超过上限还硬扛,结果是全体一起死

不做保护(硬扛):
  流量 200% 超载


  所有请求都变慢 → 都超时 → 用户重试 → 流量更大 → 彻底雪崩
  结果:100% 的用户都用不了

做保护(丢卒保车):
  流量 200% 超载


  拒绝 50% → 保住 50% 能正常用
  结果:一半用户体验正常,系统活着

核心哲学:高并发下,「部分可用」远好过「全部崩溃」。


7.2 限流:控制进来的请求速率

限流 = 给系统装一个「阀门」,超过设定速率的请求,直接拒绝或排队。

四种经典限流算法

① 固定窗口计数器
   每 1 秒计数,超过 100 就拒绝,下一秒清零重来
   缺点:窗口临界点可能瞬间涌入 2 倍流量

② 滑动窗口
   把时间切成小格,滑动统计,比固定窗口更平滑

③ 漏桶(Leaky Bucket)
   请求进桶,桶以固定速率「漏出」处理
   特点:出水速率恒定,强制平滑,但不允许突发

④ 令牌桶(Token Bucket)★ 最常用
   系统匀速往桶里放令牌,请求要拿到令牌才能通过
   特点:允许一定突发(桶里攒了令牌就能瞬间放行一批)
算法特点一句话
固定窗口简单,有临界问题每秒清零重数
滑动窗口更平滑滑动统计最近一段
漏桶出速恒定,不容突发强制匀速处理
令牌桶允许突发,最常用攒令牌,凭令牌通行

在 FastAPI 里,限流常用 Redis 实现(比如用 Redis 的计数 + 过期,或 Lua 脚本实现令牌桶),因为多实例要共享限流计数。

限流放在哪一层?

[网关限流]  ← 挡住整体流量(粗粒度,最外层)

[应用限流]  ← 保护某个具体接口 / 某个用户(细粒度)

[下游限流]  ← 保护数据库、第三方 API 不被打爆

7.3 降级:关掉非核心功能,保住核心

当系统压力过大,主动关掉一些不重要的功能,把资源留给核心链路。

电商大促,系统吃紧:
  · 关掉「商品评价」「猜你喜欢」「历史浏览」  ← 非核心,降级
  · 保住「浏览商品」「下单」「支付」          ← 核心,必须活着

降级的常见形式:

  • 返回兜底数据:推荐列表挂了?返回一个默认热门列表
  • 返回默认值/空:非关键信息查不到就先不显示
  • 关闭功能:直接关掉某个耗资源的功能入口

降级是「有计划的舍弃」:提前想好「压力大时先砍哪些功能」,做成开关,紧急时一键降级。


7.4 熔断:下游挂了,别再往上撞

熔断针对的是依赖的下游服务出问题的场景。它像家里的「保险丝」——下游故障时,快速失败,别让请求堆积。

为什么需要熔断

没有熔断:
  下游服务(比如短信网关)挂了,每个请求都要等超时(比如 3 秒)
  → 大量请求卡在这里等待
  → 你的线程/连接全被占满
  → 你自己也被拖垮(故障扩散)

有熔断:
  检测到下游频繁失败 → 「熔断打开」→ 后续请求直接快速失败
  → 不再傻等,不占用资源 → 保护自己

熔断器的三个状态

   ┌─────────┐  失败率超阈值   ┌─────────┐
   │ 关闭     │──────────────▶│ 打开     │
   │ (正常)   │               │ (快速失败)│
   └─────────┘               └────┬────┘
        ▲                         │ 过一段时间
        │  试探成功                 ▼
        │                    ┌─────────┐
        └────────────────────│ 半开     │
              试探失败         │ (放几个试探)│
                             └─────────┘

关闭:正常放行
打开:直接失败,不再调用下游
半开:过一会儿放几个请求试探,好了就恢复,还不行继续打开

7.5 三者的关系

        系统压力过大 / 下游故障

      ┌─────────┼─────────┐
      ▼         ▼         ▼
    限流       降级       熔断
  控制入口   砍非核心    隔离故障下游
  (少进来)  (省资源)   (别被拖死)
手段针对做法一句话
限流入口流量太大超速率就拒绝少放点进来
降级系统整体吃紧关掉非核心功能保核心、弃枝叶
熔断下游服务故障快速失败不再调用别被拖死

本章小结

你要记住要点
核心哲学部分可用 > 全部崩溃,丢卒保车
限流控制进来的速率,令牌桶最常用
降级主动关非核心功能,保核心链路
熔断下游故障时快速失败,防止故障扩散
三者关系限流管入口、降级管自身、熔断管下游

下一章预告:前面讲的都是架构层面。回到应用本身——为什么 FastAPI 用 async 能扛更多连接?并发模型的选择,决定单机的上限。


上一章 ← 06 - 读写分离与负载均衡 | 下一章 → 08 - 并发模型与异步 IO