Skip to content

Prometheus 离线部署完全指南:从 Chart 导出到镜像打包 ​

Prometheus 离线部署完全指南:从 Chart 导出到镜像打包示意图

前言 ​

在成功部署 Grafana 之后,我们需要为其配置数据源。Prometheus 作为最流行的监控系统,是 Grafana 的天然搭档。然而,在内网环境中,我们同样需要提前准备好 Prometheus 的离线部署包。

本文完整记录了 Prometheus Helm Chart 离线包的制作过程,包含:

  • Chart 拉取与依赖处理
  • 镜像版本修复(Chart 中的 appVersion 与实际镜像 tag 不一致的坑)
  • values 配置
  • 镜像导出
  • 内网部署与验证

环境说明 ​

项目信息
操作系统Ubuntu 22.04 / CentOS 7
Kubernetes1.25+
Helm 版本v3.14.0+
Chart 版本prometheus-25.27.0
Prometheus 版本v2.54.1
容器运行时containerd

第一部分:拉取 Prometheus Chart ​

1.1 添加 Helm 仓库 ​

bash
# 添加 Prometheus 社区仓库
helm repo add prometheus-community https://prometheus-community.github.io/helm-charts
helm repo update

1.2 查看可用版本 ​

bash
# 搜索 Chart 版本
helm search repo prometheus-community/prometheus

1.3 拉取 Chart ​

bash
# 拉取指定版本(以 25.27.0 为例)
helm pull prometheus-community/prometheus --version 25.27.0

# 或拉取最新版本
helm pull prometheus-community/prometheus

# 解压查看
tar -zxvf prometheus-25.27.0.tgz
cd prometheus/

第二部分:处理 Chart 依赖 ​

2.1 查看依赖信息 ​

bash
cat Chart.yaml | grep -A 20 "dependencies:"

输出示例:

yaml
dependencies:
- condition: alertmanager.enabled
  name: alertmanager
  repository: https://prometheus-community.github.io/helm-charts
  version: 1.12.*
- condition: kube-state-metrics.enabled
  name: kube-state-metrics
  repository: https://prometheus-community.github.io/helm-charts
  version: 5.25.*
- condition: prometheus-node-exporter.enabled
  name: prometheus-node-exporter
  repository: https://prometheus-community.github.io/helm-charts
  version: 4.39.*
- condition: prometheus-pushgateway.enabled
  name: prometheus-pushgateway
  repository: https://prometheus-community.github.io/helm-charts
  version: 2.14.*

2.2 下载所有依赖 ​

bash
# 下载依赖到 charts/ 目录
helm dependency update .

# 查看下载的依赖
ls -la charts/
# alertmanager-1.12.0.tgz
# kube-state-metrics-5.25.0.tgz
# prometheus-node-exporter-4.39.0.tgz
# prometheus-pushgateway-2.14.0.tgz

2.3 重新打包(含所有依赖) ​

bash
cd ..
helm package prometheus/
# 生成 prometheus-25.27.0.tgz(包含所有子 Chart)

第三部分:镜像版本问题 —— 关键坑点 ​

3.1 问题发现 ​

查看子 Chart 的 appVersion:

bash
cat prometheus/charts/prometheus-node-exporter/Chart.yaml | grep appVersion
# appVersion: 1.8.2

cat prometheus/charts/kube-state-metrics/Chart.yaml | grep appVersion
# appVersion: 2.13.0

3.2 问题分析 ​

组件Chart 中 appVersionDocker Hub/Quay.io 实际 tag是否一致
prometheus-node-exporter1.8.2v1.8.2缺少 v 前缀
kube-state-metrics2.13.0v2.13.0缺少 v 前缀

关键问题:Chart 中的 appVersion 不带 v 前缀,但镜像仓库中的 tag 带 v。如果直接使用默认值,部署时会拉取不存在的镜像。

3.3 解决方案:创建自定义 values 文件 ​

