用心打造
VPS知识分享网站

Docker容器反复重启怎么办?先看退出码和日志!

刚启动的Docker容器不断在 Up 和 Restarting 之间切换,最直观的做法是继续执行重启命令。但容器已经在被重启策略反复拉起,再手工重启只会让日志更乱,甚至覆盖最接近根因的启动信息。

这类问题应先确认主进程为什么退出。退出码、容器日志、OOM状态和实际启动参数通常能把范围迅速缩小,再决定修配置、补依赖还是调整资源。

容器重启

先确认是不是重启循环

查看所有容器及当前状态:

docker ps -a
docker inspect -f '{{.State.Status}} {{.State.ExitCode}} {{.State.OOMKilled}} {{.RestartCount}}' CONTAINER

CONTAINER 换成容器名或ID。RestartCount 持续增加,说明Docker正在按重启策略重新拉起;状态为 Exited 且次数不变,则可能没有设置自动重启。

先记录退出码、是否被OOM终止和重启次数。Restarting只是结果,退出码和日志才是排查入口。 不要在保存证据前反复删除并重建容器。

立即读取最近一次启动日志

可以带时间戳查看末尾日志:

docker logs --timestamps --tail 200 CONTAINER

配置语法错误、环境变量缺失、端口占用、数据库连接失败和文件权限问题,往往会在主进程退出前留下明确记录。日志完全为空时,要核对镜像入口命令是否真的启动了预期程序,以及程序是否把日志写进容器内文件而不是标准输出。

容器重启很快时,可先临时关闭自动重启策略,保留现场:

docker update --restart=no CONTAINER

这只是为了停止循环并观察,不是最终修复。问题解决后再恢复符合业务需求的策略。

退出码能告诉你什么

退出码0通常表示主进程正常结束。对一次性任务很正常,对需要持续运行的Web服务则说明启动脚本可能执行完就退出,或后台化方式让PID 1提前结束。

退出码126常见于命令存在但不可执行,127更接近命令找不到。137可能与SIGKILL有关,其中包括内存不足触发的终止,但不能只凭137断定OOM,应同时查看 .State.OOMKilled 和内核日志。

143通常与SIGTERM有关,可能来自正常停止、编排更新或健康管理流程。退出码只能提供方向,还要和容器日志、Docker事件及宿主机日志对齐。

检查启动命令、挂载和环境变量

先读取容器的实际配置,而不是只看手边那份旧Compose文件:

docker inspect CONTAINER
docker compose config

重点核对 Entrypoint、Cmd、环境变量、挂载路径、工作目录和用户身份。宿主机上的配置文件被改名、挂载成目录、权限不足,都会让应用启动即退出。

使用Compose时,docker compose config 可以展示变量替换后的合并配置。敏感环境变量不要直接复制到工单或公开日志中,只记录变量是否存在以及应用读取结果。

健康检查失败不一定会让普通容器重启

Dockerfile中的 HEALTHCHECK 用于判断容器内服务是否健康,状态可能变成 unhealthy。普通Docker容器仅仅健康检查失败,通常不会因为这个状态自动重启;是否重建还取决于外部编排或监控工具。

因此看到 unhealthy 后,应先读取健康检查输出:

docker inspect -f '{{json .State.Health}}' CONTAINER

检查命令可能依赖容器里不存在的 curl、错误的端口或过短的启动等待时间。不要为了让状态变绿就删除健康检查,应让检查目标与真实服务一致。

排查依赖服务和启动顺序

应用容器可能在数据库、Redis或消息队列准备前就启动。仅保证依赖容器先创建,不等于依赖服务已经可以接收连接。Compose环境可结合健康检查和依赖条件控制启动顺序,应用自身也应具备合理重试机制。

先从应用日志确认失败目标,再在同一Docker网络中测试名称解析和端口连通。不要把宿主机的 localhost 直接当成另一个容器地址,因为每个容器都有独立网络命名空间。

资源不足时再考虑扩容或迁移

.State.OOMKilled 为 true,内核日志也在相同时间记录内存终止,才有证据说明资源不足。先检查容器内存限制、宿主机可用内存和应用峰值,再决定优化参数或升级配置。

准备重建干净环境做对照时,可以在 萤光云 复现镜像、挂载和资源限制,也可以用按小时计费的 LightNode 跑一轮并行验证。新服务器规格更高但容器仍按相同配置立即退出,说明根因更可能在镜像或启动参数,而不是算力。

修复后怎么验收

恢复重启策略前先手工启动一次,确认主进程持续运行、日志不再重复同一报错。随后查看重启次数是否停止增长,并验证容器内服务、外部访问和依赖连接。

最后重启Docker服务或服务器,确认容器能按预期恢复。验收应同时满足状态稳定、重启次数不再增加、健康检查正常、业务请求成功,宿主机日志没有新的OOM记录。

常见问题

把restart设置为always能解决容器退出吗?

不能。它只会在容器停止后再次拉起,启动命令、配置或资源问题仍然存在,还可能形成更快的重启循环。

容器日志为空应该先做什么?

先检查实际Entrypoint和Cmd,确认主进程是否启动,以及日志是否输出到标准输出。随后检查挂载、权限和应用自己的日志目录。

退出码137一定是内存不足吗?

不一定。137表示进程收到SIGKILL,OOM只是可能原因之一。应结合容器的OOMKilled字段和宿主机内核日志确认。

赞(0)
未经允许不得转载;国外VPS测评网 » Docker容器反复重启怎么办?先看退出码和日志!
分享到