首页/数据/NoSQL 速查/过载保护:限流、排队与降级
选型与架构50 条

过载保护:限流、排队与降级

过载时系统吞吐会随并发上升而下降,保护手段是限制在途请求:入口限流、队列上限、快速失败与按优先级降载。数据库层配合超时、只读降级与熔断,把压力挡在存储之前。

NoSQL 速查数据更新于 2026-10-13

过载时为什么越忙越慢

系统超过饱和点后,吞吐会随并发上升而下降:请求排队、上下文切换、锁竞争与重试叠加,让响应时间急剧恶化。过载保护的核心不是提升上限,而是限制在途请求数量并让多余请求快速失败:入口限流、队列上限、优先级降级与熔断,都是围绕「不让无限请求堆进系统」设计的。

入口限流(nginx 示例)

入口限流(nginx 示例)
# 按来源地址限速,zone 名与共享内存区域大小要事先定义
limit_req_zone $binary_remote_addr zone=api:10m rate=20r/s;

server {
  location /api/ {
    limit_req zone=api burst=40 nodelay;   # burst 允许的突发量,nodelay 立即拒绝超出部分
    proxy_pass http://app_backend;
  }
}

# 连接数上限同样是过载保护的一部分
# limit_conn_zone $binary_remote_addr zone=conn:10m;
# limit_conn conn 20;

应用侧降载(伪代码)

应用侧降载(伪代码)
sem = BoundedSemaphore(200)      # 在途请求上限

def handle(req):
    if not sem.acquire(blocking=False):
        return reject_503()           # 快速失败,不排队堆积
    try:
        return process(req)
    finally:
        sem.release()

# 降级路径:重查询走缓存或直接返回简化结果
def search(req):
    if degraded_mode and req.is_heavy:
        return cached_or_plain_result(req)

常用手段

  • 按用户或接口限流:区分核心接口与次要接口的配额
  • 队列设长度上限:排队长度可控,超出立即拒绝而不是无限等待
  • 快速失败:宁可返回失败,也不让请求在系统里滞留数倍超时时间
  • 优先级降级:压测、导出类重任务在过载时先被拒绝或延后
  • 熔断与断路:下游连续失败时停止调用,给下游恢复留出空间
  • 数据库侧保护:短超时、只读降级、重查询走缓存

层次与要点

层次手段配置要点
入口限流、连接数上限burst 与 nodelay 决定突发流量的处理方式
应用在途请求上限、队列长度队列必须有限,排队时间要计入总超时
请求分级核心与次要接口区分配额导出、报表类重查询优先降级
数据库短超时、连接池上限、熔断连接池与超时链条要内外一致
恢复半开探测与逐步放量熔断恢复不宜一次放全量流量
重试要带退避与抖动并计入重试预算:故障期间无节制重试会把原始流量放大数倍,这是过载恶化的最常见路径。
过载时的返回值要选清楚:拒绝请求会立即产生可见错误,接受后超时则占用资源更久。通常优先选择快速拒绝并配合重试与告警。

易错点

  • 队列不限长度:请求越排越久,客户端超时后重试,形成自我加压的恶性循环
  • 过载时仍全量返回数据:分页大小、时间范围与导出任务需要能动态收窄
  • 只做入口限流不看数据库:入口被限住但慢查询仍占满连接池,系统依旧不可用
  • 熔断恢复直接放全量流量:下游刚恢复就再次被打满,出现反复震荡

数据来源与参考

  • AWS Well-Architected: 过载保护(概念参考)
  • NGINX Docs: limit_req
  • Elasticsearch Guide: Circuit breaker
​‌‌​​‌​​​‌‌​‌‌‌‌​‌‌​​​‌‌​‌‌‌​​‌‌​​‌​‌‌‌​​‌‌‌​​​‌​‌‌​‌​​‌​‌‌‌​​​‌​‌‌​‌​​‌​‌‌​​​‌‌​‌‌‌​‌​​​‌‌​‌‌‌‌​​‌​‌‌‌​​‌‌​​​‌‌​‌‌​‌‌‌‌​‌‌​‌‌​‌