主题
uat1 集群 Rancher Monitoring 部署与故障排查手册
- 日期:2026-08-01
- 目标集群:
uat1(RKE2 v1.35.6+rke2r1,Rancher v2.14.3 管理的下游集群,集群 IDc-m-5dx2sdbr) - 节点:sza122023/24/29/30/31(192.168.122.23/24/29/30/31,Rocky 9.8,amd64)
- 组件:rancher-monitoring
109.0.4+up80.9.1-rancher.18+ nfs-subdir-external-provisioner 4.0.18(app v4.0.2) - 镜像/Chart 仓库:内网 Harbor
192.168.122.156:30000(镜像项目rancher、sig-storage;chart OCI 项目charts) - NFS:
192.168.122.1:/mnt/xfs/rancher/uat1
1. 背景与目标
在 uat1 集群部署 Rancher Monitoring 全栈(Prometheus / Alertmanager / Grafana / node-exporter / kube-state-metrics / adapter),要求:
- 镜像与 Helm chart 全部走内网 Harbor(离线可用);
- 监控数据持久化到 NFS;
- 通过 Rancher UI 正常访问 Grafana。
过程中解决了 3 个独立故障:集群 DNS 瘫痪、helm-operation 卡死、Grafana 代理访问 404。以下按处理顺序记录。
2. 故障一:集群 DNS 瘫痪(根因,隐蔽 40 小时)
2.1 现象
在 Rancher UI 点击安装 Monitoring 后,cattle-monitoring-system 命名空间一直为空,cattle-system 中大量 helm-operation-* Pod 报错:
Waiting for Kubernetes API to be available
Timeout waiting for kubernetes2.2 排查链
| 检查 | 结果 |
|---|---|
Pod → API Server 直连(wget https://10.23.0.1:443) | ✅ 通(401 为正常响应) |
nslookup kubernetes.default.svc.cluster.local | ❌ NXDOMAIN,两个 CoreDNS Pod 均如此 |
| CoreDNS SA 权限(用其 token 调 API) | ✅ 可正常 list endpoints,RBAC 无问题 |
| Corefile | 发现自定义 local 域配置 |
2.3 根因
集群的 HelmChartConfig/rke2-coredns 中自定义了 extraConfig,其中有一条防 mDNS 泄漏的规则:
local {
template IN ANY local {
rcode NXDOMAIN
}
}CoreDNS 域名路由按最长后缀匹配:cluster.local 也是 local 的子域,于是所有集群内部 Service 域名查询都被这条模板拦截返回 NXDOMAIN。该配置在集群创建初期(约 40 小时前)就已生效,但下游 agent 通信全部走 IP 直连,故障一直隐蔽,直到安装 Monitoring 需要解析 kubernetes.default 才爆发。
2.4 修复
在 HelmChartConfig/rke2-coredns 的 extraConfig 中显式补充 cluster.local 域(更长后缀优先匹配,恢复 kubernetes 插件应答),保留原有自定义域:
yaml
apiVersion: helm.cattle.io/v1
kind: HelmChartConfig
metadata:
name: rke2-coredns
namespace: kube-system
spec:
failurePolicy: reinstall
valuesContent: |-
extraConfig:
ai-ear.cn: # 原有:内网域名指向 Rancher 节点
parameters: |
{
template IN A ai-ear.cn {
answer "{{ .Name }} 60 IN A 192.168.122.20"
answer "{{ .Name }} 60 IN A 192.168.122.21"
answer "{{ .Name }} 60 IN A 192.168.122.22"
fallthrough
}
template IN AAAA ai-ear.cn {
rcode NOERROR
}
}
cluster.local: # 新增:显式接管集群域,避免落入 local 域
parameters: |
{
kubernetes cluster.local {
pods insecure
ttl 30
}
forward . /etc/resolv.conf
cache 30
loadbalance
}
local: # 原有:屏蔽 .local mDNS 泄漏
parameters: |
{
template IN ANY local {
rcode NXDOMAIN
}
}修改后 CoreDNS reload 插件约 30 秒自动加载,无需重启。验证:
bash
nslookup kubernetes.default.svc.cluster.local # ✅ 10.23.0.1
nslookup sza122031.local # ✅ NXDOMAIN(符合 local 域预期)
nslookup ai-ear.cn # ✅ 192.168.122.20~22DNS 恢复后,Rancher 积压的 rancher-webhook、system-upgrade-controller 升级自动完成。教训:CoreDNS 自定义短后缀域(如 local、internal)时,必须检查是否会吞掉 cluster.local 等关键域。
3. helm CLI 部署 Monitoring
Rancher UI 的安装记录已失效(管理面 apps.catalog.cattle.io 无记录),改为 helm CLI 手动部署。Rancher 通过命名空间和 release 名识别,与 UI 安装效果一致。
bash
# kubeconfig 取自任一 control-plane 节点 /etc/rancher/rke2/rke2.yaml,
# server 地址 127.0.0.1:6443 改为节点 IP
# ① CRD chart(prometheus-operator 的全部 CRD)
helm upgrade --install rancher-monitoring-crd \
rancher-monitoring-crd-109.0.4+up80.9.1-rancher.18.tgz \
--namespace cattle-monitoring-system --wait
# ② 主 chart,systemDefaultRegistry 指向内网 Harbor
helm upgrade --install rancher-monitoring \
rancher-monitoring-109.0.4+up80.9.1-rancher.18.tgz \
--namespace cattle-monitoring-system \
--set global.cattle.systemDefaultRegistry=192.168.122.156:30000 \
--wait --timeout 10m注:节点 containerd 已配置通配镜像仓库(
registries.yaml中mirrors."*"指向 Harbor),且 Harborrancher项目为 public,镜像拉取无需认证。
部署结果:10 个 Pod 全部 Running,镜像全部来自内网 Harbor,Prometheus targets 27/27 up。
4. 部署 NFS 动态供给(nfs-subdir-external-provisioner)
4.1 NFS 服务端(192.168.122.1,libvirt 宿主机)
bash
echo '/mnt/xfs/rancher/uat1 *(rw,sync,no_subtree_check,no_root_squash)' >> /etc/exports
exportfs -ra
# 任一集群节点验证
mount -t nfs 192.168.122.1:/mnt/xfs/rancher/uat1 /tmp/nfs-test && touch /tmp/nfs-test/.t && rm /tmp/nfs-test/.t && umount /tmp/nfs-test4.2 镜像与 chart 同步到内网 Harbor
bash
# Harbor 建项目(API)
curl -X POST -u '<用户名>:<密码>' -H 'Content-Type: application/json' \
-d '{"project_name":"sig-storage","public":true}' http://192.168.122.156:30000/api/v2.0/projects
curl -X POST -u '<用户名>:<密码>' -H 'Content-Type: application/json' \
-d '{"project_name":"charts","public":true}' http://192.168.122.156:30000/api/v2.0/projects
# 镜像:registry.k8s.io 经华为云 SWR 国内源同步
skopeo copy --all --dest-tls-verify=false \
docker://swr.cn-north-4.myhuaweicloud.com/ddn-k8s/registry.k8s.io/sig-storage/nfs-subdir-external-provisioner:v4.0.2 \
docker://192.168.122.156:30000/sig-storage/nfs-subdir-external-provisioner:v4.0.2
# chart:github releases 经 gh-proxy 加速下载,再以 OCI 方式推送 Harbor
curl -sL -o nfs-subdir-external-provisioner-4.0.18.tgz \
https://gh-proxy.com/https://github.com/kubernetes-sigs/nfs-subdir-external-provisioner/releases/download/nfs-subdir-external-provisioner-4.0.18/nfs-subdir-external-provisioner-4.0.18.tgz
helm registry login 192.168.122.156:30000 -u '<用户名>' -p '<密码>' --insecure
helm push nfs-subdir-external-provisioner-4.0.18.tgz oci://192.168.122.156:30000/charts --plain-http4.3 从内网仓库部署
bash
helm upgrade --install nfs-subdir-external-provisioner \
oci://192.168.122.156:30000/charts/nfs-subdir-external-provisioner \
--version 4.0.18 --plain-http \
--namespace nfs-provisioner --create-namespace \
--set nfs.server=192.168.122.1 \
--set nfs.path=/mnt/xfs/rancher/uat1 \
--set image.repository=192.168.122.156:30000/sig-storage/nfs-subdir-external-provisioner \
--set image.tag=v4.0.2 \
--set storageClass.name=nfs \
--set storageClass.defaultClass=true \
--wait验证:StorageClass nfs (default) 就绪;测试 PVC 秒级 Bound,NFS 服务端动态生成子目录;删 PVC 后自动归档为 archived-*。
5. Monitoring 开启持久化
新建 monitoring-persistence-values.yaml:
yaml
prometheus:
prometheusSpec:
storageSpec:
volumeClaimTemplate:
spec:
storageClassName: nfs
accessModes: ["ReadWriteOnce"]
resources:
requests:
storage: 20Gi
alertmanager:
alertmanagerSpec:
storage:
volumeClaimTemplate:
spec:
storageClassName: nfs
accessModes: ["ReadWriteOnce"]
resources:
requests:
storage: 5Gi
grafana:
persistence:
enabled: true
type: pvc
storageClassName: nfs
size: 5Gi
accessModes: ["ReadWriteOnce"]bash
helm upgrade rancher-monitoring rancher-monitoring-109.0.4+up80.9.1-rancher.18.tgz \
-n cattle-monitoring-system --reuse-values -f monitoring-persistence-values.yaml \
--wait --timeout 10m验证:3 个 PVC Bound,TSDB 数据持续写入 NFS(du -sh 可见增长),targets 31/31 up。
注意:NFS 承载 Prometheus TSDB 属于"可用但非最佳实践",大规模场景建议 local-path/Longhorn。Pod 重建期间 nginx 缓存的 502 约 5 分钟自愈,无需干预。
6. 故障三:Rancher UI 访问 Grafana 失败
6.1 现象
Rancher UI → Monitoring → Grafana,报错:
lost connection to cluster: failed to find Session for client stv-cluster-api6.2 原因一:瞬时隧道中断(可自愈)
该错误是 Rancher remotedialer 隧道在 cluster-agent 重启窗口的瞬时表现(Rancher 3 副本同时记录 tunnel disconnect,agent 数秒后自动重连)。确认方法:
bash
# 管理面查看集群状态
kubectl get clusters.management.cattle.io c-m-5dx2sdbr # Connected / Ready
# 各 rancher 副本近期无 "failed to find Session" 日志6.3 原因二:chart 缺少集群 ID(必须修复)
helm CLI 手动安装时 global.cattle.clusterId 为空(UI 安装会自动注入),导致 Grafana nginx 代理的 appSubUrl 变为 /k8s/clusters//api/...(空集群 ID),前端资源 URL 全部错乱。修复:
bash
helm upgrade rancher-monitoring ... --reuse-values \
--set global.cattle.clusterId=c-m-5dx2sdbr \
--set global.cattle.clusterName=uat1
# configmap 变更不会自动滚动,需手动重启
kubectl rollout restart deployment -n cattle-monitoring-system rancher-monitoring-grafana6.4 验证代理链路
流量真实路径:浏览器 → Rancher → 下游 apiserver → service → nginx(:8080)。apiserver 会剥离 /api/v1/.../proxy 前缀,nginx 收到的是 /login 这类短路径;appSubUrl 只用于前端生成回链 URL。按真实路径验证:
bash
curl -s -o /dev/null -w "%{http_code}" http://<grafana-svc>/login # 200
curl -s http://<grafana-svc>/login | grep -o 'appSubUrl[^,]*' # 含 c-m-5dx2sdbr
curl -s http://<grafana-svc>/api/health # {"database": "ok"}7. 最终验证清单
| 项目 | 结果 |
|---|---|
| helm release | rancher-monitoring + rancher-monitoring-crd deployed(109.0.4) |
| Pod | 10/10 Running |
| 镜像 | 全部来自 192.168.122.156:30000 |
| Prometheus targets | 31/31 up |
| PVC | prometheus 20Gi / alertmanager 5Gi / grafana 5Gi 全部 Bound |
| NFS 数据 | TSDB 持续写入 /mnt/xfs/rancher/uat1/cattle-monitoring-system-* |
| Grafana | Rancher UI 代理访问正常,{"database": "ok"} |
| DNS | cluster.local / ai-ear.cn / .local 三类解析均符合预期 |
8. 经验总结
- CoreDNS 自定义域先做后缀冲突检查:
local、internal、corp这类短后缀域极易吞掉cluster.local,且故障可长期隐蔽(agent 类组件走 IP 直连不受影响)。 - 排查 DNS 不要停在"Pod→API 通不通":应用层的
kubernetes.default解析才是大多数组件的真实依赖。 - helm CLI 安装 rancher-monitoring 必须补三个值:
systemDefaultRegistry(离线镜像)、clusterId、clusterName(否则 Grafana 代理和指标集群标签都会残缺)。 - Harbor OCI 托管 chart + 通配镜像仓库:内网集群可实现"chart 与镜像全内网"的离线部署模式,可复用到任意上游 chart。