docs: tighten gitops ci release rules
This commit is contained in:
parent
4a959cafc2
commit
013e7bf47c
@ -143,14 +143,20 @@ Go 项目默认变量写在 `.gitlab-ci.yml` 的 `variables:`:
|
||||
|
||||
只在 `vX.Y.Z` tag 上触发发布链路。
|
||||
|
||||
### build-images job
|
||||
### image build jobs
|
||||
|
||||
输入:源码、Dockerfile、多组件构建上下文。
|
||||
输入:源码、Dockerfile、单组件构建上下文。
|
||||
|
||||
输出:推送到 `registry.baizhi.cloud/<app>/<component>:<version>` 的运行时镜像。
|
||||
输出:分别推送到 `registry.baizhi.cloud/<app>/<component>:<version>` 的运行时镜像。
|
||||
|
||||
设计原则:不同服务的镜像必须独立构建,避免一个组件改动或失败拖慢所有组件发布。
|
||||
|
||||
要求:
|
||||
|
||||
- 不要生成一个串行构建所有镜像的单体 `build-images` job;每个需要构建镜像的服务使用独立 job,例如 `build-backend-image`、`build-frontend-image`、`build-nginx-image`
|
||||
- 如果多个组件构建脚本完全一致,可以使用 `parallel:matrix`,但矩阵中的每个组件仍必须是 GitLab 可独立调度、独立失败、独立重试的构建单元
|
||||
- 每个镜像构建 job 只负责一个组件的 Dockerfile、构建上下文、tag 与 push
|
||||
- release 链路必须等待所有应用自建镜像构建成功;优先用 `needs:` 精确声明,而不是只依赖 stage 顺序
|
||||
- 登录 `registry.baizhi.cloud`
|
||||
- 优先使用 `docker buildx`
|
||||
- 只有检测到私有 Git 依赖时,才通过 `.netrc` 和 build secret 传入;否则不要生成 `.netrc` 相关步骤
|
||||
@ -169,6 +175,23 @@ Go 项目默认变量写在 `.gitlab-ci.yml` 的 `variables:`:
|
||||
- `--insecure-skip-tls-verify`
|
||||
- 不要假设 `.gitlab-ci.yml` 中的环境变量会自动进入 `docker build` / `docker buildx build`
|
||||
|
||||
### GitLab CI YAML 与脚本合法性
|
||||
|
||||
生成或修复 `.gitlab-ci.yml` 时要优先保证 GitLab CI 配置本身可解析、可执行、可维护。
|
||||
|
||||
要求:
|
||||
|
||||
- 不要在 CI 脚本里用 Python 临时解析或改写 YAML;优先使用 `yq`、`helm`、`git`、`install`、`mkdir`、`cp`、`rsync` 这类明确的 CLI
|
||||
- 修改 `Chart.yaml` 的 `version` / `appVersion` 使用 `yq -i`,不要用 Python heredoc 或内联脚本
|
||||
- 修改 Argo CD `Application` 的 `targetRevision` 使用 `yq -i` 定位字段,避免用脆弱的 `sed` 跨行替换
|
||||
- 对 CI 文件做合法性自检时,至少能用 `yq e '.' .gitlab-ci.yml` 验证 YAML 语法;如果环境有 GitLab CI lint 工具或 API,再补充 GitLab 语义校验
|
||||
- `.gitlab-ci.yml` 中的多行 shell 逻辑保持最小化;复杂到需要编程语言脚本时,优先把脚本提交到仓库中的可审查文件,而不是在 CI YAML 里塞内联程序
|
||||
|
||||
禁止:
|
||||
|
||||
- 在 `.gitlab-ci.yml` 中嵌入 `python - <<'PY'`、`python -c` 或临时 Python 脚本来改 YAML
|
||||
- 用字符串替换方式盲改 `application.yaml` 中所有 `targetRevision`
|
||||
|
||||
### package-chart job
|
||||
|
||||
输入:`deploy/helm/<app>/Chart.yaml`、`deploy/helm/<app>/values.yaml`、`deploy/helm/<app>/templates/*`
|
||||
@ -179,10 +202,11 @@ Go 项目默认变量写在 `.gitlab-ci.yml` 的 `variables:`:
|
||||
|
||||
- `helm registry login registry.baizhi.cloud`
|
||||
- 在临时目录复制 `deploy/helm/<app>/`
|
||||
- 把复制品中的 `version` 和 `appVersion` 改成 tag 版本
|
||||
- 用 `yq -i` 把复制品中的 `version` 和 `appVersion` 改成 tag 版本
|
||||
- 业务镜像的默认 tag 必须跟随 `appVersion`,不要依赖 release values 覆盖业务镜像 tag
|
||||
- `helm package`
|
||||
- `helm push`
|
||||
- 如果应用包含自建镜像,`package-chart` 必须通过 `needs:` 等待所有镜像构建 job 成功
|
||||
|
||||
### update-gitops-repo job
|
||||
|
||||
@ -195,6 +219,12 @@ Go 项目默认变量写在 `.gitlab-ci.yml` 的 `variables:`:
|
||||
- `releases/<app>/manifests/` 下的发布结果
|
||||
- `apps/<app>/application.yaml` 中当前应用 chart source 的 `targetRevision`
|
||||
|
||||
依赖关系:
|
||||
|
||||
- `update-gitops-repo` 必须显式依赖 `package-chart` 成功,优先写 `needs: ["package-chart"]`
|
||||
- 不要让 `update-gitops-repo` 和 `package-chart` 仅靠同 stage 顺序或隐式执行顺序关联
|
||||
- 如果 release stage 中还有其他准备 job,也必须保证 GitOps 仓库更新发生在 Chart 包成功推送之后
|
||||
|
||||
处理顺序固定为:
|
||||
|
||||
1. 克隆 `https://${GITEA_USER}:${GITEA_TOKEN}@deploy.baizhi.cloud/gitops-admin/argodeploy.git`
|
||||
@ -203,7 +233,7 @@ Go 项目默认变量写在 `.gitlab-ci.yml` 的 `variables:`:
|
||||
4. 保留已有的 `releases/<app>/manifests/kustomization.yaml` 与 `releases/<app>/manifests/db-secret.yaml`
|
||||
5. 将 `deploy/release/secret.yaml` 物化为 `releases/<app>/manifests/secret.yaml`
|
||||
6. 替换 `releases/<app>/metadata.yaml` 中的 `__VERSION__`;只有第三方镜像、非业务版本字段或明确需要的环境配置才允许替换 `releases/<app>/values.yaml` 中的 `__VERSION__`
|
||||
7. 更新 `apps/<app>/application.yaml` 中当前应用 chart source 的 `targetRevision`
|
||||
7. 用 `yq -i` 更新 `apps/<app>/application.yaml` 中当前应用 chart source 的 `targetRevision`,只改当前应用的 chart source
|
||||
8. 只有存在 diff 时才提交并推送 `main`
|
||||
|
||||
禁止:
|
||||
@ -211,6 +241,7 @@ Go 项目默认变量写在 `.gitlab-ci.yml` 的 `variables:`:
|
||||
- 在 CI 中调用 `kubectl`
|
||||
- 在 CI 中调用 `argocd app sync`
|
||||
- 把 hard refresh 当常规发布步骤
|
||||
- 在 Chart 包推送成功前更新 GitOps 仓库
|
||||
|
||||
## Helm Chart 规则
|
||||
|
||||
@ -238,6 +269,29 @@ Chart 必须反映应用的真实运行架构。
|
||||
- 不要依赖 Kubernetes 不支持的 `$(OTHER_ENV)` 展开
|
||||
- 对 Neo4j 这类镜像,不要注入不存在的 `NEO4J_*` 配置名,例如 `NEO4J_PASSWORD`
|
||||
|
||||
### Argo CD sync-wave
|
||||
|
||||
当 Chart 或 release manifests 中存在资源依赖顺序时,使用 Argo CD sync wave 明确表达顺序,避免依赖文件名、模板渲染顺序或 Kubernetes 最终一致性碰运气。
|
||||
|
||||
固定规则:
|
||||
|
||||
- annotation 键必须写成 `argocd.argoproj.io/sync-wave`,不要写成 `rgocd.argoproj.io/sync-wave` 或其他拼写
|
||||
- wave 值使用字符串,例如 `"-20"`、`"0"`、`"10"`
|
||||
- 低 wave 先同步,高 wave 后同步;不要把依赖方和被依赖方放在同一个 wave
|
||||
- 只有确实存在跨资源启动顺序要求时才加 sync-wave,不要给所有资源机械添加 annotation
|
||||
|
||||
推荐顺序:
|
||||
|
||||
- `-30`:ServiceAccount、RBAC、基础 Secret、基础 ConfigMap
|
||||
- `-20`:PVC / `volumeClaimTemplates` 所依赖的存储前置资源、应用私有 Secret、应用私有 ConfigMap
|
||||
- `-10`:应用自带的私有基础设施,例如 Neo4j、向量库、内部依赖服务的 StatefulSet / Deployment
|
||||
- `-5`:内部依赖的 Service,尤其是会被后续 nginx upstream 或应用启动配置引用的服务名
|
||||
- `0`:后端、worker、API 等核心业务 Deployment / StatefulSet
|
||||
- `5`:核心业务 Service
|
||||
- `10`:nginx / frontend 入口 Deployment,以及对外 `NodePort` Service
|
||||
|
||||
如果 nginx 配置在容器启动时解析 upstream,必须保证 upstream 对应 Service 的 wave 早于 nginx Deployment;如果应用启动依赖 Secret / ConfigMap / PVC,必须保证这些资源的 wave 早于消费它们的 workload。
|
||||
|
||||
如果应用依赖平台 shared 之外的私有服务,必须明确表达依赖来源:
|
||||
|
||||
- 要么由 Chart 生成应用自带资源
|
||||
@ -419,12 +473,17 @@ Chart 必须反映应用的真实运行架构。
|
||||
|
||||
- `git status --short`
|
||||
- `git diff --check`
|
||||
- `yq e '.' .gitlab-ci.yml`
|
||||
- `helm template`(前提是 Chart 与 values 已能渲染)
|
||||
|
||||
至少确认:
|
||||
|
||||
- 接入文件齐全
|
||||
- `.gitlab-ci.yml` 包含 test、镜像构建、Chart 发布、GitOps 同步
|
||||
- `.gitlab-ci.yml` YAML 语法合法,不包含用于改 YAML 的内联 Python
|
||||
- `.gitlab-ci.yml` 包含 test、组件级独立镜像构建、Chart 发布、GitOps 同步
|
||||
- 多服务应用的业务镜像不是由一个串行 `build-images` job 统一构建;每个自建镜像可被 GitLab 独立调度和重试
|
||||
- `package-chart` 通过 `needs:` 等待所有必要镜像构建成功
|
||||
- `update-gitops-repo` 通过 `needs:` 依赖 `package-chart` 成功
|
||||
- release values 指向 `registry.baizhi.cloud`
|
||||
- release values 不覆盖应用自建业务镜像 tag;业务镜像 tag 由 Chart `appVersion` 默认决定
|
||||
- 第三方镜像没有被错误改写到平台 registry
|
||||
@ -432,6 +491,7 @@ Chart 必须反映应用的真实运行架构。
|
||||
- 如果 Dockerfile 原本使用 Docker Hub 源,已切换到 `registry-mirrors.dev.in.chaitin.net`,且未误改其他非 Docker Hub 镜像源
|
||||
- 如果 Dockerfile 中使用 `apk`,已切换到中科大源
|
||||
- GitOps update job 指向 `https://deploy.baizhi.cloud/gitops-admin/argodeploy.git`
|
||||
- GitOps update job 用 `yq` 精确更新当前应用 chart source 的 `targetRevision`
|
||||
- CI 中没有直接调用 Argo
|
||||
- 只使用 `deploy.baizhi.cloud` 与 `registry.baizhi.cloud`
|
||||
- 没有使用不安全的 registry 访问方式
|
||||
@ -439,6 +499,7 @@ Chart 必须反映应用的真实运行架构。
|
||||
- 如果镜像内包含固定 upstream 配置,upstream service 名与 Chart 渲染结果一致
|
||||
- Neo4j 一类自带依赖的启动环境变量不依赖 `$(OTHER_ENV)` 展开
|
||||
- 如果应用包含需要持久化数据的服务,对应 PVC / `volumeClaimTemplates` 已显式设置 `storageClassName: longhorn`
|
||||
- 如果资源存在启动顺序依赖,`argocd.argoproj.io/sync-wave` 拼写正确,wave 顺序符合依赖方向
|
||||
- 如果检测到的私有 Git 依赖中包含 `git.in.chaitin.net/ai/baizhiyun/opensdk`,缺少必填百智云私有配置时交互停在当前项继续索取
|
||||
|
||||
## 最终输出
|
||||
@ -462,3 +523,7 @@ Chart 必须反映应用的真实运行架构。
|
||||
- 在未检测到私有 Git 依赖中的 `git.in.chaitin.net/ai/baizhiyun/opensdk` 时仍强行接入百智云
|
||||
- Dockerfile 明明使用了 Docker Hub / `apk` 默认源,却没有切到 `registry-mirrors.dev.in.chaitin.net` / 中科大源,或误改了原本不在 Docker Hub 的镜像源
|
||||
- 用户未提供必填值时伪造占位内容
|
||||
- 多个服务镜像塞进一个串行 build job,导致无法并行构建、无法单独重试、失败定位困难
|
||||
- `update-gitops-repo` 没有依赖 `package-chart`,GitOps 仓库先于 Chart 推送被更新
|
||||
- 在 `.gitlab-ci.yml` 中用 Python heredoc 临时改 `Chart.yaml`、release values 或 `application.yaml`
|
||||
- `argocd.argoproj.io/sync-wave` 拼错为 `rgocd.argoproj.io/sync-wave`,或把依赖方放在被依赖资源之前
|
||||
|
||||
Loading…
Reference in New Issue
Block a user