给运维 AI Agent 写 Skill:五条规则,让它按 SOP 干活

运维 Agent 跑起来不稳,大多数时候不是模型不够好,而是 Skill 没写对。

模型每次"自由发挥",同一个问题今天查这个字段、明天换一种过滤方式,结论飘,过程也不可复现。
Skill 的核心价值就一件事:把你的排障 SOP 固化下来,让 Agent 每次都走同一条链路。


目录结构先定死

k8s-pod-diagnosis/
├── SKILL.md
├── references/
│   ├── inputs.md
│   └── commands/
│       ├── 01_pod_status.sh
│       ├── 02_pod_events.sh
│       ├── 03_pod_logs.sh
│       └── 04_pod_describe.sh
└── assets/
    └── report_template.md

三层分工:

  • SKILL.md:调度层,只放规则和执行顺序
  • references/commands/:执行层,一个脚本一件事
  • assets/:输出层,约束报告格式

references/ 不是默认全量阅读区。需要参数时读 inputs.md,需要执行时直接跑脚本,整理结论时再读模板。


规则一:命令必须脚本化,不要让 LLM 临时生成

运维场景里,命令的一致性比灵活性重要得多。

LLM 每次生成命令,参数顺序可能变、过滤条件可能少、错误处理可能不一样。演示没问题,线上差一个参数就是两种结果。

脚本固化的不只是命令本身,还有:

  • 参数怎么传
  • 输出怎么裁剪
  • 哪些情况返回 [SKIP],哪些情况继续执行

规则二:SKILL.md 要短,但规则要硬

SKILL.md 的定位是执行说明,不是背景介绍。它只需要写清楚四件事:

  1. 这个 Skill 解决什么,不解决什么
  2. 输入参数去哪里看
  3. 脚本按什么顺序执行
  4. 最终输出长什么样

必须写死的规则:

  • 直接执行脚本,不读脚本内容,不改脚本逻辑
  • 某步失败后,哪些继续,哪些停止
  • 数据拿不到时标记 [SKIP],不阻塞诊断
  • 证据不足时写"待确认",不猜根因

不把这些写进去,Agent 会开始"自作聪明":先读脚本,再理解,再自己拼一套新的调用逻辑。脚本里处理好的边界条件全部被打散。


规则三:执行清单里直接给完整命令

这是最容易踩的坑。

只写脚本名:

1. 01_pod_status.sh
2. 02_pod_events.sh

这种写法对人没问题,对模型不够明确。模型会先去 read 脚本内容,再自己改写成另一套调用方式。

正确写法是直接给完整调用示例:

# 脚本 用途 调用示例
1 01_pod_status.sh Pod 状态 bash $CMD_DIR/01_pod_status.sh --kubeconfig "$KUBECONFIG" --namespace "$NS" --pod-name "$POD"
2 02_pod_events.sh Pod 事件 bash $CMD_DIR/02_pod_events.sh --kubeconfig "$KUBECONFIG" --namespace "$NS" --pod-name "$POD"

模型看到的不是"有几个脚本文件",而是"有几条应该直接执行的命令"。


规则四:脚本要失败得清楚

脚本的职责是采集和预处理,不是帮模型推理。

几个硬性要求:

  • 一个脚本只干一件事,不写万能脚本
  • 参数显式,走 CLI 参数,不从环境猜
  • 失败要明确输出错误,不静默吞掉
  • 输出格式稳定,标题和关键字段固定
  • 能在脚本里过滤的噪音,不要原样喂给模型
  • 诊断脚本默认只读,不改环境

规则五:控制 SKILL.md 的大小

SKILL.md 一旦写太长,模型容易顾此失彼:前面的规则,后面就忘了。

控制方法:

  • 详细说明拆到 references/,不堆在主文件里
  • 同一件事不在不同章节重复写
  • 如果一个 Skill 已经长到需要来回翻,考虑拆成两个

总结

一个运维 Skill 稳不稳,核心看它有没有在逼模型少猜:

  • 能枚举的规则提前写死
  • 能脚本过滤的内容不留给模型临场处理
  • 输出模板固定,不每次换说法
  • 证据不足允许说"不确定",不硬给结论

运维 Agent 不是用来展示语言能力的,是拿来接线上工作的。线上最怕的不是慢,是错得很自信。

Logo

欢迎加入DeepSeek 技术社区。在这里,你可以找到志同道合的朋友,共同探索AI技术的奥秘。

更多推荐