实用脚本能自动监控Kubernetes集群?5个开源工具+Shell自动化方案
目录导读
- 为什么需要自动监控K8s集群? – 生产环境的故障成本与监控必要性
- 五大开源监控工具对比 – Prometheus、Grafana、Kube-State-Metrics等实战对比
- Shell+Python自动脚本实战 – 从资源巡检到告警推送的完整代码
- 如何避免监控脚本的陷阱? – 高频轮询、API限流与冗余告警解决
- 常见问题QA – 权限、性能、多云监控的核心疑问
- 总结与行动清单 – 从0到1搭建你的自动监控脚本
为什么需要自动监控K8s集群?
当你的Kubernetes集群从开发环境扩展到30+节点、500+Pod时,手动kubectl top已经无法应对突发故障,根据CNCF 2024调查报告,63%的生产级K8s事故源于监控缺失或告警延迟,自动监控脚本的核心价值在于:

- 实时捕获异常:比如节点OOM(内存溢出)、Pod CrashLoopBackOff、HPA(自动扩缩容)失效
- 降低人力成本:运维团队从被动排查转向主动防御
- 可视化与告警:将CPU/内存/网络数据转化为可执行的报警通知
五大开源监控工具对比(基于搜索引擎真实用户反馈)
| 工具 | 核心优势 | 适合场景 | 常见坑 |
|---|---|---|---|
| Prometheus | 多维数据模型+PromQL | 时序数据采集、长期存储 | 存储膨胀需配置保留策略 |
| Grafana | 可视化仪表盘+告警引擎 | 监控面板展示、多数据源 | 复杂告警规则需调试 |
| Kube-State-Metrics | 无侵入暴露K8s对象状态 | 资源quota、HPA状态监控 | API版本兼容性问题 |
| Node Exporter | 节点级硬件/系统指标 | 节点CPU丢包、磁盘IO | 需单独部署至daemonset |
| Alertmanager | 告警去重+路由+静默 | 告警通知至Slack/钉钉/邮件 | 高并发场景需配置集群模式 |
搜索引擎关键词优化提示:大量用户搜索“K8s监控脚本不重启Pods”或“自动发现Pod异常并重启”,这正是脚本化的突破口。
Shell+Python自动脚本实战:从资源巡检到告警
以下脚本结合了kubectl与Python的requests库,注意域名已替换为示例且不包含真实URL。
基础资源巡检脚本(Shell)
#!/bin/bash
# k8s_monitor.sh 自动检测节点与Pod状态
# 用法:crontab -e 添加 */5 * * * * /path/k8s_monitor.sh
log_file="/var/log/k8s_monitor_$(date +%Y%m%d).log"
alert_threshold=80 # CPU/内存使用率告警阈值
# 检测节点状态
not_ready_nodes=$(kubectl get nodes | grep -v "Ready" | grep -v "STATUS")
if [ -n "$not_ready_nodes" ]; then
echo "[ERROR] 节点异常: $not_ready_nodes" | tee -a $log_file
fi
# 检测CrashLoopBackOff的Pod
crash_pods=$(kubectl get pods --all-namespaces | grep -i "CrashLoopBackOff")
if [ -n "$crash_pods" ]; then
echo "[WARN] CrashLoopBackOff Pod: $crash_pods" | tee -a $log_file
# 自动重启(谨慎使用!)
echo "$crash_pods" | awk '{print $1, $2}' | while read ns pod; do
kubectl delete pod -n $ns $pod --grace-period=0 --force 2>/dev/null
done
fi
# 检测节点CPU/内存使用(需要metrics-server)
curl -s --cacert /etc/kubernetes/pki/ca.crt --cert /etc/kubernetes/pki/apiserver-kubelet-client.crt --key /etc/kubernetes/pki/apiserver-kubelet-client.key \
"https://example.com:6443/api/v1/nodes" | jq '.items[].status.capacity | {cpu: .cpu, memory: .memory}'
# 重要提示:域名部分已改为占位符,实际需替换为你集群的API Server地址(无需证书认证时可简化为kubectl top nodes)。
Python增强版:告警推送(钉钉示例)
# k8s_alert.py 自动统计异常并发送消息
import subprocess
import requests
import json
WEBHOOK_URL = "https://example.com/robot/send?access_token=xxx" # 替换为实际Webhook
def get_alerts():
result = subprocess.run(['kubectl', 'get', 'pods', '--all-namespaces', '-o', 'json'],
capture_output=True, text=True)
pods = json.loads(result.stdout)['items']
alerts = []
for pod in pods:
status = pod['status'].get('phase', 'Unknown')
container_status = pod['status'].get('containerStatuses', [])
for cs in container_status:
if cs.get('state', {}).get('waiting', {}).get('reason') in ['CrashLoopBackOff', 'ErrImagePull']:
alerts.append({
'namespace': pod['metadata']['namespace'],
'name': pod['metadata']['name'],
'reason': cs['state']['waiting']['reason']
})
return alerts
def send_dingding(msg):
payload = {"msgtype": "text", "text": {"content": msg}}
requests.post(WEBHOOK_URL, json=payload, timeout=5)
if __name__ == "__main__":
alerts = get_alerts()
if alerts:
msg = f"K8s异常告警:发现{len(alerts)}个问题Pod\n"
for a in alerts[:5]: # 限制前5个避免刷屏
msg += f" - {a['namespace']}/{a['name']}: {a['reason']}\n"
send_dingding(msg)
自动化部署建议
- 定时执行:在集群节点上配置crontab
*/5 * * * * /usr/bin/python3 /opt/k8s_alert.py - 权限控制:创建ServiceAccount并绑定
cluster-admin角色(生产环境建议最小权限) - 日志管理:使用
logrotate控制日志大小,避免磁盘爆满
如何避免监控脚本的陷阱?
常见坑1:高频轮询打爆API Server
- 问题:每个节点独立执行
kubectl get pods,导致API Server QPS飙升 - 解决:使用
kubectl cache或通过kube-state-metrics暴露指标,而不是直接调用API
常见坑2:自动重启导致雪崩
- 问题:脚本自动删除CrashLoopBackOff的Pod,但底层问题(如配置错误)未修复
- 解决:添加安全阀值(如限制1小时内最多重启3次),并发通知到运维群
常见坑3:时间戳与时区漂移
- 问题:不同节点时间不一致导致日志混乱
- 解决:脚本内使用
date -u标准UTC,并定期运行ntpdate同步
常见问题QA(基于Bing/Google高频搜索)
Q1:脚本需要kubectl权限吗?是否安全?
A:需要,建议在集群内通过ServiceAccount分配只读权限(如view角色),避免使用kubeconfig admin。绝对不要在脚本中硬编码明文token,请使用Kubernetes Secrets挂载。
Q2:监控多个集群时怎么办?
A:在脚本中传入多个Kubeconfig路径,或使用kubectl --context切换,更推荐用Prometheus联邦集群实现统一监控。
Q3:能否监控自定义指标(如应用JVM)?
A:可以,通过Prometheus Client暴露指标后,将scripts升级为Exporter形式,或通过kubectl exec采集特定端点,注意exec会占用Pod资源,建议使用Sidecar模式。
Q4:脚本报错“certificate signed by unknown authority”怎么办?
A:确认K8s API证书正确,或在脚本中添加--insecure-skip-tls-verify(仅限内部网络),安全方案是拼接正确的CA证书路径。
Q5:如何避免告警轰炸?
A:使用Alertmanager的group_wait和repeat_interval去重;在脚本中设置静默周期(如同一Pod每小时只告警一次)。
总结与行动清单
你现在可以立即执行的步骤:
- 部署metrics-server:确保
kubectl top nodes正常返回数据 - 复制并测试巡检脚本:先放在非生产集群验证,注意域名替换
- 配置告警渠道:联系运维获取钉钉/飞书/企业微信Webhook
- 设置crontab:注意避免集群中所有节点同时执行,随机偏移秒数(如
*/5 * * * * sleep ${RANDOM:0:2}; ./monitor.sh)
最后提示:监控脚本不是万能的,它只能处理已知模式的异常,真正生产级监控请结合Prometheus Operator、Loki日志、Tempo链路追踪构成可观测性体系,但作为入门或小团队,一个自动脚本足以将响应时间从小时级压缩到分钟级。
本文综合自CNCF官方文档、Kubernetes社区最佳实践及一线运维案例