症状
监控里三个计划任务天天报 退出码 1:
SuperAIMaintain(每日维护)SuperAIFullSuite(全量套件)SuperAIMonthlyDeepCheck(月度深度体检)
第一反应通常是"维护逻辑坏了"。但这次不是。
查的顺序(这套顺序可复用)
- 先看任务状态,不看日志:
Get-ScheduledTask+Get-ScheduledTaskInfo→ 拿到State、LastRunTime、LastTaskResult(1 = 失败)。 - 看它到底跑哪个脚本:
(Get-ScheduledTask -TaskName X).Actions→ 通常是个 wrapper(task_wrappers_py/X.py)。 - 读 wrapper 日志:
data/logs/tasks/X_<日期>.log,注意每一步的exit=和最后那行「总判定」。 - 读产物 JSON:
data/reports/ai_pc_maintain_<日期>.json→ 看all_ok和逐个steps[name].exit。
第 4 步是转折点:
{ "steps": { ...19 个步骤... }, "all_ok": false }
19 个步骤里只有 1 步 exit=1,其余 18 步全是 exit=0。失败的那一步叫:
安全带(功能体检) cmd = workdir/safety_gate.py --quiet exit=1 (跑了 462 秒)
因果链
safety_gate.py --quiet exit=1 「有 7 项异常」
⇒ ai_pc_maintain_<date>.json all_ok = False
⇒ achievements_board.py:93 d["maint_ok"] = j.get("all_ok") ⇒ False
⇒ SuperAIMaintain 退出码 1
⇒ 另外两个套件同样调用安全带 ⇒ 同样退出码 1
所以:维护本身没坏,是"安全带"把它连坐了。 修闸门 = 同时修三个任务。
今天顺着这条链做的两件事
闸门从 7 项降到 6 项,都是"让证据变新鲜",一行判断逻辑都没改:
| 项 | 之前 | 现在 |
|---|---|---|
| 规则与记忆体检 | ❌ 报告是 78.2 小时前写的 | ✅ 通过(重跑生成器) |
| 仪表盘证据新鲜度 | ❌ 5 条证据过期 | ❌ 但降到 4 条(重跑其中一个校验脚本,那条退出了名单) |
剩下两处我故意没动,并且写清楚了为什么:
vision_cluster_entry_selfcheck.json:全仓库搜了一圈,只有读取方、没有产出脚本 ⇒ 不知道该怎么合法地把它变新鲜;cifar_boost_run_*.txt:要重跑训练脚本(重活),而当时内存占用 89%,按我自己定的阈值不跑。
"没做"也要写成结论——否则下一个人会以为"已经修好了"。
一条可以带走的判据
看到"某个任务持续失败",先问"它是在哪一步失败的",而不是"这个任务哪里坏了"。 如果失败步是检查类步骤(安全体检、门禁、自检),那要修的是检查所指向的东西,不是任务本身。
反例(防止把这条用歪)
如果某天失败的是业务步骤,那就该修业务步骤。只有失败步明确是"安全检查"时,才适用上面这条因果链。 判断口径要写进文档,不然下一个看到"任务失败"的人会把所有锅都推给闸门——那也是一种偷懒。