MySQL 部署与多实例配置完全指南

MySQL 部署与多实例配置完全指南

前言

在生产环境中,我们经常需要在一台物理服务器上同时运行多个 MySQL 实例。这种多实例部署方式能够充分利用服务器硬件资源,实现业务隔离、读写分离、主从复制等多种架构需求。本文将系统性地介绍 MySQL 的启动方式、多实例配置文件编写、初始化步骤以及生产环境部署的最佳实践,帮助运维工程师和 DBA 快速掌握 MySQL 多实例部署的全部要点。


一、MySQL 启动方式概述

在使用 systemd 的 Linux 发行版(如 CentOS 7/8、RHEL 7+)中,MySQL 支持三种主要的启动方式。理解它们的区别,有助于在多实例场景下选择最合适的管理方案。

1.1 mysqld_safe 方式

mysqld_safe 是传统的 MySQL 启动脚本,在 my.cnf 中通过 [mysqld_safe] 配置节指定日志和 PID 文件路径:

[mysqld_safe]
log-error = /var/log/mysqld.log
pid-file  = /var/run/mysqld/mysqld.pid

mysqld_safe 会在 mysqld 进程异常退出时自动重启它,且会将错误信息记录到错误日志中,是一种较为可靠的守护进程方式。但在多实例场景下,它不如另外两种方式灵活。

1.2 mysqld_multi 方式

mysqld_multi 是 MySQL 官方提供的多实例管理工具。在配置文件中通过 [mysqld_multi] 配置节定义全局参数,然后为每个实例单独定义配置节(如 [mysqld3306][mysqld3307]):

[mysqld_multi]
mysqld     = /usr/bin/mysqld_safe
mysqladmin = /usr/bin/mysqladmin
user       = multiadmin
pass       = password

[mysqld3306]
port       = 3306
socket     = /var/lib/mysql/mysql3306.sock
datadir    = /data/mysql/3306/data
# ... 其他参数 ...

启动与停止命令:

mysqld_multi start 3306
mysqld_multi stop 3306
mysqld_multi start 3307
mysqld_multi stop 3307

# 带日志输出启动
mysqld_multi --log=/var/log/mysqld3306.log start 3306

需要注意的是,mysqld_multi 依赖 multiadmin 用户来执行 SHUTDOWN 操作,需要在每个实例中创建该用户:

GRANT SHUTDOWN ON *.* TO 'multiadmin'@'localhost' IDENTIFIED BY 'password';

1.3 systemd 多实例模式(推荐)

自 MySQL 5.7 起,systemd 原生支持多实例管理。通过在 [mysqld@端口号] 配置节中使用 @ 后缀,systemd 可以自动识别不同实例。这是目前推荐的管理方式,因为它能够充分利用 systemd 的进程监控、自动重启和日志管理功能。

# 启动实例
systemctl start mysqld@3306
systemctl start mysqld@3307

# 停止实例
systemctl stop mysqld@3306

# 查看状态
systemctl status mysqld@3306

# 设置开机自启
systemctl enable mysqld@3306

二、systemd 服务文件配置

systemd 多实例模式的核心是一个模板化的 service 文件(/usr/lib/systemd/system/mysqld@.service),%I%i 会被替换为 @ 后面的端口号后缀:

[Unit]
Description=MySQL Server
Documentation=man:mysqld(8)
Documentation=http://dev.mysql.com/doc/refman/en/using-systemd.html
After=network.target
After=syslog.target

[Install]
WantedBy=multi-user.target

[Service]
User=mysql
Group=mysql
Type=forking
PIDFile=/var/run/mysqld/mysqld-%i.pid

# 禁用 systemd 对 mysqld 服务的启停超时逻辑
TimeoutSec=0

# 以 root 权限执行前置和后置脚本
PermissionsStartOnly=true

# 创建系统表所需的前置脚本
ExecStartPre=/usr/bin/mysqld_pre_systemd %I

# 启动主服务,--defaults-group-suffix=@%I 会匹配 my.cnf 中对应的 [mysqld@端口号] 配置节
ExecStart=/usr/sbin/mysqld --defaults-group-suffix=@%I --daemonize --pid-file=/var/run/mysqld/mysqld-%i.pid $MYSQLD_OPTS

