Minimus registry 将于 10 月 22 日下线。对仍在 CI、Kubernetes 清单或基础镜像中引用 Minimus 镜像的团队而言,这不是一次可以延后的镜像整理,而是一次供应链依赖迁移:下线后,新的构建、部署扩容和灾难恢复都可能因拉取镜像失败而中断。
Docker 给出的替代方向是 Docker Hardened Images(DHI)。迁移的重点不只是把镜像地址替换掉,还要验证运行时兼容性、更新锁定的 digest,并把镜像来源重新纳入构建与发布流程。
先找出 Minimus 依赖在哪里
不要只搜索 Dockerfile。镜像引用通常散落在 Helm values、Kubernetes YAML、CI 配置、Compose 文件和部署脚本中。可以在仓库根目录执行下面的命令,先生成一份待迁移清单:
rg -n -i 'minimus|registry\.minimus' \
--glob 'Dockerfile*' \
--glob '*.yml' \
--glob '*.yaml' \
--glob 'compose*.yaml' \
--glob 'compose*.yml' \
--glob '.gitlab-ci.yml' \
--glob '.github/workflows/*.yml' \
.
搜索结果应按风险排序处理:
- 生产运行镜像:优先迁移,特别是 Deployment、Job、CronJob 和基础运行时镜像。
- 构建阶段镜像:确认编译器、包管理器和 CA 证书是否仍满足构建需求。
- 测试与开发镜像:虽然风险较低,但也应避免在下线日期后让 CI 因旧镜像失败。
- 按 digest 固定的引用:替换后必须重新记录新镜像 digest,不能沿用旧值。
此外,检查集群中当前实际运行的镜像,防止仓库配置已经落后于线上状态:
kubectl get pods -A \
-o jsonpath='{range .items[*]}{.metadata.namespace}{"\t"}{.metadata.name}{"\t"}{range .spec.containers[*]}{.image}{"\n"}{end}{end}' \
| rg -i 'minimus|registry\.minimus'
从“能拉下来”走到“能安全运行”
Docker Hardened Images 的价值在于为容器工作负载提供经过加固的镜像选择,但镜像替换仍需按应用行为验证。较小、较严格的运行时环境,往往会暴露过去被基础镜像掩盖的隐式依赖,例如 shell、时区数据、动态链接库、非 root 文件权限或证书链。
迁移时尤其要核对以下项目:
- 入口命令:应用是否依赖
/bin/sh、bash或镜像内的调试工具。 - 用户与文件权限:DHI 的默认用户、工作目录和可写目录是否符合应用预期。
- 运行库与证书:Java、Node.js、Python 或原生二进制程序需要的共享库、CA 证书和时区数据是否齐全。
- 平台架构:确认镜像支持实际使用的
linux/amd64、linux/arm64等平台。 - 漏洞与可追溯性流程:迁移后重新执行镜像扫描、SBOM 生成、签名验证和 digest 固定。
关键原则是:不要把“镜像构建成功”当作“迁移完成”。构建只能证明 Dockerfile 可执行;真正的验收应覆盖启动、健康检查、核心请求、日志输出和权限敏感操作。
可以这样改造 Kubernetes 工作负载
下面以一个常见的 Web 服务为例。镜像名称和 tag 仅用于演示,请根据 Docker Hardened Images 中为你的语言和运行时选择的实际镜像地址替换 IMAGE_REFERENCE。
apiVersion: apps/v1
kind: Deployment
metadata:
name: orders-api
spec:
replicas: 2
selector:
matchLabels:
app: orders-api
template:
metadata:
labels:
app: orders-api
spec:
containers:
- name: api
image: IMAGE_REFERENCE
imagePullPolicy: IfNotPresent
ports:
- containerPort: 8080
env:
- name: PORT
value: "8080"
securityContext:
allowPrivilegeEscalation: false
readOnlyRootFilesystem: true
runAsNonRoot: true
capabilities:
drop:
- ALL
volumeMounts:
- name: tmp
mountPath: /tmp
readinessProbe:
httpGet:
path: /healthz
port: 8080
initialDelaySeconds: 3
periodSeconds: 5
volumes:
- name: tmp
emptyDir: {}
这里的 readOnlyRootFilesystem: true 和非 root 运行并非迁移必选项,但很适合作为兼容性检查。若应用因此启动失败,不应立刻取消安全限制;应先确认它究竟需要写入哪些路径,再通过 emptyDir 或持久卷显式挂载所需目录。
部署前可在本地或 CI 中完成最小验证。将 IMAGE_REFERENCE 换成实际 DHI 镜像后运行:
set -euo pipefail
IMAGE_REFERENCE='IMAGE_REFERENCE'
docker pull "$IMAGE_REFERENCE"
docker inspect "$IMAGE_REFERENCE" --format '{{.Id}}'
docker run --rm --read-only --tmpfs /tmp "$IMAGE_REFERENCE"
最后一条命令是否适用取决于镜像的默认入口点。有些应用镜像需要端口、环境变量或应用参数才能启动;这时应把运行命令替换成项目真实的 smoke test,而不是为了通过命令而弱化验证。
把迁移当作一次受控发布
建议在 10 月 22 日之前完成两个阶段。第一阶段是建立完整清单,并在非生产环境替换所有 Minimus 引用;第二阶段是在生产环境采用灰度或分批发布,保留可回滚的应用版本,但不要把“回滚到 Minimus 镜像”作为下线后的恢复方案。
上线前检查可以保持简洁:
- 仓库、Helm chart 和 CI 配置中不再存在 Minimus 镜像地址。
- 新镜像已经在目标架构上拉取、构建并完成应用级 smoke test。
- 生产部署使用明确的 tag 或 digest,并已更新镜像扫描与审批记录。
- 应用在非 root、只读根文件系统等预期安全约束下的行为已被验证,或已有明确的例外说明。
- 团队知道 Docker 提供迁移支持,并在遇到镜像选择或兼容性问题时尽早使用该支持渠道。
这次迁移的真正交付物不是一组新的镜像 URL,而是一条在 Minimus 下线后仍能稳定构建、拉取、部署和审计的容器供应链。