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-quota ResourceQuota 余量内。
  • Name
    端口
    Description
    容器以 --metrics-bind-address=:8443 暴露 metrics,对应 Service argocd-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.namespaceargocdApplication 对象所在命名空间
watch.namespacesargocd监听 ImageUpdater CR 的命名空间(v1.x 移除了 CRD 的 spec.namespace,必须与 Application 同命名空间)
interval2m镜像仓库扫描间隔
log.levelinfo日志级别
git.user / git.emailargocd-image-updater / argocd-image-updater@yldm.tech写回 commit 的提交身份

registries.conf 定义了两个镜像仓库:GitHub Container Registryprefix: ghcr.io,凭据 pullsecret:argocd/ghcr-secret,用于列出私有 ghcr.io/yldm-tech/* 镜像的 tag)和 DNF Registryprefix: registry.dunaifen.games,经 Traefik TLS 匿名提供,列 tag 无需凭据,供 DNF 游戏服镜像使用)。

两份凭据均由 External Secrets 从 Vault 同步:

  • Name
    ghcr-secret
    Description
    externalsecret-ghcr.yaml,类型 kubernetes.io/dockerconfigjsonremoteRef.key: github-runner/github-token(property config)。带 read:packages scope,供 registries.conf 列 ghcr.io 镜像 tag,与 base/common-secrets 同源。
  • Name
    git-creds
    Description
    externalsecret-git-creds.yaml,键 sshPrivateKeyremoteRef.key: argocd/repo/golang-server(property sshPrivateKey)。对 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.gitbranch: mainwriteBackTarget: "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.Z git 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 总览

评论