# 环境变量文件
EnvironmentFile=-/etc/sysconfig/mysql

# 设置文件描述符限制
LimitNOFILE = 65535

Restart=on-failure
RestartPreventExitStatus=1
PrivateTmp=false

配置好 service 文件后,执行 systemctl daemon-reload 即可使用。


三、my.cnf 配置文件详解

多实例的 my.cnf 配置是整个部署的核心。每个实例通过 [mysqld@端口号] 标识,配置节内的所有参数仅对该实例生效。

3.1 实例基础配置

每个实例必须配置以下核心参数,且不同实例的参数必须各不相同以避免冲突:

[mysqld@3306]
port        = 3306
pid-file    = /var/run/mysqld/mysqld3306.pid
socket      = /var/lib/mysql/mysql3306.sock
datadir     = /data/serverdata/mysql/3306/data
log-bin     = /data/serverdata/mysql/3306/binlog/mysql-bin
log-error   = /var/log/mysql/mysqld3306.log
tmpdir      = /data/serverdata/mysql/3306/tmp
slow_query_log_file = /data/serverdata/mysql/3306/slowlog/slow.log

关键注意事项:

  • port:每个实例端口号必须唯一
  • pid-file:PID 文件路径必须唯一
  • socket:Socket 文件路径必须唯一,客户端登录时需通过 -S 参数指定
  • datadir:数据目录必须独立,不同实例不能共享
  • log-bin:Binlog 路径必须独立,且建议放置在独立的物理磁盘上以提高 I/O 性能
  • server_id:配置主从复制时必须唯一

3.2 字符集与 utf8mb4 配置

推荐使用 utf8mb4 作为默认字符集,它完整支持 emoji 表情和所有 Unicode 字符:

[mysqld@3306]
character-set-server  = utf8mb4
collation-server      = utf8mb4_unicode_ci
init_connect          = 'SET NAMES utf8mb4'
character-set-client-handshake = FALSE

[client]
default-character-set = utf8mb4

[mysql]
default-character-set = utf8mb4

配置说明:

参数说明
character-set-server设置服务端默认字符集为 utf8mb4
collation-server设置服务端排序规则,utf8mb4_unicode_ci 提供最准确的 Unicode 排序
init_connect普通用户连接时自动执行的语句,确保客户端连接使用 utf8mb4
character-set-client-handshake设为 FALSE 可忽略客户端字符集设置,统一使用服务端配置

3.3 通用运行参数

[mysqld@3306]
# DNS 与连接
skip-name-resolve                  # 禁用 DNS 解析,加快连接速度
skip-host-cache                    # 禁用主机名缓存
max_connections = 2000             # 最大连接数
wait_timeout = 3600                # 非交互连接超时时间(秒)
connect_timeout = 800              # 连接超时时间(秒)
max_connect_errors = 10            # 最大连接错误次数,防止暴力破解

# 数据包与缓冲
max_allowed_packet = 64M           # 服务端接受的最大数据包大小
bulk_insert_buffer_size = 8M       # 批量插入缓存(主要针对 MyISAM)
query_prealloc_size = 16384        # 语句解析持久性缓冲区
query_alloc_block_size = 16384     # 语句解析内存分配块大小

# 日志
slow_query_log                     # 开启慢查询日志
long_query_time = 0.1              # 慢查询阈值(秒)
expire_logs_days = 14              # binlog 保存天数
log_queries_not_using_indexes      # (可选)记录未使用索引的 SQL

# Binlog 配置
binlog-format = ROW                # binlog 格式,ROW 模式记录最完整的数据
binlog_rows_query_log_events = 1   # binlog 中记录原始 SQL 语句

# GTID 复制
enforce_gtid_consistency = on      # 强制 GTID 一致性
gtid-mode = on                     # 开启 GTID 模式
log-slave-updates = true           # 从库将复制事件写入 binlog(级联复制必备)

