外观
作业优先级抢占演练
难度与前置
难度:进阶
前置:队列已按 priority-queue 拆好 P0/默认/回刷池;能在测试或演练账号提交占坑作业。
读完能做什么:按 runbook 干跑「高优抢占低优」一次,留下杀开关、队列排空时延、P0 无静默丢弃的验收数字,并知道冻结窗下能不能演。
适用场景
- 优先级与抢占规则已上线,但从未在类生产负载下验证过
- 大促前要证明回刷/即席不会拖死 P0,且抢占可回滚
- 值班要熟悉「谁被抢、告警长什么样、何时敲杀开关」
- 变更窗/冻结窗期间能否演练需要明确规则
不适用:
- 优先级语义、队列隔离理论本身(见 priority-queue,本文不重复)
- 补数窗口怎么选、怎么干跑数据正确性(见 backfill-drill)
- 依赖 READY 设计(见 dependency)
- 在生产冻结日无紧急单却强行压测(见 change-window)
真实场景(一条)
短剧投放晨间 P0 ads_ad_spend_1d 与月末回刷同集群。规则写了「P0 可抢 backfill」,但从未演练。某次回刷占满槽位后:
- P0 排队 70 分钟;无人敢点杀开关,怕误杀 P0
- 回刷被抢后无续跑,分区空洞,对账当丢数
- 事后:理论页有,演练记录无
按本 runbook:演练窗提交可控低优占坑 → 触发高优 → 记录抢占时延与排空 → 演练结束杀开关清空占坑 → 确认 P0 成功且无静默丢弃。观察期同类 P0 资源迟到从 70min 降到 ≤ 约定 SLA。
怎么做(步骤清单)
1. 演练前门禁(不通过不开跑)
text
抢占演练准入
□ 读过 priority-queue;本次只验证演练指标,不改优先级语义
□ 窗口:非冻结日 或 已走 change-window 紧急/演练批注
□ 账号:演练/测试队列;禁止用生产 P0 作业当「占坑炮灰」
□ 杀开关:可一键停演练低优 / 限流回刷并行度;值班在线
□ 回滚:演练结束恢复队列配额与并发上限的步骤已写清
□ 公告:演练频道 + 预计时长;P0 告警升级为「演练相关则标注」2. 干跑步骤(建议 45~90 分钟)
| 步 | 动作 | 记录 |
|---|---|---|
| 1 | 在 backfill/低优池提交 N 个占坑作业(CPU/内存打满保障池借用额度) | 提交时刻、并行度 |
| 2 | 确认 P0 保障池可用额度被借穿或接近借穿 | 监控截图/链接 |
| 3 | 提交或等待真实/影子 P0 作业进入队列 | P0 作业 ID |
| 4 | 观察抢占:低优是否被回收;P0 是否获得槽位 | 抢占触发时刻、P0 开始跑时刻 |
| 5 | 低优被抢后的行为:失败重试 / 续跑 / 进死信 | 是否静默丢弃 |
| 6 | 敲杀开关:停占坑、恢复配额 | 排空耗时 |
| 7 | 确认 P0 终态成功;低优可解释失败或可续 | 终态表 |
text
演练记录卡(可复制)
日期(上海):________ 窗口类型:□常规演练 □冻结期特批
占坑作业数 N:____ 队列:________
P0 作业:________
T0 占坑打满:________
T1 抢占触发:________ (T1-T0)
T2 P0 获得资源:________ (T2-T1,目标 ≤ ____ 秒/分钟)
T3 杀开关排空完成:________ (T3 敲开关起算,目标 ≤ ____)
P0 终态:成功/失败 低优:续跑/失败可解释/静默丢失*
*静默丢失 = 演练失败,必须修
值班:________ owner:________3. 与冻结窗、告警、依赖的互动
- 冻结窗:默认不演练抢占压测;例外需 change-window 批注且范围仅演练队列
- 告警:alert-oncall 频道预告;演练触发的 P2 可降噪,P0 失败仍按真警
- 依赖:影子 P0 也要满足 READY 语义,避免「没依赖却在测抢占」测成假绿(见 dependency)
- 补数:占坑不要写成真回刷生产分区;真补数安全窗仍走 backfill-drill
4. 回滚与杀开关(演练必测)
text
杀开关最小集
1) 停演练占坑作业 / 将 backfill 并发打到 0
2) 收回借用配额到 sla-guard
3) 公告「演练结束」;取消降噪
4) 若 P0 仍失败:按真警升级,不归因「演练没事」回滚失败(杀开关无效、P0 被误杀)→ 演练判定不通过,先修平台再重演。
常见坑(至少这些)
把 priority-queue 理论再抄一遍,演练步骤为空
用生产 P0 当占坑牺牲品
P0 只可作「被保护方」观测对象或影子作业。冻结日无批注开压测
与变更窗冲突。无杀开关或从未按过
排空时间未知 = 未验收。低优被抢后任务消失无日志
静默丢弃,比抢占本身更危险。演练时把所有告警静音,真 P0 失败无人知
抢占成功但依赖未 READY,P0「空跑成功」
联动 silent-failure 与 dependency。演练后不恢复并发上限,次日回刷永久 0
如何验收(带数字的前后对比)
| 项 | 改前(示例) | 改后(目标) |
|---|---|---|
| 抢占演练记录 | 无 | 每季度 ≥1 次完整卡 |
| P0 获槽时延(T2-T1) | 未知 / 70min | ≤ 约定(如 5min) |
| 杀开关后队列排空 | 未知 | ≤ 约定(如 3min) |
| 演练中 P0 静默失败/丢弃 | 有风险 | 0 |
| 低优被抢可解释(日志/状态) | 无 | 100% |
| 冻结期无批注演练次数 | ≥1 | 0 |
text
优先级抢占演练验收(可复制)
演练 ID:________ 日期:________
T2-T1:____ T3 排空:____ 杀开关可用:Y/N
P0 终态成功:Y/N 静默丢弃:____(期望 0)
冻结窗合规:Y/N 告警预告:Y/N 配额已恢复:Y/N
签字(值班长/平台):________Checklist:
- [ ] 步骤表 + 记录卡可执行,不重复 priority-queue 理论长文
- [ ] 链到 priority-queue / change-window / alert-oncall / backfill-drill / dependency
- [ ] 验收含杀开关、排空时延、P0 零静默丢弃
- [ ] 无假外链;无未公开集群名
相关专篇(互链,不重写)
| 你要做的事 | 看哪篇 |
|---|---|
| 优先级语义与队列设计 | 任务优先级与资源抢占 |
| 何时允许变更/演练 | 变更窗口与发布日历 |
| 演练告警与真警 | 告警与值班 |
| 补数干跑安全 | 补数演练 |
| READY ≠ 有资源 | 调度依赖 |
| 作业绿但结果空 | 空跑/静默失败检出 |
| 本篇 | 只做抢占演练 runbook 与验收,不替代 priority-queue |
相关面试题
题库小程序链接待定;先用站内锚点占位。
- [ ] 题:抢占演练准入清单最少要有哪些项?为何禁止用生产 P0 当占坑?(考察点:准入 + 保护 P0)→ 占位:
#todo-interview-preempt-drill-gate - [ ] 题:如何用 T2-T1 与杀开关排空时间验收演练?(考察点:可测数字)→ 占位:
#todo-interview-preempt-drill-sla - [ ] 题:低优被抢后「静默丢弃」如何判定?与作业失败可解释有何不同?(考察点:零静默丢弃)→ 占位:
#todo-interview-preempt-drill-silent - [ ] 题:冻结窗下能否做抢占压测?与 change-window 如何互动?(考察点:边界/不适用)→ 占位:
#todo-interview-preempt-drill-freeze