先定读者,再定输出

举报
yd_257405204 发表于 2026/10/23 09:17:53 2026/10/23
【摘要】 值班的同学凌晨三点打开终端,只想一眼看到"哪台机器有问题";交接班的人想对比昨天和今天;告警系统只想拿到一个结构化的结论。同一份脚本输出要同时喂饱这三种读者,靠的不是加日志,而是约束格式。 先定读者,再定输出 大多数体检

值班的同学凌晨三点打开终端,只想一眼看到"哪台机器有问题";交接班的人想对比昨天和今天;告警系统只想拿到一个结构化的结论。同一份脚本输出要同时喂饱这三种读者,靠的不是加日志,而是约束格式。

先定读者,再定输出

大多数体检脚本一开始都是给自己写的:echo "checking disk..."、echo "done",跑通了就上线。三个月后没人看得懂输出,因为里面混了三类信息:进度日志、检查结果、异常堆栈。它们的受众完全不同。

  • 进度日志给写脚本的人调试用,应该走 stderr,或者只在 --debug 下出现;
  • 检查结果给值班和交接班的人看,走 stdout,格式必须稳定;
  • 结构化数据给告警系统和 CI 看,用 --format=json 单独输出。

把这三样混在同一个 stdout 里,是脚本"活不过半年"的最常见原因。

结论先行:第一屏就要能下判断

不要按脚本内部执行顺序输出。检查项的执行顺序是代码结构决定的,和严重程度无关。第一行固定放汇总,例如:

[FAIL] 共 24 项,通过 20,警告 2,失败 2:disk_var、ntp_offset

下面再按 FAIL → WARN → INFO → PASS 排序,同一级别内按检查项 id 字典序。每行固定五个字段:状态、检查项 id、当前值、阈值、建议动作。id 用英文短名并保持稳定,比如 disk_var 而不是"根分区使用率检查",因为 id 会被 grep、被写进白名单、被告警规则引用,改一次就要改五处。

让 diff 有意义:输出必须可比较

体检脚本真正的价值在横向对比——和昨天比、和同机房的另一台比。所以输出要能被 diff:

  • 时间戳只出现在 header 里,行内一律不放;
  • 所有列表按 id 排序,不按发现顺序;
  • 数值统一单位与精度,用 printf "%.1f%%" 而不是直接打印浮点;
  • 列宽固定,中文放最后一列,避免对齐被多字节字符打乱。

把结果写到 /var/log/healthcheck/latest.txt,同时保留最近 30 份带日期的副本。噪声为 0 之后,diff yesterday.txt today.txt 的输出就是当天真正发生的变化。

阈值与抑制:别让同一件事报三次

没有抑制机制的体检脚本会在磁盘满之前先把人逼疯。三个最小可用的手段:

  • 分级:只有 FAIL 触发告警,WARN 进日报,INFO 只在 --verbose 下出现;
  • 连续计数:状态文件里存 {id: {count, last_notify}},连续 3 次失败才告警,恢复时补一条恢复通知;
  • 带过期的白名单:豁免项必须写 expires: 2025-06-30,到期自动失效。没有过期时间的白名单,半年后就是一张"没人敢删"的清单。

阈值不要硬编码在脚本里。放到 healthcheck.conf,脚本只负责读和比,调阈值不需要改代码、不需要 review。

退出码与双通道输出

退出码是脚本和外部世界唯一的强约定,别浪费它:0 全部通过,1 有 WARN,2 有 FAIL,3 脚本自身出错。这样 CI 里直接 ./check.sh || notify 就能用,也能区分"机器有问题"和"脚本挂了"。

同时提供 --format=json,字段名和文本输出保持一致:jq -r '.items[] | select(.status=="FAIL") | .id' 就能取出失败项去驱动自动化处置。人看文本、机器看 JSON,两份输出共用同一份采集结果,不要写两套逻辑。

【声明】本内容来自华为云开发者社区博主,不代表华为云及华为云开发者社区的观点和立场。转载时必须标注文章的来源(华为云社区)、文章链接、文章作者等基本信息,否则作者和本社区有权追究责任。如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@huaweicloud.com
  • 点赞
  • 收藏
  • 关注作者

评论(0)

0/1000
抱歉,系统识别当前为高风险访问,暂不支持该操作

全部回复

上滑加载中

设置昵称

在此一键设置昵称,即可参与社区互动!

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。