Podman Login 登录信息重启后失效的处理

rootless Podman 里跑 podman login,命令显示成功,但机器重启后再拉私有镜像,又像没登录过一样。这个现象不是 registry token 突然过期,通常是登录信息写到了临时目录。

问题现象

最常见的操作是这样:

podman login docker.io

当时能正常 podman pull。重启系统后,拉镜像或者启动依赖私有镜像的 Quadlet 服务时,又出现未登录、认证失败之类的问题。

可以用 --verbose 看 Podman 实际用了哪个认证文件:

podman login --verbose docker.io

如果输出里有类似这一行,就说明登录信息写在运行时目录里:

Used: /run/user/1000/containers/auth.json

原因

Podman 官方的 podman-login(1) 写得很明了:Linux 上 podman login 默认读写的认证文件是:

${XDG_RUNTIME_DIR}/containers/auth.json

rootless 用户常见就是:

/run/user/1000/containers/auth.json

/run 通常是临时文件系统,重启后会清空。Podman 文档里的示例也明确提到,默认凭据放在 $XDG_RUNTIME_DIR,它是 /run 下的目录,所以不会跨重启保留。

这就解释了为什么看起来像“登录过期”:不是登录流程失败,而是 auth.json 没了。

写入持久 authfile

把认证信息明确写到用户配置目录:

mkdir -p ~/.config/containers
podman login --authfile ~/.config/containers/auth.json docker.io
chmod 600 ~/.config/containers/auth.json

--authfilepodman login 的参数,用来指定认证文件路径。这里选 ~/.config/containers/auth.json,因为它在用户家目录下,即使系统重启也会保留。

如果你用的是其他 registry,把 docker.io 换成对应地址:

podman login --authfile ~/.config/containers/auth.json quay.io
podman login --authfile ~/.config/containers/auth.json ghcr.io
podman login --authfile ~/.config/containers/auth.json registry.example.com

验证一下:

podman login --authfile ~/.config/containers/auth.json --get-login docker.io

能打印用户名就说明这个文件里有对应 registry 的登录信息。

设置 REGISTRY_AUTH_FILE

只在 login 时加 --authfile 还不够。后续 Podman 操作,尤其是 pull/run 和 Quadlet 自动拉镜像时,也要让 Podman 知道默认去读这个持久文件。

Podman 支持用 REGISTRY_AUTH_FILE 覆盖默认认证文件路径:

export REGISTRY_AUTH_FILE="$HOME/.config/containers/auth.json"

当前 shell 里可以直接测试:

podman pull docker.io/library/alpine:latest

想让交互式 shell 长期生效,可以写进 ~/.profile~/.bashrc~/.zshrc,按你实际用的 shell 来。

export REGISTRY_AUTH_FILE="$HOME/.config/containers/auth.json"

如果镜像是由 rootless Quadlet / systemctl --user 服务拉取的,单纯写 shell rc 文件不一定会传给 systemd 用户管理器。可以直接在 Quadlet 文件里写 [Service] 环境变量,只影响这个容器服务:

[Service]
Environment=REGISTRY_AUTH_FILE=%h/.config/containers/auth.json

改完 Quadlet 后重新加载并重启服务:

systemctl --user daemon-reload
systemctl --user restart your-container.service