# 主从复制优化
server_id = 153306                 # 服务器唯一 ID
auto_increment_offset = 1          # 自增列起点(多主模式必备)
auto_increment_increment = 2       # 自增列步长(双主时设为 2,避免主键冲突)
slave-skip-errors = 1062           # 跳过主键重复错误
slave-parallel-type = LOGICAL_CLOCK
slave-parallel-workers = 16        # 并行复制线程数
master_info_repository = TABLE
relay_log_info_repository = TABLE

# 其他
explicit_defaults_for_timestamp    # 禁用 TIMESTAMP 列的自动更新行为
default_password_lifetime = 0      # 密码永不过期
lower_case_table_names = 0         # 表名区分大小写(Linux 下推荐 0)
symbolic-links = 0                 # 禁用数据库文件软链接
ft_min_word_len = 2                # 全文索引最小词长度(中文推荐设为 2)
event_scheduler = on               # 开启事件调度器
log_bin_trust_function_creators = on  # 信任函数创建者,允许创建存储函数

3.4 MyISAM 与缓存参数

# MyISAM 引擎
myisam_sort_buffer_size = 32M      # MyISAM 表排序缓冲
key_buffer_size = 1024M            # MyISAM 索引缓冲区

# 缓存与限制
tmp_table_size = 128M              # 内存临时表最大值,超过后写入磁盘
max_heap_table_size = 32M          # 内存表(MEMORY 引擎)最大大小
join_buffer_size = 64M             # JOIN 操作缓冲区
read_buffer_size = 2M              # 全表扫描缓冲区
sort_buffer_size = 2M              # 排序操作缓冲区
table_open_cache = 1800            # 表缓存数量
thread_cache_size = 384            # 线程缓存数量

# 查询缓存(MySQL 8.0 已移除此功能,以下仅适用于 MySQL 5.7 及以下)
query_cache_limit = 200M           # 单个查询缓存上限
query_cache_size = 512M            # 查询缓存总大小
query_cache_type = 1               # 查询缓存开关

3.5 InnoDB 引擎参数

InnoDB 参数直接决定数据库性能,是最关键的配置项:

# InnoDB 存储引擎
innodb_flush_method = O_DIRECT     # 数据文件刷写模式,绕过 OS 缓存直接写入磁盘
innodb_log_files_in_group = 2      # redo log 文件数量
innodb_log_file_size = 256M        # 单个 redo log 文件大小(总 redo log = 2 * 256M = 512M)
innodb_flush_log_at_trx_commit = 2 # 事务提交时日志刷写策略(0最快,1最安全,2折中)
innodb_file_per_table = 1          # 独立表空间模式
innodb_buffer_pool_size = 20G      # InnoDB 缓冲池大小(核心参数,建议设为物理内存的 50%-70%)
sql_mode = NO_ENGINE_SUBSTITUTION,STRICT_TRANS_TABLES

关于 innodb_buffer_pool_size:此参数非常关键,直接决定了 InnoDB 的性能。在多实例场景下,所有实例的 innodb_buffer_pool_size 之和不得超过服务器物理内存的 70%-80%,否则可能导致系统 OOM。


四、MySQL 安装

以下是基于 RPM 包的 MySQL 5.7 Community 版本安装步骤:

# 卸载系统自带的 MariaDB
rpm -qa | grep mariadb | xargs rpm -e --nodeps

# 安装 MySQL RPM 包(请根据实际版本调整包名)
rpm -ivh mysql-community-common-5.7.11-1.el7.x86_64.rpm
rpm -ivh mysql-community-libs-5.7.11-1.el7.x86_64.rpm
rpm -ivh mysql-community-libs-compat-5.7.11-1.el7.x86_64.rpm
rpm -ivh mysql-community-client-5.7.11-1.el7.x86_64.rpm
rpm -ivh mysql-community-server-5.7.11-1.el7.x86_64.rpm
rpm -ivh mysql-community-devel-5.7.11-1.el7.x86_64.rpm
注意:在生产环境中,建议通过官方 yum 仓库安装,以便及时获取安全更新。MySQL 8.0 的安装方式与此类似,仅包名中的版本号不同。

五、测试环境多实例部署

测试环境中通常部署较少实例数量(如 2 个),每个实例的 innodb_buffer_pool_size 可以适当调低(如 200M),以节省内存资源。以下是一个完整的双实例测试环境配置示例:

