argocd-image-updater · 镜像 tag 自动写回
argocd-image-updater 是这套 GitOps 流程里负责「发现新镜像版本并把它写回仓库」的控制器:它定期扫描各服务的镜像仓库,找到符合规则的更高语义化版本 tag,再以 git commit 的方式把新 tag 写进对应应用 kustomization 的 images: 块、推到 main,剩下的滚动部署交给 ArgoCD 完成。仓库里那些 build: automatic update of … 提交就是它产生的。
它在集群里干什么
控制器跑在 argocd 命名空间里,因为它需要直接读取同命名空间下的 ArgoCD Application 对象和 ImageUpdater CR,并复用 argocd 的 ssh-known-hosts ConfigMap 做 git 写回。每隔一段时间它对每个被纳管的应用做一次:扫描该应用镜像在仓库里的所有 tag → 按 allowTags 正则过滤出 X.Y.Z 形式的语义化版本 → 用 semver 策略挑出最高版本 → 若比当前更高,则把新 tag 通过 SSH push 写回 k8s-config 仓库对应 kustomization 的 images: 块。它本身不直接改集群里的 Deployment,而是改 git,由 ArgoCD 检出后再同步。
部署形态
- Name
- 命名空间
- Description
argocd(与 Application 和 ImageUpdater CR 同命名空间,便于直接读取与复用 git 凭据)。
- Name
- 工作负载类型
- Description
- Deployment
argocd-image-updater-controller,单副本(replicas: 1)。
- Name
- 镜像与版本
- Description
quay.io/argoprojlabs/argocd-image-updater:v1.2.1(vendored 上游 install 清单,钉在 v1.2.1)。
- Name
- 资源
- Description
- 经
patch-deployment-resources.yaml收紧为 requests 100m/256Mi、limits 250m/512Mi——单租户、只服务一小撮应用,无需上游默认的 250m/512Mi requests,以留在argocd-quotaResourceQuota 余量内。
- Name
- 端口
- Description
- 容器以
--metrics-bind-address=:8443暴露 metrics,对应 Serviceargocd-image-updater-controller-metrics-service的 8443/TCP。
- Name
- 安装清单
- Description
install.yaml为上游 v1.2.1 的完整 vendored 产物:CRD(ImageUpdater)+ RBAC + controller Deployment + config/secret + metrics Service + NetworkPolicy。
整个目录是一个 kustomize root,namespace: argocd,由 install.yaml、两个 ExternalSecret、以及 imageupdaters/ 下聚合的所有 CR 组成,再叠加两个 patch(config-patch.yaml 配置 ConfigMap、patch-deployment-resources.yaml 收紧资源)。
配置与依赖
控制器的行为由 ConfigMap argocd-image-updater-config(经 config-patch.yaml 注入)驱动,通过 env 引用各键:
| 配置键 | 值 | 含义 |
|---|---|---|
argocd.namespace | argocd | Application 对象所在命名空间 |
watch.namespaces | argocd | 监听 ImageUpdater CR 的命名空间(v1.x 移除了 CRD 的 spec.namespace,必须与 Application 同命名空间) |
interval | 2m | 镜像仓库扫描间隔 |
log.level | info | 日志级别 |
git.user / git.email | argocd-image-updater / argocd-image-updater@yldm.tech | 写回 commit 的提交身份 |
registries.conf 定义了两个镜像仓库:GitHub Container Registry(prefix: ghcr.io,凭据 pullsecret:argocd/ghcr-secret,用于列出私有 ghcr.io/yldm-tech/* 镜像的 tag)和 DNF Registry(prefix: registry.dunaifen.games,经 Traefik TLS 匿名提供,列 tag 无需凭据,供 DNF 游戏服镜像使用)。
两份凭据均由 External Secrets 从 Vault 同步:
- Name
- ghcr-secret
- Description
externalsecret-ghcr.yaml,类型kubernetes.io/dockerconfigjson,remoteRef.key: github-runner/github-token(propertyconfig)。带read:packagesscope,供registries.conf列 ghcr.io 镜像 tag,与base/common-secrets同源。
- Name
- git-creds
- Description
externalsecret-git-creds.yaml,键sshPrivateKey,remoteRef.key: argocd/repo/golang-server(propertysshPrivateKey)。对k8s-config有写权限的 SSH key,复用 ArgoCD repo 凭据用的同一把 Vault key(已确认可写),image-updater 用它把 tag bump push 回 main。
依赖链:External Secrets Operator + ClusterSecretStore vault-backend → Vault(取凭据),以及 ArgoCD 本体(读 Application、复用 ssh-known-hosts、由它消费写回的 commit)。
每个服务的 ImageUpdater CR
imageupdaters/ 下每个文件是一个 ImageUpdater CR,对应一个服务;在 imageupdaters/kustomization.yaml 里增删一个文件即可让某服务上/下线自动更新。所有 CR 结构一致:writeBackConfig.method: "git:secret:argocd/git-creds"(SSH 写回)、gitConfig.repository: git@github.com:yldm-tech/k8s-config.git、branch: main、writeBackTarget: "kustomization:/applications/<category>/<service>",更新策略统一为 updateStrategy: "semver"(无约束 = 追踪最高语义化版本),allowTags: "regexp:^[0-9]+\\.[0-9]+\\.[0-9]+$"(只认 X.Y.Z,跳过 latest/sha/任意 tag)。
每个 CR 都带两个 annotation:argocd.argoproj.io/sync-wave: "2"(在 CRD 于 wave 0 建立后再应用)和 argocd.argoproj.io/sync-options: SkipDryRunOnMissingResource=true(首次同步 CRD 尚不存在时跳过 dry-run,否则 ArgoCD 报 no matches for kind ImageUpdater)。
当前纳管的服务(kustomization.yaml 中启用项)包括 aidict、analytics、auth、commerce、creativestore、engagement、gateway、kamify、kubepocket、magicbox、management、media、myetc、notification、fluxa、scheduler、social、tg-support-bot、user,以及游戏服 dnf-server。boardserver/cardserver/pvpserver/rpgserver 已于 2026-06-12 随服务下线被注释停用。几个特例:
- Name
- fluxa
- Description
- 一个 alias
fluxa覆盖 server / worker / migrate 三者(它们共用ghcr.io/yldm-tech/fluxa镜像),写回applications/platform/fluxa。
- Name
- dnf-server
- Description
- 镜像为
registry.dunaifen.games/dnf(非 ghcr)。CI 的 image job 在vX.Y.Zgit tag 上推出registry.dunaifen.games/dnf:X.Y.Z,更新器写回applications/game/dnf-server;两套 DNF 服务共用此镜像,一条 entry 同时更新两者。
访问与监控
控制器无对外 Ingress。仅有一个 ClusterIP 类型的 metrics Service(argocd-image-updater-controller-metrics-service,8443/TCP)。安装清单自带一条 NetworkPolicy allow-metrics-traffic:仅放行来自带 metrics: enabled 标签的命名空间到 8443 端口的入站流量。本目录未声明 ServiceMonitor、PrometheusRule、HPA、VPA 或 PDB。
注意事项
argocd-image-updater 与 renovate 只负责换镜像 tag,而对自托管基础设施,一次版本号 bump 经常本身就是 breaking change:新 tag 往往还需要新的 CRD、probe、env、配置或数据迁移,光换 tag 会让组件 crash-loop。仓库历史上已被坑过四次——vault(非 root 镜像需 disable_mlock)、mongo(需 AVX + mongosh + 清空数据)、metallb(minor bump 需新 CRD + probe/env 改动)、meilisearch(引擎拒绝旧 on-disk DB 且不自动迁移)。这类包在 renovate.json 里带 dependencyDashboardApproval;接受 bump 时务必在同一个 PR里一起 port 对应的上游 manifest 改动(或迁移/清空数据),绝不能只合 tag。
infrastructure 总览