cat > prometheus-values.yaml <<'EOF'
# 全局配置
global:
  scrape_interval: 15s

# 禁用不需要的组件(内网环境精简部署)
alertmanager:
  enabled: false
  image:
    repository: prometheus/alertmanager
    tag: v0.27.0
    pullPolicy: IfNotPresent

# 禁用不需要的组件(内网环境精简部署)
prometheus-pushgateway:
  enabled: false
  image:
    repository: prometheus/pushgateway
    tag: v1.9.0
    pullPolicy: IfNotPresent

# 修复 Node Exporter 镜像 tag
prometheus-node-exporter:
  enabled: true
  image:
    repository: prometheus/node-exporter
    tag: v1.8.2          # 带 v 前缀
    pullPolicy: IfNotPresent

# 修复 kube-state-metrics 镜像 tag
kube-state-metrics:
  enabled: true
  image:
    repository: kube-state-metrics/kube-state-metrics
    tag: v2.13.0         # 带 v 前缀
    pullPolicy: IfNotPresent

# Prometheus Server 配置
server:
  persistentVolume:
    enabled: false       # 测试环境不持久化
  image:
    repository: quay.io/prometheus/prometheus
    tag: v2.54.1
    pullPolicy: IfNotPresent
EOF

第四部分:验证 Chart 配置 ​

4.1 渲染模板,查看镜像地址 ​

bash
helm template test ./prometheus/ -n monitoring \
  -f prometheus-values.yaml \
  | grep -E "image:" | sort -u

4.2 预期输出 ​

yaml
image: "quay.io/prometheus-operator/prometheus-config-reloader:v0.76.0"
image: "quay.io/prometheus/alertmanager:v0.27.0"
image: "quay.io/prometheus/prometheus:v2.54.1"
image: "quay.io/prometheus/pushgateway:v1.9.0"
image: quay.io/prometheus/node-exporter:v1.8.2
image: registry.k8s.io/kube-state-metrics/kube-state-metrics:v2.13.0

注意:prometheus-config-reloader 是 ConfigMap 热加载的 sidecar 容器,需要额外拉取。

4.3 验证没有重复 registry ​

bash
helm template test ./prometheus/ -n monitoring \
  -f prometheus-values.yaml \
  | grep "image:" | grep "quay.io/quay.io"

# 如果没有输出,说明配置正确

第五部分:拉取并保存镜像 ​

5.1 完整的镜像列表 ​

组件镜像地址用途
Prometheusquay.io/prometheus/prometheus:v2.54.1主服务
Node Exporterquay.io/prometheus/node-exporter:v1.8.2节点指标采集
kube-state-metricsregistry.k8s.io/kube-state-metrics/kube-state-metrics:v2.13.0K8s 资源状态
Alertmanagerquay.io/prometheus/alertmanager:v0.27.0告警管理
Pushgatewayquay.io/prometheus/pushgateway:v1.9.0指标推送网关
Config Reloaderquay.io/prometheus-operator/prometheus-config-reloader:v0.76.0配置热加载

5.2 一键拉取并保存镜像 ​

bash
#!/bin/bash
# 拉取并保存所有镜像

mkdir -p images

images=(
  "quay.io/prometheus/prometheus:v2.54.1"
  "quay.io/prometheus/node-exporter:v1.8.2"
  "registry.k8s.io/kube-state-metrics/kube-state-metrics:v2.13.0"
  "quay.io/prometheus/alertmanager:v0.27.0"
  "quay.io/prometheus/pushgateway:v1.9.0"
  "quay.io/prometheus-operator/prometheus-config-reloader:v0.76.0"
)

for image in "${images[@]}"; do
    echo ">> 拉取: $image"
    docker pull $image
    tar_name=$(echo $image | tr '/' '_' | tr ':' '_').tar
    echo ">> 保存: images/$tar_name"
    docker save $image -o images/$tar_name
