Docker 中的持久化存储(如数据库数据)该怎么管理?

用 Docker volume 管理持久数据:docker volume create 创建,docker run -v 卷名:/容器路径 挂载,复用卷可跨容器生命周期保留数据,但需避免误删并备份;有状态服务也可使用合适的绑定挂载,数据库打包备份需先正常停止所有写入者。

最佳实践
Docker 中的持久化存储(如数据库数据)该怎么管理?封面

标准做法:用命名卷(named volume)——docker volume create mydata 创建,docker run -v mydata:/var/lib/mysql 挂载到容器的数据目录。卷数据存在宿主机由 Docker 管理的目录里,复用持久卷时可跨容器生命周期保留数据,但仍受显式删除、宿主故障和升级兼容性影响;有状态数据应使用持久卷或合适的绑定挂载并备份。

基本用法

# 创建卷
docker volume create mysqldata

# 先在当前会话安全设置 MYSQL_ROOT_PASSWORD,再挂载使用
docker run -d --name mysql \
  -v mysqldata:/var/lib/mysql \
  -e MYSQL_ROOT_PASSWORD \
  mysql:8

# 查看与定位
docker volume ls
docker volume inspect mysqldata    # 看宿主机上的实际路径

不写 docker volume create 直接在 -v 名字:/路径 里用新名字,Docker 会自动创建命名卷。

三种挂载方式对比

方式 写法 适用
命名卷 -v mysqldata:/var/lib/mysql 数据库等应用数据,首选
绑定挂载 -v /host/dir:/container/dir 要直接看到/编辑宿主机文件(配置、代码热更)
tmpfs --tmpfs /run 临时数据,不持久化;可能进入 swap,敏感数据需额外控制

备份与迁移

用临时容器打包卷内容:

# 先正常停止所有写入者,再做冷备;确认数据库正常退出而非超时被强杀
docker stop mysql
docker run --rm -v mysqldata:/data:ro -v "$(pwd)":/backup \
  alpine tar -czf /backup/mysqldata.tar.gz -C /data .

# 恢复到一个全新的空卷,完成验证后再启用
# 先确认 mysqldata-restored 尚不存在,避免复用已有卷
docker volume create mysqldata-restored
docker run --rm -v mysqldata-restored:/data -v "$(pwd)":/backup:ro \
  alpine sh -c "cd /data && tar -xzf /backup/mysqldata.tar.gz"

数据库类数据建议用其自身工具备份(mysqldump/pg_dump),卷打包只适合停机冷备。

清理

docker volume ls -f dangling=true   # 看无主卷
docker volume prune                  # 当前默认清理未使用匿名卷;-a 才包括命名卷,按版本核对

常见问题(FAQ)

Q:容器删了卷还在吗?
A:通常保留,但 volume rm、prune、compose down -v 等可删除卷;匿名卷还受容器 --rm/-v 影响。卷位于 daemon 侧,Desktop 通常在虚拟机内,远程卷驱动则由对应存储负责。

Q:卷能挂给多个容器吗?
A:可以,多个容器共享同一卷;但数据库类应用多数不支持多实例同时写同一数据目录,共享前确认应用语义。

Q:compose 里怎么定义卷?
A:顶层 volumes: 声明,服务里 - 卷名:/路径 引用;compose 会自动加项目名前缀。

获取专属方案

联系我们

加入社区

微信扫码
加入官方交流群

立即体验

在线开通,按量计费,真正的云服务!

立即开始

选择观测云版本

代码托管平台