[mysqld@3306]
port        = 3306
pid-file    = /var/run/mysqld/mysqld3306.pid
socket      = /var/lib/mysql/mysql3306.sock
datadir     = /data/serverdata/mysql/3306/data
log-bin     = /data/serverdata/mysql/3306/binlog/mysql-bin
log-error   = /var/log/mysql/mysqld3306.log
tmpdir      = /data/serverdata/mysql/3306/tmp
slow_query_log_file = /data/serverdata/mysql/3306/slowlog/slow.log

skip-name-resolve
skip-host-cache
slow_query_log
lower_case_table_names = 0
explicit_defaults_for_timestamp
binlog-format = ROW
binlog_rows_query_log_events = 1
server_id = 153306
auto_increment_offset = 1
auto_increment_increment = 2
slave-skip-errors = 1062
log-slave-updates = true
event_scheduler = on
log_bin_trust_function_creators = on
enforce_gtid_consistency = on
gtid-mode = on
max_connections = 2000
wait_timeout = 3600
connect_timeout = 800
max_allowed_packet = 64M
max_connect_errors = 10
bulk_insert_buffer_size = 8M
query_prealloc_size = 16384
query_alloc_block_size = 16384
default_password_lifetime = 0
character-set-server = utf8mb4
collation-server = utf8mb4_unicode_ci
init_connect = 'SET NAMES utf8mb4'
character-set-client-handshake = FALSE
symbolic-links = 0
ft_min_word_len = 2
long_query_time = 0.1
expire_logs_days = 7
slave-parallel-type = LOGICAL_CLOCK
slave-parallel-workers = 16
master_info_repository = TABLE
relay_log_info_repository = TABLE

# MyISAM 参数
myisam_sort_buffer_size = 32M
key_buffer_size = 1024M

# 缓存与限制
tmp_table_size = 128M
max_heap_table_size = 32M
join_buffer_size = 64M
read_buffer_size = 2M
sort_buffer_size = 2M
table_open_cache = 1800
thread_cache_size = 384
query_cache_limit = 200M
query_cache_size = 512M
query_cache_type = 1
max_allowed_packet = 128M

# InnoDB
innodb_flush_method = O_DIRECT
innodb_log_files_in_group = 2
innodb_log_file_size = 256M
innodb_flush_log_at_trx_commit = 2
innodb_file_per_table = 1
innodb_buffer_pool_size = 200M
sql_mode = NO_ENGINE_SUBSTITUTION,STRICT_TRANS_TABLES

[mysqld@3307]
port        = 3307
pid-file    = /var/run/mysqld/mysqld3307.pid
socket      = /var/lib/mysql/mysql3307.sock
datadir     = /data/serverdata/mysql/3307/data
log-bin     = /data/serverdata/mysql/3307/binlog/mysql-bin
log-error   = /var/log/mysql/mysqld3307.log
tmpdir      = /data/serverdata/mysql/3307/tmp
slow_query_log_file = /data/serverdata/mysql/3307/slowlog/slow.log

skip-name-resolve
skip-host-cache
slow_query_log
lower_case_table_names = 0
explicit_defaults_for_timestamp
binlog-format = ROW
binlog_rows_query_log_events = 1
server_id = 153307
auto_increment_offset = 1
auto_increment_increment = 2
slave-skip-errors = 1062
log-slave-updates = true
event_scheduler = on
log_bin_trust_function_creators = on
enforce_gtid_consistency = on
gtid-mode = on
max_connections = 2000
wait_timeout = 3600
connect_timeout = 800
max_allowed_packet = 64M
max_connect_errors = 10
bulk_insert_buffer_size = 8M
query_prealloc_size = 16384
query_alloc_block_size = 16384
default_password_lifetime = 0
character-set-server = utf8mb4
collation-server = utf8mb4_unicode_ci
init_connect = 'SET NAMES utf8mb4'
character-set-client-handshake = FALSE
symbolic-links = 0
ft_min_word_len = 2
long_query_time = 0.1
expire_logs_days = 7
slave-parallel-type = LOGICAL_CLOCK
slave-parallel-workers = 16
master_info_repository = TABLE
relay_log_info_repository = TABLE