done

echo "✅ 镜像导出完成!"
ls -lh images/

第六部分:组织离线包目录 ​

6.1 最终目录结构 ​

prometheus-offline-25.27.0/
├── prometheus-25.27.0.tgz          # Helm Chart 包(含所有依赖)
├── prometheus/                      # 源码目录(可选)
│   ├── Chart.yaml
│   ├── values.yaml
│   ├── templates/
│   └── charts/                      # 依赖子 Chart
│       ├── alertmanager-1.12.0.tgz
│       ├── kube-state-metrics-5.25.0.tgz
│       ├── prometheus-node-exporter-4.39.0.tgz
│       └── prometheus-pushgateway-2.14.0.tgz
├── prometheus-values.yaml           # 自定义配置
├── images/
│   ├── quay.io_prometheus_alertmanager_v0.27.0.tar
│   ├── quay.io_prometheus_node-exporter_v1.8.2.tar
│   ├── quay.io_prometheus_prometheus_v2.54.1.tar
│   ├── quay.io_prometheus_pushgateway_v1.9.0.tar
│   ├── quay.io_prometheus-operator_prometheus-config-reloader_v0.76.0.tar
│   └── registry.k8s.io_kube-state-metrics_kube-state-metrics_v2.13.0.tar
├── README.md                        # 部署说明
└── install.sh                       # 一键安装脚本
└── import-images.sh                 # 工作节点专用镜像导入脚本

6.2 创建部署说明 ​

bash
cat > README.md <<'EOF'
# Prometheus 离线部署包 v25.27.0

## 文件说明
- `prometheus-25.27.0.tgz` - Helm Chart 包
- `prometheus-values.yaml` - 自定义配置
- `images/` - 容器镜像目录

## 部署要求
- Kubernetes 集群 1.19+
- containerd 或 Docker 运行时
- Helm 3.0+

## 快速部署

### 方式一:一键安装
```bash
./install.sh
```

### 方式二:手动部署

#### 1. 导入镜像
```bash
ctr -n k8s.io images import images/*.tar
```

#### 2. 安装 Chart
```bash
helm install prometheus ./prometheus-25.27.0.tgz \\
  -n monitoring \\
  -f prometheus-values.yaml
```

#### 3. 验证
```bash
kubectl get pods -n monitoring
kubectl port-forward -n monitoring svc/prometheus-server 9090:80
```

## 版本信息
- Prometheus: v2.54.1
- Node Exporter: v1.8.2
- kube-state-metrics: v2.13.0
- Helm Chart: 25.27.0
EOF

6.3 创建一键安装脚本 ​

bash
cat > install.sh <<'EOF'
#!/bin/bash
# Prometheus 离线一键安装脚本
# 支持 containerd 和 Docker

set -e

NAMESPACE=${1:-monitoring}
RELEASE_NAME=${2:-prometheus}

echo ">> 创建命名空间..."
kubectl create namespace $NAMESPACE --dry-run=client -o yaml | kubectl apply -f -

