docker compose 部署 mysql 主从常见问题源于配置顺序与初始化时机不当:server-id 和 log-bin 必须配对且全局唯一;depends_on 不保证服务就绪,需配合 healthcheck 和 init 脚本;挂载路径、端口映射、复制命令(start replica)及权限配置均需严格校验。

docker compose up -d 一条命令就能跑起来,但主从连不通、数据不同步、容器反复重启——这些问题几乎都出在配置顺序和初始化时机上。
my.cnf 中 server-id 和 log-bin 必须配对出现
主库不启 log-bin,从库就拉不到日志;从库开了 log-bin 却没设 log_slave_updates=1,级联复制就会断掉。
-
server-id在整个集群里必须唯一,主库设1,从库至少是2或更大整数,不能重复也不能为0 - 主库必须启用
log-bin(如log-bin=mysql-bin),格式建议固定用ROW:binlog-format=ROW - 从库若要支持级联(比如再挂一个从库),必须加
log_slave_updates=1;否则它的 binlog 是空的 -
read-only=1要写在从库配置里,但别加在主库——否则写操作直接被拒绝
docker-compose.yml 里 depends_on 不等于“已就绪”
depends_on 只控制容器启动顺序,不等待 MySQL 服务真正监听 3306 端口。主库还没初始化完,从库就开始连,必然报错 ERROR 2003 (HY000): Can't connect to MySQL server 或后续 CHANGE REPLICATION SOURCE TO 失败。
- 不要依赖
depends_on做主从初始化,它只管容器启停,不管 mysqld 是否 ready - 推荐方案:主库用
init.sql自动建复制用户,例如CREATE USER 'repl'@'%' IDENTIFIED BY 'repl123'; GRANT REPLICATION SLAVE ON *.* TO 'repl'@'%'; - 从库启动后,需手动执行
CHANGE REPLICATION SOURCE TO—— 这步无法靠 compose 自动完成,必须进容器执行 - 如果想自动化,得写 shell 脚本 +
healthcheck,检测mysqladmin ping -h mysql-master -u root -proot成功后再触发同步配置
挂载路径和配置文件位置容易写错
MySQL 容器读配置的默认路径是 /etc/mysql/conf.d/(Debian/Ubuntu 系)或 /etc/mysql/my.cnf(Alpine 系),镜像版本不同,路径可能不一致。
- 官方
mysql:8.0镜像认/etc/mysql/conf.d/下的.cnf文件,所以挂载要写成./master/my.cnf:/etc/mysql/conf.d/my.cnf - 别写成
/etc/mysql/my.cnf,否则会覆盖整个配置,导致字符集、时区等基础项丢失 - 数据卷名(如
master-data)必须在volumes:区块下显式声明,否则 compose 启动时报volume not found - 端口映射别冲突:主库映
"3306:3306",从库至少换一个宿主机端口,比如"3307:3306"
从库执行 START REPLICA 前必须确认状态
运行 START REPLICA 之后立刻查 SHOW REPLICA STATUS\G,重点看三行:
-
Replica_IO_Running: Yes—— 表示能连上主库并拉日志;如果为No,多半是网络不通、用户权限不对或主库log-bin没开 -
Replica_SQL_Running: Yes—— 表示本地回放正常;如果为No,常见原因是主从表结构不一致、从库写了数据破坏了只读约束、或遇到 DDL 冲突 -
Seconds_Behind_Master: 0(或稳定小数值)—— 表示基本同步;如果是NULL,说明 IO 或 SQL 线程挂了
最常被忽略的是:MySQL 8.0.23+ 已将命令从 START SLAVE 改为 START REPLICA,旧脚本不改会报错 Unknown command。