# MyISAM 参数
myisam_sort_buffer_size = 32M
key_buffer_size = 1024M

# 缓存与限制
tmp_table_size = 128M
max_heap_table_size = 32M
join_buffer_size = 64M
read_buffer_size = 2M
sort_buffer_size = 2M
table_open_cache = 1800
thread_cache_size = 384
query_cache_limit = 200M
query_cache_size = 512M
query_cache_type = 1
max_allowed_packet = 128M

# InnoDB
innodb_flush_method = O_DIRECT
innodb_log_files_in_group = 2
innodb_log_file_size = 256M
innodb_flush_log_at_trx_commit = 2
innodb_file_per_table = 1
innodb_buffer_pool_size = 200M
sql_mode = NO_ENGINE_SUBSTITUTION,STRICT_TRANS_TABLES

[mysqldump]
single-transaction
quick

六、生产环境多实例部署

6.1 多磁盘部署策略

在生产环境中,建议将不同实例的数据目录分散到不同的物理磁盘上,以提升 I/O 性能并避免磁盘 I/O 争用。典型的分配策略如下:

实例端口数据盘数据目录
3306/data/data/serverdata/mysql/3306/data
3307/data1/data1/serverdata/mysql/3307/data
3308/data2/data2/serverdata/mysql/3308/data
3309/data3/data3/serverdata/mysql/3309/data
3310/data/data/serverdata/mysql/3310/data
3311/data1/data1/serverdata/mysql/3311/data
3312/data2/data2/serverdata/mysql/3312/data
3313/data3/data3/serverdata/mysql/3313/data

多磁盘部署可以显著降低磁盘 I/O 等待时间,特别是对于 binlog 写入和数据文件读取场景。如果服务器配备 SSD,建议将 binlog 目录与数据目录放置在同一块高速磁盘上。

6.2 生产环境 innodb_buffer_pool_size 分配

生产环境的 innodb_buffer_pool_size 需根据每个实例的业务负载合理分配。以下是一个 128GB 物理内存服务器上 10 个实例的典型分配方案:

# 核心业务实例(大内存)
[mysqld@3306]
innodb_buffer_pool_size = 20G

# 一般业务实例
[mysqld@3307]
innodb_buffer_pool_size = 20G

[mysqld@3308]
innodb_buffer_pool_size = 20G

# 中等负载实例
[mysqld@3309]
innodb_buffer_pool_size = 20G

[mysqld@3310]
innodb_buffer_pool_size = 20G

# 轻负载实例
[mysqld@3311]
innodb_buffer_pool_size = 12G

[mysqld@3312]
innodb_buffer_pool_size = 20G

[mysqld@3313]
innodb_buffer_pool_size = 20G

[mysqld@3314]
innodb_buffer_pool_size = 8G

[mysqld@3315]
innodb_buffer_pool_size = 20G
关键原则:所有实例的 innodb_buffer_pool_size 总和不应超过服务器物理内存的 70%。以上示例总和约为 180GB,适用于 256GB 以上内存的服务器。

6.3 生产环境特殊配置

生产环境相比测试环境需要额外关注以下参数:

# 并行复制(提升从库回放速度)
slave-parallel-type = LOGICAL_CLOCK
slave-parallel-workers = 16
master_info_repository = TABLE
relay_log_info_repository = TABLE

# 复制过滤(仅复制指定数据库)
replicate-do-db = your_database_name

# 跳过错误类型(生产环境中可根据实际情况调整)
slave-skip-errors = 1062,1032

# 计划任务与触发器
event_scheduler = on
log_bin_trust_function_creators = on

关于 slave-skip-errors:该参数应谨慎使用。1062 是主键重复错误,1032 是记录不存在错误。在数据一致性要求极高的场景下,不建议跳过任何错误,而应当排查并修复根本原因。


七、多实例初始化

7.1 初始化前的目录准备

初始化前必须创建所有相关目录并赋予 mysql 用户权限:

# 创建各实例所需目录
mkdir -p /data/serverdata/mysql/3306/{data,binlog,tmp,slowlog}
mkdir -p /data/serverdata/mysql/3307/{data,binlog,tmp,slowlog}
mkdir -p /data1/serverdata/mysql/3307/{data,binlog,tmp,slowlog}
# ... 依此类推

