{"name":"流量控制","id":"软件工程-架构-系统设计-流量控制","content":"# 流量控制\n\n## 概述\n\n流量控制（Traffic Control）是一套用于确保系统在有限资源约束下保持稳定、高可用、可预测运行的治理体系。\n它通过在不同层次对流量进行识别、度量、限制和削峰，实现 **资源保护、防止过载、削峰填谷、平滑突发流量、保障核心业务稳定** 等目标。\n\n## 流量控制的本质\n\n流量控制的核心矛盾：**系统资源有限** VS **访问流量不可控且可能波动极大**\n\n因此需要建立一个能在资源逼近极限时进行自动管控的体系，使得系统在高压场景下仍能 **提供可预测、稳定、可退化的服务能力**。\n\n其目标包括：\n\n* **资源保护**：保护 CPU、内存、线程池、数据库连接等稀缺资源\n* **服务能力匹配**：使下游能力与上游流量匹配\n* **风控与业务保护**：避免因为突发流量导致全局性故障\n* **系统容错能力**：通过拒绝、降级、排队等方式避免系统雪崩\n* **服务质量治理**：防止个别接口抢占过多资源\n\n## 限流适用边界\n\n### 适用前提\n\n限流的有效性建立在以下条件之上：\n\n1. **存在资源瓶颈**—— 限流保护的是稀缺资源（CPU、内存、线程池、连接池）。无瓶颈则限流徒增复杂度\n2. **流量不可控**—— 限流的核心价值是管控无法预知的流量冲击。可控流量应优先用资源规划\n3. **需要公平性**—— 多用户/多调用方共享资源时，限流防止少数方抢占过多资源\n4. **瓶颈可观测**—— 限流依赖对资源状态的实时感知（CPU、线程池、RT）。若无法感知瓶颈，限流阈值无依据\n\n### 限流的代价\n\n引入限流需要权衡：\n\n| 问题 | 影响 |\n|------|------|\n| 误杀正常请求 | 用户体验下降 |\n| 增加系统复杂度 | 运维成本提升 |\n| 引入额外延迟 | 吞吐量下降 |\n| 阈值设置不当 | 资源浪费或保护失效 |\n\n## 限流维度\n\n同一个请求，可以消耗 1ms CPU，也可以消耗 10 秒线程。QPS 相同，资源消耗可能相差万倍。\n\n核心维度：\n\n- **QPS**——控制流速。下游处理速率恒定，QPS 限制强行将输入速率匹配到下游能力范围\n- **并发数**——控制容量。线程池、连接池资源有限，同时占用不能超过这个数\n\n两者**是不同的维度**，描述同一资源压力的不同侧面。只控 QPS 不控并发：高 QPS + 慢请求 → 线程堆积；只控并发不控 QPS：高并发 + 快请求 → 下游过载。\n\n维度选择由**瓶颈位置**决定：下游有限 → 侧重 QPS；资源池有限 → 侧重并发；高 QPS + 慢请求 → 两维组合。\n\n## 流量控制能力模型\n\n流量控制是闭环系统：识别流量特征 → 感知系统状态 → 执行控制行动。三模块对应闭环三环节，缺一则闭环断裂。\n\n### 流量画像\n\n* 流量分布（分钟级/秒级/突发情况）\n* 访问类型（读、写、热点、背景任务）\n* 调用链路影响范围\n\n### 指标体系\n\n系统能力边界依赖关键指标，包括：\n\n* **TPS（事务数/秒）**\n* **HPS（请求数/秒）**\n* **QPS（查询数/秒）**\n* 延迟 P99/P95/P90\n* 最大并发数\n* IO 带宽、网络带宽\n\n不同业务还存在自定义指标：\n如游戏的在线人数、IO 服务的最大带宽等。\n\n### 控制策略\n\n**限流策略**（控制流量不超限）：\n\n* 固定限流（静态阈值）\n* 动态限流（根据RT、错误率实时调整）\n\n**超额处理策略**（流量已超限后如何应对）：\n\n* **快速失败**——直接拒绝，减少资源浪费\n* **排队等待**——等待资源恢复，适用于可延迟请求\n* **柔性限流**——用户无感知：随机延迟、次要请求随机丢弃、前端本地缓存/去抖\n* **降级**——关闭非核心接口、返回默认值、限制写操作、去掉昂贵查询\n\n## 流量承载能力与水位模型\n\n系统承载能力必须通过：\n\n* **全链路压测**\n* **历史高峰数据**\n* **资源评估（CPU、线程、连接池、IO）**\n\n确定两类水位：\n\n* **安全水位**：系统在稳定范围可承载的流量\n* **极限水位**：系统在极端情况下能承受的最大极限\n\n过低浪费资源，过高会导致雪崩。\n\n## 限流阈值确定\n\n阈值回答的是：**系统能承受多少？该留多少余量？**\n\n**压测优先**——阈值是测出来的，不是猜出来的。观测数据只能反映\"曾经来过多少\"，无法回答\"系统极限是多少\"。用真实流量模型压到系统临界点，在重压力区上限设阈值，而非崩溃区。\n\n**冗余原则**——无法压测时，阈值 = 历史峰值 × (1 + 冗余系数)。冗余覆盖三类不确定性：流量波动、下游衰退、局部故障。核心接口冗余更大。\n\n**分层原则**——阈值沿调用链路逐层加严：入口宽松、应用精确、下游最严。游阈值总和应低于上游入口处理能力，避免流量堆积。\n\n**动态原则**——静态阈值迟早失灵。阈值必须可运行时调整，理想形态是基于 RT/错误率的自适应调节。\n\n## 流量控制核心技术模型\n\n### 计数器算法\n\n**原理**：维护一个当前活动请求数计数器，超过阈值即限流。\n典型实现：线程池大小、数据库连接池大小、Nginx worker limit。\n\n#### 固定时间窗计数\n\n```\n算法类型：固定时间窗 (Fixed Window)\n限制条件：每 1 分钟限制 100 次请求 (Limit 100 per 1min)\n\n时间轴分布：\n|-------------------------|-------------------------|------------------->\n0:00                    1:00                      2:00                时间 (Time)\n          [ 上一周期 ]              [ 当前周期 ]\n          (Last Cycle)            (Current Cycle)\n\n流量爆发点：\n                0:55      1:00      1:05\n                  ●--------|---------●\n                  |        |         |\n                  +--------+---------+\n                  |  100次 |  100次  |\n                  +--------+---------+\n                  <------- 10秒 ------->\n                        共 200 次请求\n```\n\n问题：在窗口切换的边界点可能出现突发流量未被限制。\n\n#### 滑动窗口计数\n\n```\n时间片 (Time Slices)\n      ---------------------------------------------> (滑动方向)\n      +------+------+------+------+------+------+------+\n      |  10  |  7   |  5   |  15  |  0   |  0   |  0   |\n      +------+------+------+------+------+------+------+\n             ^~~~~~~~~~~~~~~~~~~~~^\n                滑动窗口 (Window)\n```\n\n```\n滑窗 (Sliding Window)\n      ----------------------------> (数据流/处理方向)\n      +------+------+------+------+------+------+------+\n      |  0   |  7   |  5   |  15  |  8   |  5   |  7   |\n      +------+------+------+------+------+------+------+\n      ^~~~~~~^                           ^~~~~~~~~~~~~^\n      (已滑过)                            (当前窗口/活跃)\n```\n\n更精确，按前 N 时间片累计请求数判断。\n\n### 队列限流\n\n（参考：/软件工程/性能工程.md#排队论）\n\n所有请求入队，由后端消费端按能力处理。\n可扩展：\n\n* 多队列多优先级\n* 加入最长期限（避免过长等待）\n* 排队超时快速失败\n\n### 漏桶算法\n\n```\n[ 数据输入 / 流量注入 ]  <-- 可能是突发、不规律的 (Unregulated)\n              |\n              |  (滴水/排队)\n              v\n      +-------+-------+\n      |               |\n      |   [ 桶 / 队列 ]  |  <-- 缓冲区 (Buffer)，容量为 B\n      |  (已缓存的数据)  |\n      |               |\n      +-------+-------+\n              |\n              |  (恒定速率流出)\n              v\n      [ 数据输出 / 转发 ]     <-- 恒定速率 R (Regulated / Constant Rate)\n```\n\n**本质：限制处理速率（Rate）**\n\n* 入桶不限速\n* 出桶以固定速率处理\n* 桶满则丢弃流量\n\n适合：**出现瞬时高并发的时候，需要平滑流量处理** 的场景。\n\n### 令牌桶算法\n\n```\nr 令牌/秒 (填充速率)\n          |\n          |   /-----------\\\n          v  |   ( 令牌 )  |\n        +----+-----------+----+\n        |       |~~~~~|       |\n        |       |~~~~~|       | <--- 桶容量为 b 个令牌\n        |       |~~~~~|       |\n        +-------+-------+-----+\n                |\n                | (取出令牌)\n                v\n  数据包      +-------+\n  ========>  | 等待  |       / \\\n   (流入)    | 令牌  | ----> <   > ---移除令牌---> 传输至网络\n             +-------+       \\ /         (流出)\n```\n\n**本质：限制平均速率 + 允许突发流量**\n\n* 固定速率向桶中增加令牌\n* 请求需要消耗令牌\n* 允许桶中积累一定额度 → 支持突发\n\n### 动态限流\n\n借鉴 TCP 拥塞控制。\n\n方法：\n\n1. 统计 RT P99/P95\n2. RT 超出阈值 → 自动下降阈值（如降为 ½）\n3. RT 恢复 → 逐步增加阈值\n\n用于构建：\n\n* 自动调参型限流系统\n* 高频量变化系统\n\n### 分布式限流模型\n\n**单机限流**：按节点均分配额，各节点独立执行限流。动态调整配额可防止流量倾斜。\n\n**全局限流**：集中式限流服务统一发放配额。本地缓存作兜底，限流服务异常时 fallback。\n\n**货币令牌**：请求链路携带额度 token，每调用一次扣减额度，耗尽时向中心申请新额度或多系统协同限流。\n\n### 选型方法论\n\n按场景选择：\n\n| 场景      | 推荐算法        |\n| ------- | ----------- |\n| 强一致速率控制 | 漏桶          |\n| 允许突发    | 令牌桶         |\n| 并发控制    | 计数器         |\n| 可排队任务   | FIFO 队列     |\n| 高频波动业务  | 动态限流        |\n| 分布式架构   | 全局限流 / 货币令牌 |\n\n## 演进\n\n流量控制的演进，核心驱动力是**流量规模扩张与架构复杂度提升**。\n\n| 维度 | 早期 | 演进方向 |\n|------|------|---------|\n| 部署 | 单机限流 | 分布式限流（跨节点协调计数） |\n| 阈值 | 静态配置 | 自适应限流（数据驱动反馈，借鉴 TCP 拥塞控制） |\n| 响应 | 被动拦截 | 主动预测（流量预测 + HPA 联动） |\n| 粒度 | IP/接口级 | 用户画像精细化（区分正常/恶意流量） |\n| 架构 | 分层防御散落 | 沿调用链统一协调（上游缓冲，下游兜底） |\n\n## 关联内容\n\n- [/软件工程/架构/系统设计/可用性.md](/软件工程/架构/系统设计/可用性.md) 流量控制与可用性密切相关，包括限流、降级、熔断等策略保障系统可用性\n- [/软件工程/微服务/服务治理/服务容错.md](/软件工程/微服务/服务治理/服务容错.md) 服务容错机制涵盖流量控制中的熔断、限流、降级等策略，是保障系统稳定的重要手段\n- [/软件工程/架构/系统设计/网关.md](/软件工程/架构/系统设计/网关.md) 网关承担着流量控制的重要职能，实现统一限流策略、访问频控等功能\n- [/软件工程/软件设计/代码质量/软件测试/全链路压测.md](/软件工程/软件设计/代码质量/软件测试/全链路压测.md) 全链路压测是确定流量控制阈值的重要手段，通过压测可确定系统安全水位和极限水位\n- [/软件工程/架构/系统设计/伸缩性.md](/软件工程/架构/系统设计/伸缩性.md) 伸缩性与流量控制相互配合，通过指标监控和自动化扩缩容应对流量变化\n- [/软件工程/质量工程.md](/软件工程/质量工程.md) 质量工程包含流量控制相关的性能保障措施，如全链路压测、混沌工程等\n- [/软件工程/架构/系统设计/监控系统设计.md](/软件工程/架构/系统设计/监控系统设计.md) 监控系统是流量控制的重要支撑，提供QPS、TPS等关键指标监控\n- [/软件工程/架构/系统设计/可观测性.md](/软件工程/架构/系统设计/可观测性.md) 可观测性（监控、日志、链路追踪）是流量控制治理的基础，感知层是流量闭环的必要组成\n- [/软件工程/容量保障.md](/软件工程/容量保障.md) 容量保障与流量控制密切相关，通过QPS、TPS等指标确定系统容量和限流阈值\n- [/软件工程/架构/系统设计/高并发.md](/软件工程/架构/系统设计/高并发.md) 高并发系统设计中需要综合运用流量控制的各种算法和策略\n- [/软件工程/架构/系统设计/缓存.md](/软件工程/架构/系统设计/缓存.md) 缓存与流量控制同为系统保护手段，可减轻后端服务压力，缓解流量冲击\n- [/计算机网络/运输层.md](/计算机网络/运输层.md) 运输层的流量控制机制（滑动窗口）与应用层流量控制在原理上相通\n- [/编程语言/JAVA/JAVA并发编程/线程池.md](/编程语言/JAVA/JAVA并发编程/线程池.md) 线程池是流量控制在单机层面的重要实现，通过限制并发数控制流量\n- [/中间件/数据库/分库分表中间件.md](/中间件/数据库/分库分表中间件.md) 数据库中间件的限流功能是流量控制在数据访问层面的具体应用\n- [/软件工程/架构/系统设计/混沌工程.md](/软件工程/架构/系统设计/混沌工程.md) 混沌工程可验证流量控制策略在异常场景下的有效性\n- [/软件工程/性能工程.md](/软件工程/性能工程.md) 性能工程涉及流量控制相关的性能指标和排队论原理\n","metadata":"tags: ['运维', '计算机系统', '性能']","hasMoreCommit":false,"totalCommits":1,"commitList":[{"date":"2026-06-14T21:48:35+08:00","author":"MY","message":"fix(PinyinUtils): 修复拼音转换丢失末尾字符问题","hash":"c0b8439d5c7106db9384632f106863adc22dbf8c"}],"createTime":"2026-06-14T21:48:35+08:00"}