site logo

Marico's space

Homelab 自托管常见的 Docker Compose 安全问题(附自检清单)

服务器技术 2026-04-28 17:10:55 9

译者按:自托管虽爽,但安全责任也随之而来。本文整理了 8 个常见的 Docker Compose 安全错误,看看你踩过几个。

背景

自托管的好处很明显:数据更可控、避免厂商锁定、深入理解技术栈。但代价是——那些「无聊但重要」的事也得自己来:端口暴露、容器默认配置、密钥管理、备份、更新、反向代理、数据库安全。

很多 Homelab 一开始都是这么写的:

services:
  app:
    image: myapp:latest
    ports:
      - "8080:8080"
  db:
    image: postgres:latest
    ports:
      - "5432:5432"

能用,看起来也没问题。但一个能跑的 Docker Compose 文件,不等于一个安全的配置。

8 个常见安全错误

1. 直接暴露数据库端口

数据库通常不需要暴露到公网。把 PostgreSQL(5432)、MySQL(3306)、Redis(6379)、MongoDB(27017)直接暴露出去风险很大。

更安全的做法:完全不映射端口,只让同 Docker 网络内的其他容器访问。如果真的需要本地访问,绑定到 localhost 而不是所有接口:127.0.0.1:5432:5432

2. 运行特权容器

privileged: true 会给容器超出常规的系统权限。大多数服务其实不需要这个。在启用前,问自己:这真的必需吗?有没有更细粒度的 capability 方案?镜像可信吗?服务公开暴露吗?

3. 不假思索使用 network_mode: host

主机网络模式移除了 Docker 的网络隔离,增加了端口暴露的复杂性。使用前确认:服务真的需要吗?开了哪些端口?在反向代理后面吗?普通 Docker 网络不能满足需求吗?

4. 以 root 运行容器

很多镜像默认以 root 运行。如果可能,指定非 root 用户:user: "1000:1000"。虽然有些服务需要特殊配置,但如果可以,通常值得考虑。

5. 把密钥直接写在 docker-compose.yml

这很方便,也很容易忘记。硬编码的密钥可能出现在 Git 历史、共享代码、截图、公有仓库里。更好的方案:使用 .env 文件(注意不要提交)、Docker secrets、或者密钥管理服务。

6. 到处用 latest 标签

latest 不是版本号,是移动靶。对于数据库这类有状态服务尤其危险——更新是不可控的。固定版本号(postgres:16.2redis:7.2.4),让更新变成有意的操作。

7. 没有备份策略

有持久化卷就应该有备份。好的备份计划要回答:备份什么?存哪?多久一次?加密了吗?测试过恢复吗?谁知道怎么恢复?

记住:没测试过恢复的备份不是真正的备份。

8. 以为有反向代理就安全了

Traefik、Caddy、Nginx Proxy Manager 这些工具很有用,但也可能让暴露变得更难理解。关键问题不是「有没有反向代理」,而是「我是否清楚哪些服务可从哪访问、为什么可访问?」

自检清单

暴露 Homelab 服务前,快速检查:

  • 有数据库端口直接映射到主机吗?
  • 有管理面板暴露吗?
  • 有用 privileged: true 的容器吗?
  • 有用 network_mode: host 的服务吗?
  • 容器以 root 运行吗?
  • 密钥硬编码了?
  • 镜像固定版本了?
  • 持久化卷有备份吗?
  • 知道什么是公开、私有、内部的吗?

总结

自托管给了你控制权,但控制权意味着责任。这些检查不能替代完整的安全审计,但能帮你发现很多容易忽略的问题。

原文链接