外观
Flap 检测
fleet 的 BGP 抖动检测:定义、观测、打分、根因定位、处置。会话级与前缀级是同一现象的两个粒度,现象与可观测面完全不同,但共用同一套打分核与设计原则。
| 文档 | 内容 |
|---|---|
| 观测与数据源 | 会话级的纯控制面推导、前缀级的节点侧旁路采集、存储分层 |
| flap 打分算法 | 衰减打分的数学、什么算一次变化、归因、跨节点归组、告警边沿、速率与时序 |
| 根因定位 | 判别性图元差集、四个区、置信度、准确度验证方法 |
| flap 处置 | 拒收前缀、断开对端 |
一线操作见 抖动处置;健康五态见 Control Server 内部。
什么是 flap
BGP flap 指路由状态在短时间内反复变化。两个粒度:
- 会话级抖动:一条 BGP 会话反复断建(
Established ↔ 非 Established)。会话每断一次,它承载的全部路由都随之撤销与重宣,影响面大而粗。 - 前缀级抖动:会话本身稳如常,但对端反复宣告或撤回某几条前缀,或反复改这些前缀的
AS_PATH与 next-hop。会话层完全看不见,必须贴着每一条 UPDATE 才能抓到,而且要能归因——抖动是从哪家对端进来的、前缀在哪里起源。
检测产物有五种形态,从「当下强度」到「历史事实」再到「根因」:
| 形态 | 粒度 | 数据源 | 节奏 |
|---|---|---|---|
| 衰减分(会话) | BGP 会话 | runtime snapshot 的 bgp_protocols | 约 5 min |
| 衰减分(前缀) | 前缀 × 归因对端 | 节点侧 flapfeed 旁路采集会话 | 约 60 s 上报,秒级感知 |
| 告警事件 | 会话 / 前缀 | 上两者衰减分的边沿 | 60 s 评估循环 |
| 根因定位 | 前缀 | 前缀级路径证据的图分析 | 读时算 |
| 时序存档 | fleet(速率按节点) | 累计计数差分 + 评估循环落点 | 60 s 桶,留 60 天 |
代码里沿用 P0(会话)/ P1(前缀)/ P2(告警)作简写标签,端点名也带这层含义(bgp-flaps / prefix-flaps / flap-alerts)。
三条设计原则
读代码前先记住这三条,它们贯穿全部检测逻辑:
只观测、只告警,不自动抑制。 检测层绝不参与对账与 apply,也绝不自动改路由。发现抖动只在榜单和告警流里透出;任何抑制动作都是操作员显式触发的处置,声明式下发、可撤销。一次误判不会自己放大成事故。
指数衰减打分,而非固定窗口滞回。 每次 flap 事件给对应主体
+1,分数随时间按半衰期连续衰减。好处是有记忆(短时间多次抖动累加)、单参可调(只有半衰期一个旋钮)、消警自然(不再抖,几个半衰期后自己滑落)。分数锚定在最近一次事件时刻,读取时从锚点续衰到当前——不需要后台定时器降温,榜单读一次就是当下值。宁可漏检,不可虚报。 采集失败、快照乱序、时间戳分辨率不足、会话重建的全表重灌——凡是分不清「真抖动」还是「观测假象」的场合,一律不计分。得到的分数是抖动强度的下界。
API 端点一览
只读观测端点在 /control/v1/ui,处置端点在 /control/v1/admin,都需要管理凭据。门户侧另有只读子集,见 自动对等 API。
| 端点 | 形态 | 作用 |
|---|---|---|
GET /ui/fleet/bgp-flaps | 会话 | 全机群会话 flap 榜 |
GET /ui/nodes/{id}/bgp-flaps | 会话 | 单节点会话 flap 与转移历史 |
GET /ui/fleet/prefix-flaps | 前缀 | 前缀 flap 榜 + 各节点喂送健康度;?group=prefix 每行内嵌 localization |
GET /ui/fleet/prefix-flaps/localize | 前缀 | 各抖动前缀的根因区定位(独立端点) |
GET /ui/fleet/flap-stats | 时序 | fleet 级活动时序与 90 分位截尾均值仪表 |
GET /ui/fleet/flap-peers | 前缀 + 会话 | 「哪家对端最抖」榜 |
GET /ui/fleet/flap-peers/{asn} | 前缀 + 会话 | 单对端详情:聚合 + 该方向前缀行 + 告警事件 |
GET /ui/fleet/flap-alerts | 告警 | 告警事件流(游标分页) |
GET /admin/fleet/mitigations | 处置 | 当前生效处置汇总 |
POST /admin/fleet/mitigations/prefix-block | -unblock | 处置 | 拒收 / 撤销前缀 |
POST /admin/fleet/mitigations/peer-disable | -enable | 处置 | 断开 / 恢复对端 |
会话列表类端点(如 /ui/nodes/{id}/bgp-sessions/status)会把会话级的 flapping 与 flap_score 就地并入每行:一条会话此刻可能是 Established,但只要衰减分过线就标 flapping,排序时抖动中的排最前。
字段细节见 控制台 BFF API。
参数速查
| 常量 | 值 | 位置 | 含义 |
|---|---|---|---|
| 会话级半衰期 | 1800 s | services/flaps.py | 会话分数半衰期 |
| 会话级阈值 | 3.0 | services/flaps.py | 需连续 4 份抖动快照(约 20 min)过线;3 次断连在任意间隔下都不过线 |
| 前缀级半衰期 | 600 s | flapfeed_scoring.py / prefix_flaps.py | 前缀分数半衰期。两侧必须同参 |
| 前缀级榜单线 | 20.0 | prefix_flaps.py | 榜单与徽章的 flapping 判定 |
| 前缀级告警线 | 100.0 | prefix_flaps.py | 告警开单线,与榜单线分层 |
| 消警线 | 告警线 ÷ 2 | flap_alerts.py | 迟滞,防开关乒乓(前缀 50 / 会话 1.5) |
| 剪枝分 | 0.5 | flapfeed_scoring.py | 低于即从计分表剔除 |
| 路径证据条数 | 12 | flapfeed_scoring.py | 每前缀上报的 distinct AS_PATH 上限 |
| 定位嫌疑图元阈值 | 0.5 | flap_localize.py | 判别分达不到即判 origin(散布) |
| near 门控 | 会话级阈值 3.0 | ui/observability.py | 本侧会话分未过阈的 near 置信 ×0.6、标不可断 |
| 喂送 hold | 720 s | flapfeed_bgp.py | 采集会话 hold time,KEEPALIVE 按 1/3 发 |
| 喂送 stale | 300 s | prefix_flaps.py | 控制面标记节点喂送陈旧 |
| 热态 blob TTL | 7 天 | prefix_flaps.py | pflap:<node> 的 Redis 过期时间 |
| 告警评估 | 60 s | flap_alerts.py | 边沿评估循环周期,兼活跃度落点节奏 |
阈值与会话级半衰期可经 [flap] 配置段调整,见 Control Server 配置。前缀级半衰期因 agent 耦合刻意不可调。