# 赋予 mysql 用户权限
chown -R mysql:mysql /data/serverdata/mysql
chown -R mysql:mysql /data1/serverdata/mysql

7.2 MySQL 5.7 初始化

MySQL 5.7 使用 --initialize 参数进行数据目录初始化,初始化后会自动生成一个临时密码:

# 方式一:通过默认配置文件初始化(推荐)
/usr/sbin/mysqld --defaults-file=/etc/my.cnf --initialize --user=mysql

# 方式二:直接指定数据目录初始化
/usr/sbin/mysqld --datadir=/data/mysql/3308/data --initialize --user=mysql

7.3 MySQL 5.6 初始化

MySQL 5.6 使用 mysql_install_db 脚本进行初始化:

./mysql_install_db --user=mysql \
  --basedir=/usr/server/percona-server5.6.32 \
  --datadir=/data1/mysql/3307/data/

7.4 初始化后修改密码

如果忘记或丢失了初始化生成的临时密码,可以通过 skip-grant-tables 方式重置:

步骤 1:在 my.cnf 对应实例配置节中添加 skip-grant-tables

[mysqld@3307]
skip-grant-tables
# ... 其他配置 ...

步骤 2:重启实例并登录修改密码:

systemctl restart mysqld@3307
mysql -u root -S /var/lib/mysql/mysql3307.sock
-- MySQL 5.7+ 使用 authentication_string
UPDATE mysql.user SET authentication_string = PASSWORD('YourNewPassword') WHERE user = 'root';
FLUSH PRIVILEGES;

步骤 3:退出客户端,移除配置文件中的 skip-grant-tables,重启 MySQL 服务。然后再次登录并设置最终密码:

SET PASSWORD = PASSWORD('YourNewPassword');
FLUSH PRIVILEGES;

对于 MySQL 8.0,认证方式有所变化,建议将认证插件设为 mysql_native_password

ALTER USER 'root'@'localhost' IDENTIFIED WITH mysql_native_password BY 'YourNewPassword';
FLUSH PRIVILEGES;

八、MySQL 用户账号管理

8.1 创建业务账号

合理规划数据库账号是安全管理的基础。建议为每个业务模块创建独立的数据库用户,并遵循最小权限原则:

-- 创建 DBA 管理账号
GRANT ALL PRIVILEGES ON *.* TO 'dba_admin'@'%' IDENTIFIED BY 'secure_password' WITH GRANT OPTION;

-- 创建监控账号(只读必要权限)
GRANT SELECT, RELOAD, PROCESS, SHOW DATABASES, SUPER, REPLICATION CLIENT
  ON *.* TO 'mtop'@'%' IDENTIFIED BY 'monitor_password';

-- 创建备份账号
GRANT ALL PRIVILEGES ON *.* TO 'xtrabackup'@'localhost'
  IDENTIFIED BY 'backup_password' WITH GRANT OPTION;

-- 创建复制账号
GRANT REPLICATION SLAVE ON *.* TO 'repl'@'%'
  IDENTIFIED BY 'replication_password' WITH GRANT OPTION;

FLUSH PRIVILEGES;

8.2 业务数据库权限分配

按数据库粒度分配权限,实现不同业务间的隔离:

-- 业务 A 全权限用户
GRANT ALL ON database_a.* TO 'user_a'@'%' IDENTIFIED BY 'password_a' WITH GRANT OPTION;

-- 业务 A 只读用户
GRANT SELECT ON database_a.* TO 'user_a_readonly'@'%' IDENTIFIED BY 'password_a_ro';

-- 业务 B 全权限用户
GRANT ALL ON database_b.* TO 'user_b'@'%' IDENTIFIED BY 'password_b' WITH GRANT OPTION;

FLUSH PRIVILEGES;

8.3 修改密码

-- 修改指定用户的密码
ALTER USER 'username'@'host' IDENTIFIED BY 'new_password';
FLUSH PRIVILEGES;

九、登录与连接实例

多实例环境下,必须通过 Socket 文件区分不同实例。不能简单地使用 mysql -P3306 方式登录(该方式走 TCP 连接,在生产环境中可能受限):

