📌 前置知识:本文默认读者具备 Docker 容器化、Kubernetes 基础操作经验,熟悉 Shell 脚本编写。文中所有示例基于 GitLab CI/CD 16.x、ArgoCD 2.10+、Kubernetes 1.29+ 环境。
一、引言:从"人肉部署"到 GitOps 的演进之路
在微服务架构时代,一个项目往往由十几个甚至几十个服务组成。如果仍然通过"手动打包 → 手动上传 → 手动部署"的方式发布,不仅效率低下,更会带来不可控的人为失误风险:
- 生产环境与测试环境配置不一致,导致"在我机器上明明是好的"经典问题
- 回滚依赖备份文件和人工记忆,容易出错且无法追溯
- 不同开发人员操作习惯不同,线上环境逐渐变得不可复现
GitOps 应运而生——它的核心思想只有一句话:将 Git 仓库作为系统单一真相来源(Single Source of Truth)。所有部署配置、环境参数、基础设施代码全部存储在 Git 中,任何变更都必须通过 Git 操作来完成,从而实现:
- ✅ 环境一致性:所有环境的配置均来自同一套 Git 定义
- ✅ 版本可控:每一次部署都有对应的 Git commit 可追溯
- ✅ 一键回滚:回滚即
git revert,无需手动操作 - ✅ 审计友好:Git 操作日志天然就是完整的审计记录
本文将手把手搭建一套完整的 GitOps 流水线:
代码提交(GitLab)
↓ git push
GitLab CI/CD (构建 + 镜像推送)
↓ push image to Harbor
ArgoCD (监听 Git 仓库 → 自动同步到 K8s)
↓ kubectl apply
Kubernetes 集群 (各环境 Namespace)
二、环境准备:集群与基础设施搭建
2.1 Kubernetes 集群准备
使用 kubeadm 搭建三节点集群(1 个 Master + 2 个 Worker),最低配置建议:
# 节点规划
master: 2C4G Ubuntu 22.04 LTS # 10.0.0.10
worker1: 2C4G Ubuntu 22.04 LTS # 10.0.0.11
worker2: 2C4G Ubuntu 22.04 LTS # 10.0.0.12
初始化 Master 节点:
# 所有节点安装依赖
sudo apt-get update && sudo apt-get install -y apt-transport-https ca-certificates curl
# 安装 containerd
sudo apt-get install -y containerd
sudo mkdir -p /etc/containerd
containerd config default | sudo tee /etc/containerd/config.toml
sudo sed -i 's/SystemdCgroup = false/SystemdCgroup = true/' /etc/containerd/config.toml
sudo systemctl restart containerd
# 安装 kubeadm/kubelet/kubectl
curl -fsSL https://pkgs.k8s.io/core:/stable:/v1.29/deb/Release.key | sudo gpg --dearmor -o /etc/apt/keyrings/kubernetes-apt-keyring.gpg
echo 'deb [signed-by=/etc/apt/keyrings/kubernetes-apt-keyring.gpg] https://pkgs.k8s.io/core:/stable:/v1.29/deb/ /' | sudo tee /etc/apt/sources.list.d/kubernetes.list
sudo apt-get update
sudo apt-get install -y kubelet kubeadm kubectl
sudo apt-mark hold kubelet kubeadm kubectl
# Master 初始化(Pod CIDR 使用 Calico 默认值)
sudo kubeadm init --pod-network-cidr=10.244.0.0/16 --service-cidr=10.96.0.0/12
# 配置 kubectl
mkdir -p $HOME/.kube
sudo cp /etc/kubernetes/admin.conf $HOME/.kube/config
sudo chown $(id -u):$(id -g) $HOME/.kube/config
# 安装网络插件 Calico
kubectl apply -f https://docs.projectcalico.com/manifests/calico.yaml
2.2 GitLab 部署(支持 Runner)
使用 Docker Compose 部署 GitLab CE:
# docker-compose-gitlab.yml
version: '3.8'
services:
gitlab:
image: gitlab/gitlab-ce:16.8.0-ce.0
container_name: gitlab
hostname: gitlab.example.com
environment:
GITLAB_OMNIBUS_CONFIG: |
external_url 'http://10.0.0.20'
gitlab_rails['gitlab_shell_ssh_port'] = 2222
nginx['listen_port'] = 80
postgresql['shared_buffers'] = 256MB
redis['maxmemory'] = 256mb
ports:
- "80:80"
- "2222:22"
volumes:
- /data/gitlab/config:/etc/gitlab
- /data/gitlab/logs:/var/log/gitlab
- /data/gitlab/data:/var/opt/gitlab
restart: unless-stopped
privileged: true
mkdir -p /data/gitlab/{config,logs,data}
docker-compose -f docker-compose-gitlab.yml up -d
⚠️ 注意:首次启动需要等待 5~10 分钟初始化,完成后访问
http://10.0.0.20设置 root 密码。
2.3 Harbor 私有镜像仓库部署
Harbor 是企业级 Docker 镜像仓库,支持镜像安全扫描、RBAC 权限控制、镜像复制等功能,是 GitOps 流水线的中转站。
# docker-compose-harbor.yml (Harbor 2.10)
version: '3.8'
services:
harbor:
image: goharbor/harbor-core:v2.10.1
container_name: harbor
restart: always
volumes:
- /data/harbor/data:/data
- ./ harbor.cfg:/etc/harbor/harbor.cfg:ro
network_mode: host
command: core
Harbor 配置文件 harbor.cfg:
hostname = harbor.example.com
harbor_admin_password = Harbor12345
db_password = root123
# 生产环境务必配置 HTTPS
# ssl_cert = /data/cert/server.crt
# ssl_cert_key = /data/cert/server.key
部署后访问 Harbor,创建一个名为 spring-boot-app 的公开项目(用于存放应用镜像)。
三、GitLab CI/CD 流水线设计
3.1 项目结构
spring-boot-app/
├── .gitlab-ci.yml # CI/CD 流水线配置
├── src/ # 源代码(Spring Boot 项目)
├── docker/
│ └── Dockerfile # 多阶段构建 Dockerfile
├── k8s/ # K8s 部署配置(ArgoCD 监听此目录)
│ ├── base/ # 基础配置(deployment、service 等)
│ │ ├── deployment.yaml
│ │ ├── service.yaml
│ │ └── ingress.yaml
│ └── overlays/ # 环境差异配置
│ ├── dev/
│ │ └── kustomization.yaml
│ ├── test/
│ │ └── kustomization.yaml
│ └── prod/
│ └── kustomization.yaml
└── scripts/
└── docker-build.sh
3.2 Docker 多阶段构建优化
生产级 Dockerfile 最小化镜像体积,提升冷启动速度:
# docker/Dockerfile
# ============ 构建阶段 ============
FROM maven:3.9-eclipse-temurin-21-alpine AS builder
WORKDIR /build
# 利用 Maven 缓存加速重复构建
COPY pom.xml .
RUN mvn dependency:go-offline -B
COPY src ./src
RUN mvn clean package -DskipTests -B
# ============ 运行阶段(极简镜像)===========
FROM eclipse-temurin:21-jre-alpine
WORKDIR /app
# 安全最佳实践:以非 root 用户运行
RUN addgroup -S appgroup && adduser -S appuser -G appgroup
USER appuser
# 只复制最终的 jar 包(不包括源码和构建产物)
COPY --from=builder /build/target/*.jar app.jar
# 开放非特权端口(1024 以下端口需要 root)
ENV JAVA_OPTS="-Xms256m -Xmx512m -XX:+UseG1GC"
EXPOSE 8080
# 使用 exec form 正确处理信号(PID 1)
ENTRYPOINT ["sh", "-c", "java $JAVA_OPTS -jar app.jar"]
💡 优化要点:
- 使用
eclipse-temurin:21-jre-alpine(~180MB)而非完整 JDK 镜像(~500MB)- 多阶段构建确保最终镜像不包含 Maven 源码和缓存
USER appuser遵循最小权限原则EXPOSE 8080声明应用端口(而非默认的 8080)
3.3 GitLab CI/CD 全流水线配置
.gitlab-ci.yml 是 GitLab 的流水线定义文件,使用 stages 分阶段执行:
# .gitlab-ci.yml
variables:
# 镜像仓库地址
HARBOR_URL: "harbor.example.com"
HARBOR_PROJECT: "spring-boot-app"
IMAGE_NAME: "${HARBOR_URL}/${HARBOR_PROJECT}/${CI_PROJECT_NAME}:${CI_COMMIT_SHORT_SHA}"
IMAGE_TAG_LATEST: "${HARBOR_URL}/${HARBOR_PROJECT}/${CI_PROJECT_NAME}:latest"
stages:
- build
- test
- package
- deploy
# ============ Stage 1: 代码编译 ============
maven-build:
stage: build
image: maven:3.9-eclipse-temurin-21-alpine
cache:
key: "${CI_COMMIT_REF_SLUG}-maven"
paths:
- .m2/repository
script:
- mvn clean compile -B
artifacts:
paths:
- target/classes/
expire_in: 1 hour
only:
- main
- develop
- merge_requests
# ============ Stage 2: 单元测试 + 代码质量 ============
maven-test:
stage: test
image: maven:3.9-eclipse-temurin-21-alpine
cache:
key: "${CI_COMMIT_REF_SLUG}-maven"
paths:
- .m2/repository
script:
- mvn test -B
# 生成测试覆盖率报告
- mvn jacoco:report -B
coverage: '/Total.*?([0-9]{1,3})%/'
artifacts:
when: always
reports:
junit: target/surefire-reports/TEST-*.xml
coverage_report:
coverage_format: cobertura
path: target/site/jacoco/jacoco.xml
only:
- main
- develop
- merge_requests
# ============ Stage 3: Docker 镜像构建 + 安全扫描 ============
docker-build:
stage: package
image: docker:24-dind
services:
- docker:24-dind
variables:
DOCKER_HOST: tcp://docker:2376
DOCKER_TLS_CERTDIR: "/certs"
DOCKER_TLS_VERIFY: "1"
DOCKER_CERT_PATH: "$DOCKER_HOST/certs/client"
before_script:
# 登录 Harbor(使用 GitLab CI/CD 变量存储凭证)
- echo "$HARBOR_PASSWORD" | docker login $HARBOR_URL -u "$HARBOR_USERNAME" --password-stdin
script:
- cd docker
- docker build --network=host -t $IMAGE_NAME -t $IMAGE_TAG_LATEST -f Dockerfile ..
# Trivy 安全扫描(检测 CVE 漏洞)
- docker run --rm -v /var/run/docker.sock:/var/run/docker.sock \
aquasec/trivy:latest image --severity HIGH,CRITICAL --exit-code 1 --no-progress $IMAGE_NAME
# 推送镜像到 Harbor
- docker push $IMAGE_NAME
- docker push $IMAGE_TAG_LATEST
# 清理本地镜像节省空间
- docker rmi $IMAGE_NAME $IMAGE_TAG_LATEST || true
after_script:
- docker logout $HARBOR_URL || true
only:
- main
- develop
tags:
- dockerRunner
# ============ Stage 4: K8s 配置更新(触发 ArgoCD 同步)===========
k8s-deploy:
stage: deploy
image: bitnami/kubectl:1.29
before_script:
# 配置 kubectl 访问 K8s 集群
- kubectl config set-cluster gitops --server=https://10.0.0.10:6443 --insecure-skip-tls-verify=true
- kubectl config set-credentials gitlab-ci --token=$K8S_DEPLOY_TOKEN
- kubectl config set-context gitops --cluster=gitops --user=gitlab-ci
- kubectl config use-context gitops
# 验证连接
- kubectl cluster-info
script:
# 更新 k8s 配置文件中的镜像版本(Kustomize 方式)
- cd k8s/overlays/${CI_COMMIT_REF_NAME}-env || cd k8s/overlays/dev
- |
# 替换镜像版本为新构建的 SHA
sed -i "s|image: .*|image: ${IMAGE_NAME}|" base/deployment.yaml
# 将 k8s 配置变更提交到 GitOps 仓库
- git config user.email "gitlab-ci@${CI_PROJECT_NAME}.gitlab"
- git config user.name "GitLab CI"
- git add .
- git diff --staged || true
- git commit -m "[CI] Update image to ${CI_COMMIT_SHORT_SHA} via pipeline" || echo "No changes to commit"
- git push https://gitlab-ci:${GITOPS_TOKEN}@${CI_REPOSITORY_URL#*://} HEAD:main || echo "Push skipped"
only:
- main
- develop
when: manual # 生产环境手动触发部署,避免自动部署风险
tags:
- k8sRunner
3.4 GitLab Runner 注册
Runner 是实际执行 CI/CD 任务的 Agent,注册一个专门用于 Docker 构建的 Runner:
# 在 GitLab 服务器上执行
gitlab-runner register \
--non-interactive \
--url "http://10.0.0.20" \
--registration-token "YOUR_REGISTRATION_TOKEN" \
--executor "docker" \
--docker-image "docker:24-dind" \
--docker-privileged \
--docker-volumes "/certs/client" \
--description "docker-builder-runner" \
--tag-list "dockerRunner" \
--locked="false"
🔒 安全提醒:Docker-in-Docker(dind)模式需要
--docker-privileged,这赋予容器privileged权限。生产环境建议使用 Kaniko 替代 dind,避免特权容器带来的安全风险:docker-build-kaniko: stage: package image: gcr.io/kaniko-project/executor:debug script: - echo "$HARBOR_PASSWORD" | kaniko --context $CI_PROJECT_DIR --dockerfile $CI_PROJECT_DIR/docker/Dockerfile --destination $IMAGE_NAME # 不需要 privileged 模式,更安全
四、ArgoCD GitOps 部署
4.1 ArgoCD 安装
ArgoCD 是声明式的 GitOps 持续交付工具,监听 Git 仓库中的 K8s 配置,自动将集群状态同步到 Git 定义的期望状态。
# 安装 ArgoCD(命名空间级别安装)
kubectl create namespace argocd
kubectl apply -n argocd -f https://raw.githubusercontent.com/argoproj/argo-cd/v2.10.2/manifests/install.yaml
# 安装 ArgoCD CLI
curl -sSL -o /usr/local/bin/argocd https://github.com/argoproj/argo-cd/releases/download/v2.10.2/argocd-linux-amd64
chmod +x /usr/local/bin/argocd
# 访问 ArgoCD Server(NodePort 暴露)
kubectl patch svc argocd-server -n argocd -p '{"spec":{"type":"NodePort"}}'
kubectl get svc argocd-server -n argocd
# 获取初始密码
argocd admin initial-password -n argocd
4.2 应用声明(Application)
ArgoCD 的核心是 Application CRD,它定义了"哪个 Git 仓库的哪个路径"映射到"哪个 K8s 集群的哪个命名空间":
# argocd-application-springboot.yaml
apiVersion: argoproj.io/v1alpha1
kind: Application
metadata:
name: spring-boot-app
namespace: argocd
finalizers:
- resources-finalizer.argocd.argoproj.io
spec:
project: default
source:
# GitOps 仓库地址
repoURL: https://gitlab.example.com/your-group/spring-boot-app.git
targetRevision: main
path: k8s/overlays/prod
# Kustomize 自动处理环境差异化
kustomize:
images:
# ArgoCD 会自动替换镜像版本(与 GitLab CI 中的 sed 等效)
- harbor.example.com/spring-boot-app/spring-boot-app=spring-boot-app:latest
destination:
server: https://kubernetes.default.svc
namespace: spring-boot-prod
syncPolicy:
automated:
# 自动同步(Push 触发)
selfHeal: true # 集群状态被手动修改时自动恢复
prune: true # 自动删除 Git 中已不存在的资源
syncOptions:
- CreateNamespace=true
- PrunePropagationPolicy=foreground
retry:
limit: 5
backoff:
duration: 5s
factor: 2
maxDuration: 3m
应用这个 Application:
kubectl apply -f argocd-application-springboot.yaml
argocd app get spring-boot-app # 查看应用同步状态
4.3 Kustomize 环境差异化配置
Kustomize 是 Kubernetes 原生的配置管理工具,无需模板即可实现环境差异化:
# k8s/base/deployment.yaml(基础配置)
apiVersion: apps/v1
kind: Deployment
metadata:
name: spring-boot-app
spec:
replicas: 2
selector:
matchLabels:
app: spring-boot-app
template:
metadata:
labels:
app: spring-boot-app
spec:
containers:
- name: app
image: harbor.example.com/spring-boot-app/spring-boot-app:latest
ports:
- containerPort: 8080
env:
- name: JAVA_OPTS
value: "-Xms256m -Xmx512m"
livenessProbe:
httpGet:
path: /actuator/health/liveness
port: 8080
initialDelaySeconds: 60
periodSeconds: 10
readinessProbe:
httpGet:
path: /actuator/health/readiness
port: 8080
initialDelaySeconds: 30
periodSeconds: 5
resources:
requests:
cpu: 250m
memory: 256Mi
limits:
cpu: 1000m
memory: 512Mi
# k8s/overlays/prod/kustomization.yaml(生产环境)
apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
resources:
- ../../base/deployment.yaml
- ../../base/service.yaml
- ../../base/ingress.yaml
# 生产环境差异化配置
commonLabels:
env: prod
images:
- name: spring-boot-app
newName: harbor.example.com/spring-boot-app/spring-boot-app
newTag: latest # ArgoCD 自动更新此字段
patches:
# 副本数增加到 5
- patch: |-
- op: replace
path: /spec/replicas
value: 5
target:
kind: Deployment
# 生产环境更高内存限制
- patch: |-
- op: replace
path: /spec/template/spec/containers/0/resources/limits/memory
value: "1Gi"
target:
kind: Deployment
# 生产环境配置副本数上限(HorizontalPodAutoscaler)
- patch: |-
apiVersion: autoscaling/v2
kind: HorizontalPodAutoscaler
metadata:
name: spring-boot-app-hpa
spec:
maxReplicas: 10
minReplicas: 3
scaleTargetRef:
apiVersion: apps/v1
kind: Deployment
name: spring-boot-app
target:
kind: Deployment
开发环境和测试环境只需覆盖副本数、资源限制等即可:
# k8s/overlays/dev/kustomization.yaml
apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
resources:
- ../../base/deployment.yaml
- ../../base/service.yaml
commonLabels:
env: dev
images:
- name: spring-boot-app
newTag: dev-latest
patches:
- patch: |-
- op: replace
path: /spec/replicas
value: 1
target:
kind: Deployment
五、生产级安全加固
5.1 GitLab CI/CD 敏感信息管理
切勿将密码和密钥直接写入 .gitlab-ci.yml。使用 GitLab CI/CD Variables:
# GitLab Web UI: Settings → CI/CD → Variables
HARBOR_USERNAME = registry-user
HARBOR_PASSWORD = registry-password-xxx # Masked,输出时自动隐藏
K8S_DEPLOY_TOKEN = k8s-deploy-token-xxx
GITOPS_TOKEN = gitops-deploy-token-xxx
5.2 Kubernetes Secret 安全
所有密钥使用 Sealed Secrets 或 External Secrets 管理,禁止明文存储:
# external-secrets-pull-based.yaml(External Secrets Operator)
apiVersion: external-secrets.io/v1beta1
kind: ExternalSecret
metadata:
name: harbor-credentials
spec:
refreshInterval: 1h
secretStoreRef:
name: vault-backend
kind: ClusterSecretStore
target:
name: harbor-credentials # ArgoCD 创建的 Secret 名称
creationPolicy: Owner
data:
- secretKey: username
remoteRef:
key: production/harbor
property: username
- secretKey: password
remoteRef:
key: production/harbor
property: password
5.3 Pod 安全标准(PSS)
强制执行 Pod Security Standards:
# namespace.yaml
apiVersion: v1
kind: Namespace
metadata:
name: spring-boot-prod
labels:
# 强制执行 Restricted 策略(禁止 privileged 容器、root 用户等)
pod-security.kubernetes.io/enforce: restricted
pod-security.kubernetes.io/enforce-version: v1.29
pod-security.kubernetes.io/audit: restricted
pod-security.kubernetes.io/warn: restricted
5.4 网络策略
使用 Kubernetes NetworkPolicy 实现 Pod 级别的网络隔离:
# network-policy.yaml
apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
name: spring-boot-app-netpol
namespace: spring-boot-prod
spec:
podSelector:
matchLabels:
app: spring-boot-app
policyTypes:
- Ingress
- Egress
ingress:
# 仅允许来自 Ingress Controller 的流量
- from:
- namespaceSelector:
matchLabels:
name: ingress-nginx
ports:
- protocol: TCP
port: 8080
egress:
# 仅允许访问必要的外部服务
- to:
- namespaceSelector:
matchLabels:
name: redis
- namespaceSelector:
matchLabels:
name: mysql
- namespaceSelector:
matchLabels:
name: elasticsearch
ports:
- protocol: TCP
port: 6379
- protocol: TCP
port: 3306
- protocol: TCP
port: 9200
# 允许 DNS 解析
- to:
- namespaceSelector:
matchLabels:
kubernetes.io/name: kube-dns
ports:
- protocol: UDP
port: 53
六、完整 GitOps 流程演示
6.1 开发人员提交流程
# 1. 开发人员提交代码
git checkout -b feature/new-api
git add src/main/java/com/example/Service.java
git commit -m "feat: add new API endpoint"
git push origin feature/new-api
# 2. 创建 Merge Request,触发 CI 测试流水线
# GitLab 自动运行单元测试、集成测试
# 3. 合并到 main 分支
# GitLab CI/CD 自动执行:
# [build] → [test] → [package: docker build + trivy scan] → [deploy: git push k8s config]
# 4. ArgoCD 检测到 Git 仓库变更,自动同步到 K8s 集群
# Git 仓库变更 → ArgoCD 发现 diff → 自动 apply 或手动 sync
6.2 ArgoCD CLI 常用命令
# 查看所有应用
argocd app list
# 查看应用详情(同步状态、健康状态、资源列表)
argocd app get spring-boot-app
# 手动同步(当自动同步策略未触发时)
argocd app sync spring-boot-app
# 查看资源健康状态
argocd app resources spring-boot-app
# 回滚到指定版本
argocd app rollback spring-boot-app
# 手动触发镜像更新(无需修改 Git)
argocd app set spring-boot-app --kustomize-images harbor.example.com/spring-boot-app/spring-boot-app:v1.2.3
argocd app sync spring-boot-app
6.3 流水线执行日志分析
当流水线失败时,重点检查以下环节:
# 1. Maven 构建失败:检查 pom.xml 依赖和 Java 版本
# 典型错误:Spring Boot 3.x 需要 Java 17+,但 Runner 使用 Java 11
# 解决:指定 Docker 镜像为 maven:3.9-eclipse-temurin-21-alpine
# 2. Docker build 失败:检查 Dockerfile 路径和构建上下文
# 典型错误:COPY 指令找不到文件
# 解决:确认 docker build -f docker/Dockerfile .. 的上下文正确
# 3. Trivy 安全扫描失败:检查镜像是否包含已知高危漏洞
# 典型错误:扫描到 CRITICAL 漏洞(CVSS ≥ 9.0)
# 解决:更新基础镜像版本,或在 .gitlab-ci.yml 中添加 --ignore-unfixed
# 4. ArgoCD 同步失败:检查 RBAC 权限和 Kustomize 配置
# 典型错误:HPA 补丁格式不正确
# 解决:验证 Kustomize patches 语法
kubectl kustomize k8s/overlays/prod | kubectl apply --dry-run=server
七、监控与可观测性
7.1 ArgoCD 内置监控
ArgoCD 自动收集以下指标(通过 Prometheus 抓取):
# 关键指标
argocd_app_info # 应用基本信息
argocd_app_sync_status # 同步状态(Synced/OutOfSync)
argocd_app_health_status # 健康状态(Healthy/Degraded)
argocd_app_sync_total # 同步次数统计
argocd_app_sync_duration_seconds # 同步耗时
argocd_app_k8s_request_total # K8s API 请求量
Grafana Dashboard 导入 ID:14584(ArgoCD 官方 Dashboard)。
7.2 与 Spring Boot Actuator 集成
确保 Spring Boot 应用暴露 Actuator 端点,ArgoCD 和 Prometheus 即可监控应用状态:
# application-prod.yml
management:
endpoints:
web:
exposure:
include: health,info,metrics,prometheus
base-path: /actuator
endpoint:
health:
show-details: always
probes: true # K8s 存活/就绪探针依赖
metrics:
tags:
application: ${spring.application.name}
八、常见问题与排查
| 问题现象 | 排查思路 | 解决方案 |
|---|---|---|
| ArgoCD 始终处于 OutOfSync | 检查 Git 仓库可达性和 token 权限 | 验证 deploy token 的 read_repository 权限 |
| Docker build 缓存未命中 | 检查 COPY 指令顺序 | 将依赖文件(pom.xml)COPY 放在源码 COPY 之前 |
| Pod 启动失败(CrashLoopBackOff) | kubectl logs + kubectl describe pod | 检查镜像拉取、内存限制、JVM 参数 |
| Kustomize patches 不生效 | kubectl kustomize 本地验证 | 检查 patch 路径和 op 类型 |
| GitLab Runner 任务排队 | 检查 Runner 并发数配置 | 在 GitLab Settings → CI/CD → Runners 增加并发数 |
| Trivy 扫描阻断流水线 | 确认是否为已知 CVE | 更新基础镜像,或添加 --ignore-unfixed 忽略未修复漏洞 |
九、完整架构总结
┌──────────────────────────────────────────────────────────────────┐
│ GitLab (代码仓库 + CI/CD) │
│ 代码提交 → 自动触发流水线 → Maven构建 → Docker镜像构建 → Trivy扫描 │
│ ↓ push image │
│ Harbor 私有镜像仓库 │
│ (harbor.example.com) │
└──────────────────────────────────────────────────────────────────┘
↓
┌──────────────────────────────────────────────────────────────────┐
│ GitOps 仓库 (k8s 配置文件) │
│ k8s/overlays/dev | test | prod (Kustomize) │
│ 当 GitLab CI 更新镜像版本时,GitOps 仓库同步更新 │
└──────────────────────────────────────────────────────────────────┘
↓
┌──────────────────────────────────────────────────────────────────┐
│ ArgoCD (GitOps 引擎) │
│ 持续监听 GitOps 仓库 → 检测到 diff → 自动同步到 K8s 集群 │
│ 支持:自动同步、手动同步、回滚、健康检查、重试机制 │
└──────────────────────────────────────────────────────────────────┘
↓
┌──────────────────────────────────────────────────────────────────┐
│ Kubernetes 集群 │
│ ┌─────────────┐ ┌─────────────┐ ┌─────────────┐ │
│ │ dev NS │ │ test NS │ │ prod NS │ │
│ │ 1 replica │ │ 2 replicas │ │ 5 replicas│ │
│ │ 256Mi mem │ │ 512Mi mem │ │ 1Gi mem │ │
│ └─────────────┘ └─────────────┘ └─────────────┘ │
│ HPA 自动扩缩容 + NetworkPolicy 网络隔离 + PSS 安全策略 │
└──────────────────────────────────────────────────────────────────┘
↓
┌──────────────────────────────────────────────────────────────────┐
│ 监控层 (Prometheus + Grafana) │
│ 应用指标:Actuator/Prometheus | 基础设施:node-exporter │
│ GitOps 指标:ArgoCD 内置 | 日志:ELK Stack │
└──────────────────────────────────────────────────────────────────┘
🎯 核心价值:整个流水线中,开发人员只需关注代码提交,从镜像构建、安全扫描、配置管理到集群部署全部自动化完成,任何操作都有 Git 记录可追溯,环境一致性得到根本保障。
相关标签:Docker Kubernetes GitLab ArgoCD GitOps CI/CD Kustomize Harbor
前置文章:建议配合阅读《Kubernetes 实战:将 Spring Boot 3.x 微服务部署到 K8s 集群全攻略》
评论区