Compose 是能执行的说明书,它比截图、收藏夹和临时笔记更适合长期维护。
\n
我以前维护家庭服务,最怕遇到“当时怎么装的”这个问题。教程能告诉我别人怎么装,截图能提醒我某个面板怎么点,但真正属于我这台机器的运行事实,只有 Compose 文件能长期保留下来。端口、目录、变量、网络、镜像版本、重启策略,写清楚以后才谈得上恢复。
Compose 不是只用来启动容器的命令集合。对 HomeLab 来说,它更像一份能执行的说明书:人可以读,Docker 也可以读。文件写得清楚,半年后重建服务时就不需要凭记忆复原。
.env 负责差异,compose.yml 负责结构
我会把端口、时区、用户 ID、域名、路径前缀这类会因机器变化而调整的内容放进 .env,把服务之间的结构关系放在 compose.yml。这样迁移时只需要先改变量,再用 docker compose config 看最终配置。
APP_PORT=13000
APP_IMAGE=example/dashboard:1.8.4
DATA_ROOT=/srv/docker/dashboard
TZ=Asia/Shanghaiservices:
dashboard:
image: ${APP_IMAGE}
restart: unless-stopped
ports:
- "${APP_PORT}:3000"
environment:
- TZ=${TZ}
volumes:
- ${DATA_ROOT}/config:/config
- ${DATA_ROOT}/data:/data.env 不该变成垃圾抽屉。能写在 Compose 里且不会变的结构,就不要拆出去;确实会因环境不同而变化的值,再放进 .env。这样文件读起来不会到处跳,也不会把关键路径藏得太深。
先看展开后的配置
每次改完 Compose,我第一步都跑:
docker compose config它能把 .env 展开,暴露缩进错误、变量为空、网络引用不存在、字段写错等问题。很多“容器启动了但行为不对”的故障,根源其实在展开后的配置已经偏了。比如端口变量为空、路径多了一级目录、镜像标签没按预期替换,启动时未必马上报错,后面排查会很绕。
如果配置里有敏感变量,我不会把完整输出随手贴到公开笔记里,但会保存一份摘要:服务名、镜像版本、端口、卷、网络和健康检查。摘要能证明当时的运行结构,不需要暴露秘密。
镜像版本要有控制
HomeLab 里我尽量避免所有服务都写 latest。latest 省事,但它把升级时机交给镜像发布者;某天重建容器时,拉到的可能已经不是上次验证过的版本。对有状态服务,我更喜欢固定到明确版本,例如 postgres:16.3、redis:7.2、example/app:2.4.1。
不是说永远不升级,而是升级应该是一次有边界的动作:先看变更,再备份,再改版本,再启动,再观察。这样出问题时能把版本改回去,而不是连旧版本是什么都不知道。
面板改动必须回写
Portainer、NAS 面板和其他图形工具都很好用,尤其适合看状态、查日志、临时重启。但长期配置不能只停在面板里。凡是在面板里改过端口、变量、卷、网络,我都会回到 Compose 文件里同步一遍,然后重新执行 docker compose config。
如果配置源分裂,下一次重建最容易出事故:面板里运行的是 A,文件里记录的是 B,备份脚本按 C 的目录走。短期看只是一个小改动没回写,长期就是恢复时的隐患。
我的最小检查清单
一个服务上线前,我至少确认这些内容:
docker compose config
docker compose pull
docker compose up -d
docker compose ps
docker compose logs --tail=120 dashboard
docker inspect dashboard --format '{{json .Mounts}}'pull 让我知道镜像是否能拉到;ps 看健康状态;logs 看应用是否进入正常启动流程;inspect 看数据是否落在预期目录。Compose 文件不是越复杂越好,而是要让这些检查有据可依。只要说明书能执行、能验证、能回滚,家庭服务器就少了很多靠感觉维护的时刻。
此处评论已关闭