# 正确方式:通过 Socket 文件连接
mysql -u root -p -S /var/lib/mysql/mysql3306.sock
mysql -u root -p -S /var/lib/mysql/mysql3307.sock

# 查看各实例 Socket 文件
ls -la /var/lib/mysql/mysql*.sock

十、日常运维与备份

10.1 实例启停

# systemd 方式(推荐)
systemctl start mysqld@3306
systemctl stop mysqld@3306
systemctl restart mysqld@3306
systemctl status mysqld@3306
systemctl enable mysqld@3306   # 设置开机自启

# 批量操作
for port in 3306 3307 3308 3309 3310; do
    systemctl restart mysqld@${port}
done

10.2 XtraBackup 备份

生产环境推荐使用 Percona XtraBackup 进行热备份:

# 全量备份
innobackupex --defaults-file=/etc/my.cnf \
  --user=xtrabackup --password=backup_password \
  --socket=/var/lib/mysql/mysql3306.sock \
  --parallel=8 --no-timestamp \
  /backup/mysql/3306/$(date +%Y-%m-%d_%H-%M)

# 指定数据库备份
innobackupex --defaults-file=/etc/my.cnf \
  --user=xtrabackup --password=backup_password \
  --socket=/var/lib/mysql/mysql3306.sock \
  --databases="db1 db2 db3" \
  --parallel=8 --no-timestamp \
  /backup/mysql/3306/$(date +%Y-%m-%d_%H-%M)

# 多库压缩备份
nohup innobackupex --defaults-file=/etc/my.cnf \
  --user=xtrabackup --password=backup_password \
  --socket=/var/lib/mysql/mysql3306.sock \
  --databases="db1 db2" \
  --parallel=8 --no-timestamp --stream=tar \
  /backup/tmp/ | gzip > /backup/mysql/backup.tar.gz &

# 应用日志使备份一致(准备阶段)
innobackupex --defaults-file=/etc/my.cnf \
  --user=root --use-memory=16G \
  --apply-log /backup/mysql/3306/2024-01-15_20-00/

# 恢复数据
innobackupex --defaults-file=/etc/my.cnf \
  --user=root --datadir=/data1/mysql/3306/data \
  --copy-back /backup/mysql/3306/2024-01-15_20-00/

10.3 主从复制搭建

多实例环境下配置 GTID 主从复制:

-- 在从库上执行
CHANGE MASTER TO
  MASTER_HOST = '10.60.143.37',
  MASTER_PORT = 3307,
  MASTER_USER = 'repl',
  MASTER_PASSWORD = 'replication_password',
  MASTER_AUTO_POSITION = 1;

START SLAVE;

-- 查看复制状态
SHOW SLAVE STATUS\G
注意:如果使用传统 binlog 位点同步方式,需执行 CHANGE MASTER TO MASTER_AUTO_POSITION = 0,否则 GTID 模式下会报错 ERROR 1776

十一、总结

MySQL 多实例部署是运维工程师的必备技能。本文从启动方式选型、systemd 服务配置、my.cnf 参数详解、初始化流程到生产环境部署策略,系统性地覆盖了多实例部署的各个环节。以下是一些核心要点回顾:

  1. 推荐使用 systemd 模式:比 mysqld_multi 更易维护,集成系统级进程管理和日志功能。
  2. 配置节命名规范:使用 [mysqld@端口号] 格式,与 systemd 模板服务文件中的 %I 变量匹配。
  3. 关键参数隔离portpid-filesocketdatadirlog-binserver_id 每个实例必须保持唯一。
  4. 内存规划:所有实例的 innodb_buffer_pool_size 总和不超过物理内存的 70%。
  5. 磁盘 I/O 优化:将不同实例的数据目录分散到不同物理磁盘上。
  6. 字符集统一:全链路使用 utf8mb4,确保 emoji 和特殊字符的正确存储与显示。
  7. 备份策略:使用 XtraBackup 进行热备份,生产环境务必配置定期备份任务。

通过本文提供的完整配置方案与操作步骤,你可以快速在生产环境中搭建起稳定可靠的 MySQL 多实例架构。

暂无评论