两套完整 docker-compose:测试环境 MySQL8 / 生产环境 MySQL8
区分核心差异:资源限制、日志策略、持久化、网络、备份、安全、性能参数
统一使用官方 mysql:8.0 镜像,可自行指定精确小版本如 mysql:8.0.40
一、测试环境 docker-compose.test.yml(本地开发/测试服务器)
特点
- 资源宽松,无严格限制,方便调试
- 对外直接映射端口,本地客户端可直连
- 数据持久化但支持一键清空
- 日志输出控制台,方便看SQL报错
- 简单弱密码,初始化测试库
- 不做高可用、不限制连接数
- 配置宽松,慢查询日志开启用于调试
目录结构
mysql-test/├── docker-compose.test.yml├── conf/│ └── my.cnf # 测试专用配置├── init/│ └── init.sql # 自动建库建表脚本└── data/ # 数据持久化目录└── .env # 环境配置文件
安装&.env
apt -y install docker-compose # 1.29.2-1# 当前29服务器的docker版本是Docker version 29.6.1, build 8900f1d新建 .env 文件,直接写原始密码不用转义:MYSQL_ROOT_PWD=xxxMYSQL_DATABASE=xxxMYSQL_USER=xxxMYSQL_USER_PWD=xxx
1. docker-compose.test.yml
version: "3.8"services:mysql-test:image: mysql:8.0.40env_file: .envcontainer_name: mysql8-test# 开机重启策略restart: unless-stopped# 端口映射 宿主机:容器ports:- "23309:3306"# 环境变量初始化environment:TZ: Asia/ShanghaiMYSQL_ROOT_PASSWORD: ${MYSQL_ROOT_PWD}MYSQL_DATABASE: ${MYSQL_DATABASE}MYSQL_USER: ${MYSQL_USER}MYSQL_PASSWORD: ${MYSQL_USER_PWD}# 挂载配置、初始化脚本、数据卷volumes:- ./conf/my.cnf:/etc/mysql/conf.d/my.cnf- ./init:/docker-entrypoint-initdb.d- ./data:/var/lib/mysql# 测试环境资源限制宽松deploy:resources:limits:cpus: "1.5"memory: 2G# 网络(简单桥接)networks:- test-netnetworks:test-net:driver: bridge
2. conf/my.cnf 测试配置
[mysqld]# 字符集character-set-server=utf8mb4collation-server=utf8mb4_unicode_ci# 时区default-time_zone = '+8:00'# 连接数(测试放大)max_connections = 500# 慢查询日志 调试用slow_query_log = ONslow_query_log_file = /var/lib/mysql/slow.loglong_query_time = 1# binlog 测试可关闭提升速度skip-log-bin# 缓冲池 1G内存分配300Minnodb_buffer_pool_size = 300Minnodb_log_file_size = 128M# 兼容客户端default_authentication_plugin=mysql_native_password[mysql]default-character-set=utf8mb4
3. init/init.sql 示例初始化
CREATE DATABASE IF NOT EXISTS test_db DEFAULT CHARACTER SET utf8mb4;USE test_db;CREATE TABLE IF NOT EXISTS demo(id INT PRIMARY KEY AUTO_INCREMENT,name VARCHAR(50) NOT NULL);GRANT ALL ON test_db.* TO 'test_user'@'%';FLUSH PRIVILEGES;
测试环境启停命令
# 启动docker-compose -f docker-compose.test.yml up -d# 停止旧容器docker-compose -f docker-compose.test.yml down# 重新后台启动docker-compose -f docker-compose.test.yml up -d# 查看日志docker-compose -f docker-compose.test.yml logs -f mysql-test# 销毁并清空所有数据(重置测试环境)docker-compose -f docker-compose.test.yml down -v如果之前启动过容器,./data 里面生成了 mysql 库文件,容器判定 “已初始化完成”,直接忽略 init 脚本。# 停止并删除数据卷/本地data目录docker-compose -f docker-compose.test.yml down -v# 删除本地data文件夹rm -rf ./data# 重新启动,这次会执行init.sqldocker-compose -f docker-compose.test.yml up -d
导入sql数据库数据
docker exec -it 0b90 bash
二、生产环境 docker-compose.prod.yml(线上正式服务)
生产关键改动点
- 不对外暴露端口,仅容器内网互通,禁止公网直连数据库
- 严格资源限制,防止MySQL吃光宿主机内存
- 开启binlog用于主从/备份,优化redo/undo日志
- 强密码、严格权限、关闭弱认证
- 日志持久化到文件,轮转策略
- 数据目录挂载宿主机高性能磁盘,权限管控
- 关闭调试日志,优化innodb性能参数
- 重启策略更严谨,增加健康检查自动自愈
- 网络隔离,仅内部服务网段访问
目录结构
mysql-prod/├── docker-compose.prod.yml├── conf/│ └── my.cnf├── logs/ # 生产日志单独挂载└── data/ # 独立高速磁盘挂载
1. docker-compose.prod.yml
version: "3.8"services:mysql-prod:image: mysql:8.0.40container_name: mysql8-prodrestart: always# 生产禁止端口映射到宿主机!只能内网容器访问# ports: 删掉,外部不能直连数据库# 健康检查,容器异常自动重启healthcheck:test: ["CMD", "mysqladmin", "ping", "-uroot", "-p${MYSQL_ROOT_PASSWORD}"]interval: 10stimeout: 5sretries: 3start_period: 30senvironment:TZ: Asia/Shanghai# 生产务必使用复杂密码,不要硬编码,可改用 .env 文件读取MYSQL_ROOT_PASSWORD: "Prod@Mysql#2026_Secret"MYSQL_DATABASE: business_dbMYSQL_USER: biz_userMYSQL_PASSWORD: "Biz@Pass#666_Strong"# 挂载:配置、数据、日志分离volumes:- ./conf/my.cnf:/etc/mysql/conf.d/my.cnf:ro # 只读挂载配置防止篡改- ./data:/var/lib/mysql- ./logs:/var/log/mysql# 严格资源限制,根据服务器内存调整deploy:resources:limits:cpus: "4"memory: 6Greservations:cpus: "2"memory: 4G# 专属生产内网networks:prod-internal-net:ipv4_address: 172.28.0.10 # 固定内网IP,业务服务固定地址连接networks:prod-internal-net:driver: bridgeipam:config:- subnet: 172.28.0.0/16
2. conf/my.cnf 生产高性能安全配置
[mysqld]# 基础字符集character-set-server=utf8mb4collation-server=utf8mb4_unicode_cidefault-time_zone = '+8:00'# 连接控制max_connections = 1000wait_timeout = 600interactive_timeout = 600# Binlog 开启,用于备份、主从同步log_bin = mysql-binbinlog_format = ROWexpire_logs_days = 7sync_binlog = 1# Innodb 生产核心调优(内存6G机器配置)innodb_buffer_pool_size = 4Ginnodb_log_file_size = 2Ginnodb_log_buffer_size = 64Minnodb_flush_log_at_trx_commit = 1innodb_file_per_table = ONinnodb_flush_method = O_DIRECT# 关闭调试慢日志,如需排查再临时开启slow_query_log = OFF# 安全:默认caching_sha2_password,禁用老旧native密码default_authentication_plugin=caching_sha2_password# 禁止本地文件导入导出,防安全漏洞secure-file-priv=/tmp# 表缓存table_open_cache = 2000[mysql]default-character-set=utf8mb4
生产启停命令
# 后台启动docker-compose -f docker-compose.prod.yml up -d# 实时查看运行日志docker-compose -f docker-compose.prod.yml logs -f mysql-prod# 平滑停止(保留数据卷,不会删库)docker-compose -f docker-compose.prod.yml down# 危险:销毁容器+清空所有数据,生产禁止随便执行# docker-compose -f docker-compose.prod.yml down -v
三、生产环境额外最佳实践
密码不要写死在yml 新建
.env文件存放密码,yml 中用${变量}引用,.env加入 .gitignore 禁止提交代码仓库# .envMYSQL_ROOT_PASSWORD=Prod@Mysql#2026_SecretMYSQL_PASSWORD=Biz@Pass#666_Strong
compose 中直接读取:
env_file: .env数据目录挂载独立SSD磁盘 不要存在系统盘,挂载
/data/mysql-prod到高速云盘/物理SSD定时备份脚本 容器内定时 mysqldump 导出到宿主机挂载目录,保留7天备份
网络访问控制 业务服务放在同一个
prod-internal-net网络,外部服务器不允许访问数据库容器IP定期镜像更新 每月拉取新版本mysql镜像重建容器,修复安全漏洞,数据卷保留不丢失
四、测试 vs 生产核心区别总结
| 项目 | 测试环境 | 生产环境 |
|---|---|---|
| 端口 | 3306映射宿主机,本地可直连 | 不暴露端口,仅容器内网访问 |
| 资源 | 限制宽松,内存1G | 严格预留+上限限制,匹配服务器配置 |
| Binlog | 默认关闭,提升测试速度 | 强制开启,用于备份/主从 |
| 日志 | 开启慢查询,输出控制台调试 | 关闭慢查询,日志落地文件 |
| 密码 | 简单弱密码 | 高强度复杂密码,建议.env管理 |
| 配置挂载 | 可读写 | 只读挂载:ro,防止篡改 |
| 销毁 | down -v 一键清空数据 | 禁止 -v,保留业务数据 |
| 网络 | 通用桥接 | 独立隔离内网,固定容器IP |
| 认证插件 | mysql_native_password兼容旧客户端 | 安全caching_sha2_password |
