ARTICLE DETAIL

建站实战干货

来自一线的建站与推广经验沉淀,每一条都经过真实交付验证。

Kubernetes v1.35 云原生平台实战:MetalLB、Prometheus、GitLab CI/CD 与 HPA

2026/9/4 9:23:35 拓冰建站 浏览量
Kubernetes v1.35 云原生平台实战:MetalLB、Prometheus、GitLab CI/CD 与 HPA 1. 项目目标与当前架构目标不是只部署一个 Nginx而是打通一条可验证的交付链路源码提交后由流水线构建镜像、推送镜像仓库、更新 Kubernetes 工作负载同时为应用提供统一入口、指标采集、告警与 HPA 扩缩容能力。Gitee master │ ▼ GitLab CIfetch → build → deploy │ │ │ ├─ Kaniko 构建 Commit SHA 镜像 │ └─ 阿里云 ACR ▼ Kubernetes apps/frontend-static ├─ Deployment RollingUpdate Probe ├─ Service Ingress-NGINX ├─ HPACPU 指标 └─ Prometheus / Grafana / Alertmanager1.1 实验拓扑角色主机名地址关键组件控制平面k8s-master-1192.168.117.138kube-apiserver、etcd、scheduler、controller-managerWorkerk8s-node-1192.168.117.139containerd、Calico、Ingress 后端、应用 PodWorkerk8s-node-2192.168.117.140containerd、Calico、应用 PodNFS历史存储NFS192.168.117.147/web/html迁移目标MetalLB VIP-192.168.117.188ingress-nginx-controller的 LoadBalancer 地址1.2 版本与验收快照项目当前状态OSCentOS Stream 10Kubernetesv1.35.0容器运行时containerd 2.2.1CNICalico v3.28.0kube-proxyIPVSstrictARP: true节点/Pod3/3 Ready、47/47 RunningGitLabGitLab CE 18.11.9 / Helm Chart 9.11.10监控kube-prometheus-stack 82.16.0 / Prometheus Operator v0.89.0常用验收命令kubectl get nodes -o wide kubectl get pods -A kubectl -n kube-system get configmap kube-proxy -o yaml2. 集群基础containerd、Calico 与 IPVS集群使用 kubeadm 初始化所有节点统一使用 containerd并将 kubelet 的 cgroup 驱动配置为systemd。网络层选择 CalicoPod CIDR 与kubeadm init的--pod-network-cidr保持一致。# 仅示例版本和镜像源应按实际环境确认 dnf install -y kubelet-1.35.0 kubeadm-1.35.0 kubectl-1.35.0 \ --disableexcludeskubernetes systemctl enable --now kubelet ​ # containerd 必须使用 systemd cgroup grep -n SystemdCgroup /etc/containerd/config.toml systemctl restart containerdService 转发使用 IPVS。MetalLB L2 模式需要 kube-proxy 的strictARP为true否则 VIP 的 ARP 宣告可能异常kubectl -n kube-system get configmap kube-proxy -o jsonpath{.data.config\.conf} \ | grep -E mode:|strictARP: # 预期mode: ipvs、strictARP: true3. MetalLB Ingress-NGINX裸金属 VIP 与七层路由公有云可由云厂商分配LoadBalancer地址裸金属实验集群使用 MetalLB 管理地址池。当前仅配置一个 VIP因此将它分配给ingress-nginx-controller由 Ingress 根据域名和路径转发到 ClusterIP Service。MetalLB 的IPAddressPool负责可分配地址L2Advertisement负责 L2/ARP 宣告官方说明见 MetalLB Configuration。apiVersion: metallb.io/v1beta1 kind: IPAddressPool metadata: name: first-pool namespace: metallb-system spec: addresses: - 192.168.117.188/32 --- apiVersion: metallb.io/v1beta1 kind: L2Advertisement metadata: name: example namespace: metallb-system spec: ipAddressPools: - first-poolkubectl -n metallb-system get ipaddresspool,l2advertisement kubectl -n ingress-nginx get svc ingress-nginx-controller # 当前 ServiceLoadBalancerEXTERNAL-IP192.168.117.188端口 80/443现役前端使用独立域名frontend.192.168.117.188.nip.io对应apps/frontend-static的 Ingress。根 VIP 返回 503 并不等于 MetalLB 故障当前遗留的default/web-ingress没有 Endpoint应通过目标域名验证现役路由。curl --noproxy * -I http://frontend.192.168.117.188.nip.io kubectl -n apps get ingress,service,pods当前控制器镜像为 Ingress-NGINX v1.8.1仅作为现役状态记录。Ingress-NGINX 项目已在 2026 年 3 月后结束常规维护后续生产方案应评估 Gateway API 或其他受维护的实现不要将本文环境直接宣传为可直接用于生产的入口方案。官方公告4. 存储演进NFS 故障恢复与 local-path 边界早期静态站点通过 NFS 的/web/html目录挂载到 Nginx 容器。排障中发现旧 PV 指向过期端点192.168.117.134因此采用“新建并切换、旧资源保留”的方式创建nfs-pv-html-v2/nfs-pvc-html-v2指向192.168.117.147:/web/html避免直接删除仍可回滚的旧 PV/PVC。kubectl get pv nfs-pv-html nfs-pv-html-v2 \ -o custom-columnsNAME:.metadata.name,SERVER:.spec.nfs.server,PATH:.spec.nfs.path,STATUS:.status.phase现役apps/frontend-static不再依赖 NFS流水线将index.html封装入 Nginx 镜像运行时只从 ACR 拉取版本化镜像。NFS 章节保留为一次存储迁移与回滚策略案例不作为当前前端的依赖说明。GitLab 的 PostgreSQL、Redis、Gitaly、MinIO 则使用local-path分别为 8Gi、2Gi、20Gi、10Gi。这种方式适合实验环境卷与节点绑定不具备复制存储或跨节点故障切换能力。5. 可观测Prometheus、Alertmanager 与 Grafana监控采用 Helm 部署的 kube-prometheus-stack包含 Prometheus、Alertmanager、Grafana、Prometheus Operator、Node Exporter 和 kube-state-metrics。当前已有 13 个 ServiceMonitor 与 35 个 PrometheusRule用于采集节点、Kubernetes 对象和服务指标并将规则结果交给 Alertmanager。helm -n monitoring list kubectl -n monitoring get pods kubectl get servicemonitors.monitoring.coreos.com -A kubectl get prometheusrules.monitoring.coreos.com -AGrafana 和 Prometheus 当前通过 NodePort 暴露而非第二个 MetalLB VIPkubectl -n monitoring get svc prometheus-grafana prometheus-kube-prometheus-prometheus # Grafana NodePort31356 # Prometheus NodePort30090文章不记录默认账号、密码或从 Secret 解码出的值。应通过 Kubernetes Secret、受控访问入口和独立凭据管理 Grafana、ACR 与 GitLab 的敏感信息。6. GitLab CI/CD从 Gitee 到 KubernetesGitLab 通过 Helm 部署版本为 CE 18.11.9Runner 使用 Kubernetes Executor。镜像仓库复用阿里云 ACRGitLab 内置 Registry 保持关闭。流水线的目标是从 Giteemaster获取静态资源用 Kaniko 无特权构建 Nginx 镜像以 Commit SHA 标记版本并将 Deployment、Service、Ingress、HPA 应用到apps命名空间。Gitee master → fetch-source克隆源码并保存 GITEE_COMMIT、INDEX_SHA256 → build-imageKaniko 构建并推送 registry/namespace/frontend-static:commit → deploy-appapply 清单替换镜像等待 rollout status关键变量只在 GitLab 的 CI/CD Variables 中维护不进入仓库GITEE_REPO_URL GITEE_USERNAME / GITEE_TOKEN私有仓库时需要 ACR_REGISTRY ACR_NAMESPACE ACR_USERNAME ACR_PASSWORD GIT_CLIENT_IMAGE KANIKO_IMAGE.gitlab-ci.yml的核心行为如下密码仅在运行时写入 Kaniko 的 Docker 配置variables: GITEE_BRANCH: master K8S_NAMESPACE: apps IMAGE_NAME: ${ACR_REGISTRY}/${ACR_NAMESPACE}/frontend-static # fetchgit clone --depth 1 --branch ${GITEE_BRANCH} ${GITEE_REPO_URL} source # build/kaniko/executor --destination ${IMAGE_NAME}:${GITEE_COMMIT} # deploykubectl apply ... kubectl rollout status deployment/frontend-static6.1 导入仓库不是自动同步GitLab CE 的“按 URL 导入”只在导入时复制代码后续不会持续从 Gitee 拉取。GitLab 项目自身的master必须包含最新.gitlab-ci.yml运行时的fetch-source再负责克隆 Giteemaster。因此当日志出现git clone --branch main时应同时检查GitLab 项目当前提交中的GITEE_BRANCH项目/组变量是否覆盖了 YAML 变量Gitee 的实际默认分支。6.2 三个已遇到的排障点Windows Git 自签名证书报错应将 GitLab CA 导入 Windows 受信任根证书临时排查可对单次命令使用git -c http.sslVerifyfalse不要设置全局关闭校验。GitLab 分支与 Gitee 历史分叉先git fetch gitlab和git log --left-right master...gitlab/master确认 GitLab 无独立提交后才使用git push --force-with-lease gitlab master:master。受保护分支需临时授权强推完成后立即关闭。Kaniko 推送 ACR 返回 UNAUTHORIZEDpodman login成功只说明账号可登录不代表流水线镜像路径正确。重点检查ACR_NAMESPACE是否注入正确镜像路径必须是registry/namespace/frontend-static:commit。7. 现役应用滚动更新、探针与 HPA当前apps/frontend-static的镜像由 Commit SHA 标记。Deployment 固定双副本起步使用maxUnavailable: 0、maxSurge: 1进行滚动发布并以 HTTP 探针控制就绪和存活判断。spec:replicas: 2strategy:type: RollingUpdaterollingUpdate:maxUnavailable: 0maxSurge: 1template:spec:containers:- name: frontendresources:requests:cpu: 20mmemory: 32Milimits:cpu: 200mmemory: 128MireadinessProbe:httpGet: { path: /, port: http }livenessProbe:httpGet: { path: /, port: http }HPA 使用autoscaling/v2CPU 平均利用率目标为 60%。资源 requests 是 CPU 利用率计算的前提behavior用于限制每次副本变化并避免频繁缩容。HPA 行为字段的含义可参考 Kubernetes 官方文档。本次验收中frontend-static为2/2 Ready、2/2 Available两个实例分布在不同 Worker重启次数为 0镜像标签与 Gitee Commit157d90ca9e61ff1a5d11b461e04087b84a3592af对应。早期 Nginx HPA 压测场景曾将稳定并发上限从 1000 提升至 1800、最大 QPS 提升约 12%该压测参数与当前前端 2—6 副本配置不同应分别理解。8. 发布后的验收清单# 集群基础 kubectl get nodes kubectl get pods -A # VIP 与入口 kubectl -n ingress-nginx get svc ingress-nginx-controller curl --noproxy * -I http://frontend.192.168.117.188.nip.io # 应用与 HPA kubectl -n apps get deploy,pod,svc,ingress,hpa kubectl -n apps rollout status deployment/frontend-static --timeout300s # 监控 kubectl -n monitoring get pods kubectl get servicemonitors.monitoring.coreos.com -A kubectl get prometheusrules.monitoring.coreos.com -A验收应同时检查控制面、Pod、Endpoint、HPA 条件和 HTTP 响应而不是仅看到 Pipeline 成功就判定发布完成。总结这套平台的核心价值不在于单独安装某个组件而在于把基础设施、流量、监控、镜像交付和弹性伸缩接成一条可验证的闭环代码变更可追溯到镜像标签镜像可追溯到 Kubernetes Deployment应用状态可通过探针、HPA、Prometheus 和 HTTP 验收共同确认。