echo ">> 导入镜像..."
if command -v ctr &> /dev/null; then
    echo ">> 使用 containerd..."
    for img in images/*.tar; do
        echo "  导入: $img"
        ctr -n k8s.io images import $img
    done
elif command -v docker &> /dev/null; then
    echo ">> 使用 Docker..."
    for img in images/*.tar; do
        echo "  导入: $img"
        docker load -i $img
    done
else
    echo "❌ 未检测到 containerd 或 Docker"
    exit 1
fi

echo ">> 安装 Prometheus..."
helm install $RELEASE_NAME ./prometheus-25.27.0.tgz \
  -n $NAMESPACE \
  -f prometheus-values.yaml

echo ">> 等待 Pod 就绪..."
kubectl wait --for=condition=ready pod -l app.kubernetes.io/name=prometheus -n $NAMESPACE --timeout=120s

echo ""
echo "✅ Prometheus 部署成功!"
echo ""
echo "访问方式:"
echo "  kubectl port-forward -n $NAMESPACE svc/prometheus-server 9090:80"
echo "  然后浏览器访问 http://localhost:9090"
EOF

chmod +x install.sh

6.4 创建镜像导入脚本(为多节点 Kubernetes 集群提供) ​

当 Kubernetes 集群存在多个节点时,我们需要上传离线包 prometheus-offline-25.27.0.tar.gz 到工作节点(也就是非常控制平面节点)解压离线包后只需要执行 import-images.sh 脚本,仅仅导入镜像即可,其它不需要操作!

bash
cat > import-images.sh <<'EOF'
#!/bin/bash
# 导入镜像到当前节点

set -e

echo ">> 导入镜像..."
if command -v ctr &> /dev/null; then
    echo ">> 使用 containerd..."
    for img in images/*.tar; do
        echo "  导入: $img"
        sudo ctr -n k8s.io images import "$img"
    done
elif command -v docker &> /dev/null; then
    echo ">> 使用 Docker..."
    for img in images/*.tar; do
        echo "  导入: $img"
        sudo docker load -i "$img"
    done
else
    echo "❌ 未检测到 containerd 或 Docker"
    exit 1
fi

echo "✅ 镜像导入完成!"
EOF

chmod +x import-images.sh

6.5 打包交付 ​

bash
tar -czf prometheus-offline-25.27.0.tar.gz ./prometheus-offline-25.27.0
ls -lh prometheus-offline-25.27.0.tar.gz

第七部分:内网部署与验证 ​

7.1 多节点部署说明 ​

⚠️ 多节点集群特别提醒:

如果您的 Kubernetes 集群有多个工作节点,请务必按以下顺序操作,否则 Pod 调度到未导入镜像的节点时会因镜像拉取失败而导致启动异常(ImagePullBackOff / ErrImagePull)。

推荐工作流:

bash
# 步骤 1:在所有工作节点上导入镜像
# 将离线包复制到每个工作节点,解压后执行:
./import-images.sh

# 步骤 2:在控制平面节点上执行完整安装
# 解压离线包后执行:
./install.sh

为什么这样做?

  • import-images.sh 仅导入镜像,不执行 Helm 安装
  • 确保所有节点都已准备好镜像,Kubernetes 调度器可以将 Pod 调度到任意节点
  • 避免因节点无法访问外网镜像仓库(如 registry.k8s.io、quay.io)而导致的 ImagePullBackOff

7.2 部署 ​

bash
# 1. 解压离线包
tar -xzf prometheus-offline-25.27.0.tar.gz
cd prometheus-offline-25.27.0/

# 2. 执行一键安装
./install.sh

### 7.1 部署

```bash
# 1. 解压
tar -xzf prometheus-offline-25.27.0.tar.gz
cd prometheus-offline-25.27.0/

# 2. 一键安装
./install.sh

# 或指定命名空间
./install.sh my-monitoring my-prometheus

7.3 验证部署 ​

bash
# 查看 Pod 状态
kubectl get pods -n monitoring

# 预期输出:
# NAME                                    READY   STATUS    RESTARTS   AGE
# prometheus-kube-state-metrics-xxx       1/1     Running   0          30s
# prometheus-node-exporter-xxx            1/1     Running   0          30s
# prometheus-server-xxx                   2/2     Running   0          30s

# 查看 Service
kubectl get svc -n monitoring

# 端口转发访问 Prometheus UI
kubectl port-forward -n monitoring svc/prometheus-server 9090:80

# 浏览器访问 http://localhost:9090

7.4 验证指标采集 ​

bash
# 在 Prometheus UI 中查询
# 输入:up
# 应该能看到所有 targets 的状态

# 或使用 API 查询
curl http://localhost:9090/api/v1/query?query=up

第八部分:在 Grafana 中添加 Prometheus 数据源 ​

8.1 获取 Prometheus 服务地址 ​

bash
# 集群内访问
kubectl get svc -n monitoring prometheus-server
# URL: http://prometheus-server.monitoring.svc.cluster.local:80

# 或使用 NodePort 暴露
kubectl patch svc prometheus-server -n monitoring -p '{"spec":{"type":"NodePort"}}'
kubectl get svc -n monitoring prometheus-server
# 访问:http://<NodeIP>:<NodePort>

8.2 在 Grafana 中添加数据源 ​

  1. 登录 Grafana:http://<Grafana-IP>:3000
  2. 左侧菜单 → Configuration → Data Sources
  3. 点击 Add data source → 选择 Prometheus
  4. 配置:
  • Name:Prometheus
  • URL:http://prometheus-server.monitoring.svc.cluster.local:80
  1. 点击 Save & Test

8.3 导入 Kubernetes 监控仪表盘 ​

Dashboard ID名称说明
315Kubernetes Cluster Monitoring集群整体状态
1860Node Exporter节点资源监控
17092Kubernetes Persistent VolumesPVC/PV 监控
bash
# 在 Grafana 中
# 左侧 + → Import dashboard → 输入 Dashboard ID
# 选择 Prometheus 数据源 → Import

8.4 导入 Kubernetes Persistent Volumes 数据示例 ​

第九部分:踩坑总结 ​

问题原因解决方案
Chart 中镜像 tag 与实际不一致appVersion: 1.8.2 但镜像 tag 是 v1.8.2在 values.yaml 中显式指定 tag: v1.8.2
渲染后镜像地址重复repository 包含了 registry改为 repository: prometheus/node-exporter,配合 global.imageRegistry
遗漏 config-reloader 镜像默认未关注 sidecar 容器helm template 查看所有镜像后补充拉取
内网部署时镜像拉取失败未导入镜像到 containerd使用 ctr -n k8s.io images import 导入

结语 ​

通过本文,您已经掌握了:

  1. ✅ 如何拉取 Prometheus Chart 并处理依赖
  2. ✅ 如何识别和修复 Chart 中镜像 tag 与实际不一致的问题
  3. ✅ 如何导出所有需要的镜像(包括 sidecar 容器)
  4. ✅ 如何组织生产级的离线部署包
  5. ✅ 如何在内网环境一键部署 Prometheus
  6. ✅ 如何在 Grafana 中添加 Prometheus 数据源

制作 Prometheus 离线包的核心要点:

  • Chart 依赖必须通过 helm dependency update 下载
  • 镜像 tag 需要逐个确认,不能完全依赖 appVersion
  • 使用 helm template 渲染验证所有镜像地址
  • 镜像和 Chart 缺一不可

相关资源:

附件:资源下载 ​

若您不想自行制作离线包,可直接下载已制作好的完整离线资源包,包含本文档所述的全部 Helm Chart、容器镜像、配置文件和安装脚本。

资源下载链接说明
离线包文件prometheus-offline-25.27.0.tar.gzPrometheus v25.27.0 完整离线资源包,约 182 MiB(约 191 MB;文件大小因操作系统显示标准而异)
SHA256 校验和prometheus-offline-25.27.0.tar.gz.sha256用于校验离线包完整性,确保文件未被损坏

使用建议

  1. 下载离线包后,建议先使用 sha256sum -c prometheus-offline-25.27.0.tar.gz.sha256 校验文件完整性。
  2. 将压缩包传输至目标内网服务器的 /opt/ 目录下,然后按照本文第七部分《内网部署与验证》的步骤进行部署。
  3. 多节点 Kubernetes 集群请务必参考 7.1 多节点部署说明,先在所有工作节点导入镜像,再在控制平面执行安装。
最后更新2026/08/23 15:37
如果你觉得这篇文章有帮助,或者想聊聊技术、工作,欢迎通过下面方式联系我:
contact fishfinal