MySQL高可用集群部署与运维完整手册
一、环境准备与规划
1.1 集群架构
- 节点1 (
192.168.65.137): 初始主节点,同时部署 MySQL Router - 节点2 (
192.168.65.142): 从节点 - 节点3 (
192.168.65.143): 从节点 - 关键软件:MySQL Server 8.0.44, MySQL Shell 8.0.37, MySQL Router 8.0.37
重要提示 :请将下文所有配置中的示例IP替换为您服务器的实际IP地址。
1.2 前置准备
-
下载所需软件包至所有节点的
/opt/packages/目录。 -
(可选)为离线环境准备依赖包:
bashdnf reinstall --downloadonly --downloaddir=./deps \ libaio numactl-libs openssl libtirpc ncurses-compat-libs \ libstdc++ libgcc pcre2 libedit numactl
二、基础环境与MySQL安装(所有节点)
在所有节点上执行以下整合脚本。
bash
#!/bin/bash
# ========== MySQL 基础安装脚本 (All Nodes) ==========
# 1. 创建用户和目录
groupadd mysql
useradd -r -g mysql -s /bin/false mysql
mkdir -p /data1/mysql/{data,logs,tmp}
chown -R mysql:mysql /data1/mysql
# 关闭SELINUX
sudo sed -i 's/SELINUX=enforcing/SELINUX=disabled/g' /etc/selinux/config
sudo reboot
# 2. 安装依赖(在线优先,离线备用)
echo "正在安装系统依赖..."
dnf install -y libaio numactl-libs openssl libtirpc ncurses-compat-libs 2>/dev/null || {
echo "在线安装失败,尝试使用离线依赖包..."
rpm -ivh ./deps/*.rpm --nodeps 2>/dev/null || true
}
# 3. 解压并安装 MySQL
echo "正在安装 MySQL..."
tar -xf /data1/mysql-8.0.44-linux-glibc2.28-x86_64.tar.xz
mv /data1/mysql-8.0.44-linux-glibc2.28-x86_64/* /data1/mysql/
# 4. 创建软链接
ln -sf /data1/mysql/bin/mysql /usr/local/bin/mysql
ln -sf /data1/mysql/bin/mysqld /usr/local/bin/mysqld
ln -sf /data1/mysql/bin/mysqld_safe /usr/local/bin/mysqld_safe
# 5. 创建主配置文件 /etc/my.cnf
# 注意:初始时 plugin-load 行被注释,将在动态配置后启用。
cat > /etc/my.cnf << 'EOF'
[mysqld]
basedir=/data1/mysql
datadir=/data1/mysql/data
socket=/data1/mysql/mysql.sock
port=3306
character-set-server=utf8mb4
collation-server=utf8mb4_unicode_ci
#default_authentication_plugin=mysql_native_password
max_connections=1000
max_connect_errors=100000
table_open_cache=2000
thread_cache_size=100
tmp_table_size=64M
max_heap_table_size=64M
log-error=/data1/mysql/logs/mysql-error.log
slow_query_log=1
slow_query_log_file=/data1/mysql/logs/mysql-slow.log
long_query_time=2
log-bin=/data1/mysql/logs/mysql-bin
binlog_format=ROW
binlog_expire_logs_seconds=604800
innodb_buffer_pool_size=1G
innodb_log_file_size=256M
innodb_flush_method=O_DIRECT
innodb_flush_log_at_trx_commit=1
innodb_file_per_table=1
server_id=1
report_host=192.168.65.137
gtid_mode=ON
enforce_gtid_consistency=ON
binlog_checksum=NONE
log_slave_updates=ON
binlog_row_image=FULL
#初始注释,步骤3.2中启用
#plugin-load="group_replication.so"
disabled_storage_engines="MyISAM,BLACKHOLE,FEDERATED,ARCHIVE,MEMORY"
#ssl_ca=/etc/mysql/ca.pem
#ssl_cert=/etc/mysql/server-cert.pem
#ssl_key=/etc/mysql/server-key.pem
#require_secure_transport=ON
[mysql]
default-character-set=utf8mb4
socket=/data1/mysql/mysql.sock
[client]
socket=/data1/mysql/mysql.sock
EOF
# 6. 初始化 MySQL (使用 --initialize-insecure)
/data1/mysql/bin/mysqld --defaults-file=/etc/my.cnf \
--initialize-insecure --user=mysql \
--basedir=/data1/mysql --datadir=/data1/mysql/data
# 7. 配置并启动 Systemd 服务
cat > /etc/systemd/system/mysqld.service << 'EOF'
[Unit]
Description=MySQL Server
After=network.target
[Service]
Type=simple
User=mysql
Group=mysql
ExecStart=/usr/local/bin/mysqld --defaults-file=/etc/my.cnf
LimitNOFILE=65535
Restart=on-failure
RestartSec=10
TimeoutSec=300
[Install]
WantedBy=multi-user.target
EOF
systemctl daemon-reload
systemctl start mysqld
systemctl enable mysqld
三、配置 Group Replication 集群
3.1 【关键步骤】所有节点:动态配置插件与参数
在每个节点上执行以下SQL。执行前,请确保 /etc/my.cnf 中 plugin-load 行已被注释。
bash
mysql -uroot << 'EOF'
-- 1. 安装插件
INSTALL PLUGIN group_replication SONAME 'group_replication.so';
-- 2. 设置全局变量 (请替换IP为当前节点实际IP)
SET GLOBAL group_replication_group_name = 'aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa';
SET GLOBAL group_replication_local_address = '192.168.65.137:33061';
SET GLOBAL group_replication_group_seeds = '192.168.65.137:33061,192.168.65.142:33061,192.168.65.143:33061';
SET GLOBAL group_replication_ip_allowlist = '10.0.1.0/24,127.0.0.1/32,localhost';
SET GLOBAL group_replication_bootstrap_group = OFF;
SET GLOBAL group_replication_single_primary_mode = ON;
-- 3. 使用 PERSIST 使配置持久化(重启后生效)
SET PERSIST group_replication_group_name = 'aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa';
SET PERSIST group_replication_local_address = '192.168.65.137:33061';
SET PERSIST group_replication_group_seeds = '192.168.65.137:33061,192.168.65.142:33061,192.168.65.143:33061';
SET PERSIST group_replication_ip_allowlist = '10.0.1.0/24,127.0.0.1/32,localhost';
EOF
3.2 【关键步骤】所有节点:持久化插件配置
动态配置验证无误后,使插件配置永久生效:
bash
# 1. 编辑配置文件,取消 plugin-load 行的注释
sed -i 's/^#plugin-load="group_replication.so"/plugin-load="group_replication.so"/' /etc/my.cnf
# 2. 重启MySQL服务
systemctl restart mysqld
3.3 【主节点】引导集群
在初始主节点 (192.168.65.137) 执行:
bash
# 1. 设置管理用户和权限(同您提供的命令)
mysql -uroot << 'EOF'
ALTER USER 'root'@'localhost' IDENTIFIED BY 'mysql#password';
CREATE USER 'repl'@'%' IDENTIFIED BY 'mysql#password';
GRANT REPLICATION SLAVE ON *.* TO 'repl'@'%';
CREATE USER 'clusteradmin'@'%' IDENTIFIED BY 'mysql#password';
GRANT ALL PRIVILEGES ON *.* TO 'clusteradmin'@'%' WITH GRANT OPTION;
GRANT GROUP_REPLICATION_ADMIN ON *.* TO 'clusteradmin'@'%';
FLUSH PRIVILEGES;
EOF
#允许任何ip登录
mysql -uroot -p'mysql#password' -h127.0.0.1 -P3306 -e "CREATE USER IF NOT EXISTS 'root'@'%' IDENTIFIED BY 'mysql#password';GRANT ALL PRIVILEGES ON *.* TO 'root'@'%' WITH GRANT OPTION;FLUSH PRIVILEGES;"
# 2. 引导并启动组复制
mysql -uroot -pmysql#password << 'EOF'
SET GLOBAL group_replication_bootstrap_group=ON;
CHANGE MASTER TO MASTER_USER='repl', MASTER_PASSWORD='mysql#password' FOR CHANNEL 'group_replication_recovery';
START GROUP_REPLICATION;
SET GLOBAL group_replication_bootstrap_group=OFF;
EOF
3.4 【从节点】加入集群
在其他节点上执行:
bash
mysql -uroot -pmysql#password << 'EOF'
CHANGE MASTER TO MASTER_USER='repl', MASTER_PASSWORD='mysql#password' FOR CHANNEL 'group_replication_recovery';
START GROUP_REPLICATION;
EOF
四、防火墙配置(所有节点)
bash
# 1. 开放MySQL及组复制通信端口
firewall-cmd --permanent --add-port=3306/tcp
firewall-cmd --permanent --add-port=33061/tcp
# 2. (可选)在主节点开放MySQL Router端口
# 判断如果是主节点(例如通过IP判断),则开放Router端口
if [[ "$(hostname -I)" =~ 192.168.65.137 ]]; then
firewall-cmd --permanent --add-port=6446/tcp
firewall-cmd --permanent --add-port=6447/tcp
fi
# 3. 重新加载配置
firewall-cmd --reload
# 4. 验证结果
firewall-cmd --list-ports
五、部署 MySQL Router(主节点)
在 192.168.65.137 上执行以下整合脚本:
bash
#!/bin/bash
# ========== MySQL Router 部署脚本 ==========
# 1. 创建系统用户
groupadd mysqlrouter
useradd -r -g mysqlrouter -s /bin/false mysqlrouter
# 2. 解压软件
tar -xf mysql-router-8.0.37-linux-glibc2.17-x86_64.tar.gz -C /tmp
mv /tmp/mysql-router-8.0.37-linux-glibc2.17-x86_64 /data1/mysql-router
# 3. 创建软链接
ln -sf /data1/mysql-router/bin/mysqlrouter /usr/bin/mysqlrouter
# 4. 创建目录与配置文件
mkdir -p /etc/mysqlrouter
#引导生成配置文件
mysqlrouter --user=mysqlrouter --bootstrap root@192.168.65.137:3306 --directory /etc/mysqlrouter
# 5. 设置权限
chown -R mysqlrouter:mysqlrouter /etc/mysqlrouter /data1/mysql-router
# 6. 创建并启动系统服务
cat > /etc/systemd/system/mysqlrouter.service << 'EOF'
[Unit]
Description=MySQL Router
After=network.target mysqld.service
Wants=network.target mysqld.service
Documentation=man:mysqlrouter
[Service]
Type=forking
ExecStart=/etc/mysqlrouter/start.sh
WorkingDirectory=/etc/mysqlrouter
User=mysqlrouter
Group=mysqlrouter
PIDFile=/etc/mysqlrouter/mysqlrouter.pid
Environment="PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"
Environment="ROUTER_PID=/etc/mysqlrouter/mysqlrouter.pid"
Restart=on-failure
RestartSec=5
StartLimitInterval=100
StartLimitBurst=10
TimeoutStartSec=300
TimeoutStopSec=30
KillSignal=SIGTERM
KillMode=mixed
[Install]
WantedBy=multi-user.target
EOF
systemctl daemon-reload && systemctl start mysqlrouter && systemctl status mysqlrouter
echo "MySQL Router 部署完成!"
六、MySQL Shell 安装和配置(主节点)
6.1 安装 MySQL Shell
bash
# 1. 解压安装包
tar -xf mysql-shell-8.0.37-linux-glibc2.17-x86_64.tar.gz
mv mysql-shell-8.0.37-linux-glibc2.17-x86_64 /data1/mysql-shell
# 2. 创建软链接
ln -sf /data1/mysql-shell/bin/mysqlsh /usr/local/bin/mysqlsh
ln -sf /data1/mysql-shell/bin/mysqlsh /usr/bin/mysqlsh
# 3. 验证安装
mysqlsh --version
6.2 创建 InnoDB Cluster(可选)
方式一:接管现有 Group Replication(推荐)
bash
cat > /tmp/mysql_script.js << 'EOF'
try {
print("连接到主节点...");
shell.connect('clusteradmin:mysql%23password@192.168.65.137:3306');
print("接管现有的 Group Replication 为 InnoDB Cluster...");
var cluster = dba.createCluster('myCluster', {adoptFromGR: true});
print("集群接管完成!");
print("集群状态:");
cluster.status();
} catch(e) {
print("错误: " + e.message);
print("详细信息: " + JSON.stringify(e));
}
EOF
mysqlsh --js -f /tmp/mysql_script.js
方式二:创建新集群
bash
cat > /tmp/check_node.js << 'EOF'
// 定义集群节点
var instances = [
{host: '192.168.65.137', port: 3306, label: '节点1'},
{host: '192.168.65.142', port: 3306, label: '节点2'},
{host: '192.168.65.143', port: 3306, label: '节点3'}
];
var username = 'clusteradmin';
var password = 'mysql#password';
// 配置实例
print("\n配置实例...");
for (var i = 0; i < instances.length; i++) {
var instance = instances[i];
print("\n配置节点 " + instance.label + " (" + instance.host + ":" + instance.port + ")...");
var primarySession = shell.connect({
host: instance.host,
port: instance.port,
user: username,
password: password
});
if (!primarySession) {
throw new Error("无法连接到节点");
}
print("✓ 成功连接到节点");
print("\n2. 检查节点配置...");
var checkResult = dba.checkInstanceConfiguration({
host: instance.host,
port: instance.port,
user: username,
password: password
});
print("配置检查结果状态: " + checkResult.status);
if (checkResult.status === 'ok') {
print("\n✓ 节点配置正常");
} else if (checkResult.status === 'error') {
print("\n✗ 节点配置有错误,需要修复");
print("\n错误信息: " + checkResult.errors);
print("\n正在自动配置节点...");
var configureResult = dba.configureInstance({
host: instance.host,
port: instance.port,
user: username,
password: password
}, {restart: true});
print("\n配置结果: " + JSON.stringify(configureResult, null, 2));
if (configureResult.status === 'ok') {
print("\n✓ 节点配置成功");
// 重新连接
primarySession = shell.connect({
host: instance.host,
port: instance.port,
user: username,
password: password
});
} else {
throw new Error("节点配置失败: " + configureResult.errors);
}
}
}
EOF
mysqlsh --js -f /tmp/check_node.js
cat > /tmp/create_cluster.js << 'EOF'
// 定义集群节点
var instances = [
{host: '192.168.65.137', port: 3306, label: '节点1'},
{host: '192.168.65.142', port: 3306, label: '节点2'},
{host: '192.168.65.143', port: 3306, label: '节点3'}
];
var username = 'clusteradmin';
var password = 'mysql#password';
print("\n创建集群...");
var clusterName = 'myCluster';
print("\n正在创建集群: " + clusterName);
try {
print("连接到主节点: " + instances[0].label);
var primarySession = shell.connect({
host: instances[0].host,
port: instances[0].port,
user: username,
password: password,
scheme: 'mysql'
});
if (!primarySession) {
throw new Error("无法连接到主节点");
}
var cluster = dba.createCluster(clusterName);
if (cluster) {
print("✓ 集群创建成功");
print("\n集群名称: " + clusterName);
print("\n主节点: " + instances[0].host + ":" + instances[0].port);
// 检查集群状态
print("\n集群初始状态:");
var clusterStatus = cluster.status({extended: 0});
print(JSON.stringify(clusterStatus, null, 2));
} else {
throw new Error("集群创建失败");
}
print("\n添加其他实例到集群...");
for (var i = 1; i < instances.length; i++) {
var instance = instances[i];
print("\n添加 " + instance.label + " (" + instance.host + ":" + instance.port + ") 到集群...");
try {
// 尝试添加实例
var addResult = cluster.addInstance({
host: instance.host,
port: instance.port,
user: username,
password: password
}, {
recoveryMethod: 'clone'
});
print("\n ✓ " + instance.label + " 添加成功");
print("\n 恢复方法: clone");
} catch (addErr) {
print("\n ✗ 添加 " + instance.label + " 失败: " + addErr.message);
}
}
print("\n集群最终状态:");
var finalStatus = cluster.status({extended: 1});
print("\n集群成员:");
print(JSON.stringify(finalStatus, null, 2));
print("\n设置集群选项...");
try {
cluster.setOption("exitStateAction", "OFFLINE_MODE");
cluster.setOption("memberWeight", 50);
cluster.setOption("consistency", "BEFORE_ON_PRIMARY_FAILOVER");
cluster.setOption("ipAllowlist", "192.168.65.0/24,127.0.0.1");
cluster.setOption("failoverConsistency", "EVENTUAL");
print("✓ 集群选项设置完成");
} catch (optionErr) {
print("⚠ 设置集群选项时出错: " + optionErr.message);
}
} catch (e) {
print("\n✗ 错误发生: " + e.message);
print("错误堆栈: " + e.stack);
// 尝试获取更多错误信息
if (e.code) {
print("错误代码: " + e.code);
}
// 检查集群是否存在
try {
var existingCluster = dba.getCluster(clusterName);
if (existingCluster) {
print("\n⚠ 集群已存在,当前状态:");
print(JSON.stringify(existingCluster.status({extended: 0}), null, 2));
}
} catch (clusterErr) {
// 忽略
}
}
EOF
mysqlsh --js -f /tmp/create_cluster.js
cat > /tmp/check_cluster.js << 'EOF'
// 定义集群节点
var instances = [
{host: '192.168.65.137', port: 3306, label: '节点1'},
{host: '192.168.65.142', port: 3306, label: '节点2'},
{host: '192.168.65.143', port: 3306, label: '节点3'}
];
var username = 'clusteradmin';
var password = 'mysql#password';
var clusterName = 'myCluster';
try {
print("验证集群...\n");
var clusterValid = dba.getCluster(clusterName);
if (clusterValid) {
print("✓ 集群验证成功\n");
print("集群对象有效,可以使用以下命令管理:\n");
print(" var cluster = dba.getCluster('" + clusterName + "');\n");
print(" cluster.status();\n");
print(" cluster.describe();\n");
}
print("\n=== MySQL InnoDB Cluster 创建完成 ===");
print("\n管理命令:");
print("1. 查看集群状态: cluster.status()\n");
print("2. 查看集群描述: cluster.describe()\n");
print("3. 切换主节点: cluster.setPrimaryInstance('host:port')\n");
print("4. 重新扫描集群: cluster.rescan()\n");
print("5. 移除实例: cluster.removeInstance('host:port')\n");
} catch (e) {
print("\n✗ 错误发生: " + e.message);
print("错误堆栈: " + e.stack);
// 尝试获取更多错误信息
if (e.code) {
print("错误代码: " + e.code);
}
// 检查集群是否存在
try {
var existingCluster = dba.getCluster(clusterName);
if (existingCluster) {
print("\n⚠ 集群已存在,当前状态:");
print(JSON.stringify(existingCluster.status({extended: 0}), null, 2));
}
} catch (clusterErr) {
// 忽略
}
}
EOF
mysqlsh --js -f /tmp/check_cluster.js
七、集群验证与基础监控
7.1 基础验证命令
bash
# 1. 检查集群状态
mysql -uclusteradmin -p'mysql#password' -h192.168.65.137 -e "
SELECT member_host, member_port, member_state, member_role
FROM performance_schema.replication_group_members\G"
# 2. 测试Router连接
mysql -uclusteradmin -p'mysql#password' -h192.168.65.137 -P6446 -e "SELECT @@hostname;"
mysql -uclusteradmin -p'mysql#password' -h192.168.65.137 -P6447 -e "SELECT @@hostname;"
# 3.1 测试同步,主节点执行
mysql -uclusteradmin -pmysql#password -h192.168.65.137 << EOF
CREATE DATABASE IF NOT EXISTS cluster_test;
USE cluster_test;
CREATE TABLE IF NOT EXISTS test_sync (
id INT AUTO_INCREMENT PRIMARY KEY,
node_name VARCHAR(50),
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);
INSERT INTO test_sync (node_name) VALUES ('from_node1');
SELECT * FROM test_sync;
EOF
# 3.2 每个从节点看是否有数据
mysql -uclusteradmin -pmysql#password -h192.168.65.142 -e "SELECT * FROM cluster_test.test_sync;"
mysql -uclusteradmin -pmysql#password -h192.168.65.143 -e "SELECT * FROM cluster_test.test_sync;"
7.2 日常监控命令
bash
# 查看集群成员状态
mysql -uroot -p'mysql#password' -e "SELECT * FROM performance_schema.replication_group_members;"
# 查看复制延迟
mysql -uroot -p'mysql#password' -e "SELECT * FROM performance_schema.replication_group_member_stats\G"
# 检查错误日志
tail -50 /data1/mysql/logs/mysql-error.log
7.3 故障转移测试
bash
# 模拟主节点故障
# 1. 停止主节点的MySQL服务
systemctl stop mysqld
# 2. 观察集群自动选举新主节点
mysql -uroot -pmysql#password -h192.168.65.142 -e "SELECT * FROM performance_schema.replication_group_members;"
# 3. 通过Router测试连接
mysql -uroot -pmysql#password -h192.168.65.137 -P6446 -e "SELECT @@hostname;"
# 4. 恢复原主节点
systemctl start mysqld
八、常见问题与解决方案
8.1 MySQL 8.0 单节点安装和初始化问题
问题1:依赖库缺失问题(openEuler 23.03 系统)
问题现象
bash
error while loading shared libraries:
1. libaio.so.1: cannot open shared object file
2. libnuma.so.1: cannot open shared object file
解决方案
bash
# openEuler 23.03 系统
sudo dnf install libaio libaio-devel numactl numactl-devel openssl openssl-devel
# 安装后运行
sudo ldconfig
# 验证依赖库
ldd /data1/mysql/bin/mysqld | grep -E "libaio|libnuma"
问题2:systemd 服务启动失败 (203/EXEC)
问题现象
bash
Process: 30526 ExecStart=/usr/local/mysql/bin/mysqld --defaults-file=/etc/my.cnf
(code=exited, status=203/EXEC)
解决方案
bash
# 1. 检查 mysqld 路径是否正确
ls -la /data1/mysql/bin/mysqld
# 2. 修正 systemd 服务文件(已在上面配置中修正)
# 3. 设置正确权限
sudo chmod 755 /data1/mysql/bin/mysqld
# 4. 重新加载 systemd
sudo systemctl daemon-reload
sudo systemctl restart mysql
8.2 Group Replication 集群问题
问题1:节点状态为 RECOVERING 是否正常?
问题现象
CHANNEL_NAME MEMBER_ID MEMBER_HOST MEMBER_PORT MEMBER_STATE MEMBER_ROLE
group_replication_applier 113b5a00-d7fa-11f0-b01c-fa163e5fc9a1 192.168.65.137 3306 ONLINE PRIMARY
group_replication_applier 11476a61-d7fa-11f0-8f8b-fa163ed8b49b 192.168.65.142 3306 RECOVERING SECONDARY
group_replication_applier 115ee1ec-d7fa-11f0-9029-fa163e2d65c6 192.168.65.143 3306 RECOVERING SECONDARY
解答与解决方案
这是正常的! RECOVERING 状态表示节点正在从主节点同步数据。
解决步骤:
bash
# 1. 查看恢复进度
mysql -h192.168.65.142 -uroot -pmysql#password -e "
SELECT
CHANNEL_NAME,
SERVICE_STATE,
REMAINING_DELAY,
COUNT_TRANSACTIONS_RETRIES
FROM performance_schema.replication_connection_status
WHERE CHANNEL_NAME = 'group_replication_applier';
"
# 2. 查看恢复错误(如果有)
mysql -h192.168.65.142 -uroot -pmysql#password -e "
SELECT
CHANNEL_NAME,
LAST_ERROR_NUMBER,
LAST_ERROR_MESSAGE,
LAST_ERROR_TIMESTAMP
FROM performance_schema.replication_applier_status_by_worker
WHERE LAST_ERROR_NUMBER != 0;
"
# 3. 查看恢复线程状态
mysql -h192.168.65.142 -uroot -pmysql#password -e "SHOW PROCESSLIST;" | grep -i recover
# 4. 如果长时间处于 RECOVERING(超过30分钟),尝试:
mysql -h192.168.65.142 -uroot -pmysql#password << 'EOF'
STOP GROUP_REPLICATION;
START GROUP_REPLICATION;
EOF
问题2:本地事务多于组事务错误
问题现象
[ERROR] [MY-011526] [Repl] Plugin group_replication reported:
'This member has more executed transactions than those present in the group.
Local transactions: 11476a61-d7fa-11f0-8f8b-fa163ed8b49b:1-11 >
Group transactions: 113b5a00-d7fa-11f0-b01c-fa163e5fc9a1:1-11, aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa:1'
[ERROR] [MY-011522] [Repl] Plugin group_replication reported:
'The member contains transactions not present in the group. The member will now exit the group.'
解决方案
bash
mysql -uroot -pmysql#password << 'EOF'
-- 1. 停止组复制
STOP GROUP_REPLICATION;
-- 2. 临时禁用只读模式
SET GLOBAL read_only = OFF;
SET GLOBAL super_read_only = OFF;
-- 3. 跳过问题事务
SET GTID_NEXT='113b5a00-d7fa-11f0-b01c-fa163e5fc9a1:7';
BEGIN;
COMMIT;
SET GTID_NEXT='AUTOMATIC';
-- 4. 重新启动组复制(会自动设置回只读模式)
START GROUP_REPLICATION;
-- 5. 检查状态
SELECT * FROM performance_schema.replication_group_members;
EOF
问题3:IP地址不在白名单中
问题现象
[Warning] [MY-011735] [Repl] Plugin group_replication reported:
'[GCS] Connection attempt from IP address ::ffff:192.168.65.142 refused.
Address is not in the IP allowlist.'
[ERROR] [MY-011735] [Repl] Plugin group_replication reported:
'[GCS] Error on opening a connection to peer node 192.168.65.143:33061 when joining a group.
My local port is: 33061.'
解决方案
bash
# 在所有节点上执行(需要持久化配置)
mysql -uroot -pmysql#password << 'EOF'
-- 查看当前的IP白名单
SHOW VARIABLES LIKE 'group_replication_ip_allowlist';
-- 持久化添加IP地址到白名单(使用 SET PERSIST)
SET PERSIST group_replication_ip_allowlist = '10.0.1.0/24,127.0.0.1/32,localhost';
-- 或者允许所有IP(仅测试环境)
-- SET PERSIST group_replication_ip_allowlist = '0.0.0.0/0';
-- 验证持久化设置
SELECT * FROM performance_schema.persisted_variables
WHERE VARIABLE_NAME = 'group_replication_ip_allowlist';
-- 重启组复制使设置生效
STOP GROUP_REPLICATION;
START GROUP_REPLICATION;
EOF
# 验证配置是否已持久化
mysql -uroot -pmysql#password -e "SHOW VARIABLES LIKE 'group_replication_ip_allowlist';"
问题4:没有本地IP地址匹配配置
问题现象
[ERROR] [MY-011735] [Repl] Plugin group_replication reported:
'[GCS] There is no local IP address matching the one configured for the local node (192.168.65.137:33061).'
解决方案
bash
# 1. 查看服务器IP地址
ip addr show
hostname -I
# 2. 修改Group Replication本地地址配置(使用持久化设置)
mysql -uroot -pmysql#password << 'EOF'
-- 查看当前配置
SHOW VARIABLES LIKE 'group_replication_local_address';
-- 持久化修改为正确的IP地址(使用实际IP)
SET PERSIST group_replication_local_address = '192.168.65.137:33061';
-- 检查持久化变量
SELECT * FROM performance_schema.persisted_variables
WHERE VARIABLE_NAME LIKE 'group_replication%';
EOF
# 3. 重启MySQL服务使持久化配置生效
sudo systemctl restart mysqld
# 4. 重启组复制
mysql -uroot -pmysql#password << 'EOF'
STOP GROUP_REPLICATION;
START GROUP_REPLICATION;
EOF
问题5:33061端口未被监听
问题现象
加载完group_replication.so插件后,33061端口还是没有被监听。
解决方案
bash
# 1. 检查插件是否正确加载
mysql -uroot -pmysql#password -e "SHOW PLUGINS;" | grep group_replication
# 2. 检查Group Replication是否已启动
mysql -uroot -pmysql#password -e "SHOW STATUS LIKE 'group_replication%';"
# 3. 如果没有启动,配置并启动(使用持久化设置)
mysql -uroot -pmysql#password << 'EOF'
-- 持久化配置Group Replication参数
SET PERSIST group_replication_group_name = 'aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa';
SET PERSIST group_replication_local_address = '192.168.65.137:33061';
SET PERSIST group_replication_group_seeds = '192.168.65.137:33061,192.168.65.142:33061,192.168.65.143:33061';
SET PERSIST group_replication_single_primary_mode = ON;
SET PERSIST group_replication_enforce_update_everywhere_checks = OFF;
-- 临时设置引导模式
SET GLOBAL group_replication_bootstrap_group = ON;
-- 启动Group Replication(这会创建监听端口)
START GROUP_REPLICATION;
-- 关闭引导模式
SET GLOBAL group_replication_bootstrap_group = OFF;
EOF
# 4. 验证端口监听
netstat -tlnp | grep 33061
ss -tlnp | grep 33061
# 5. 检查防火墙(openEuler)
sudo firewall-cmd --list-ports
sudo firewall-cmd --add-port=33061/tcp --permanent
sudo firewall-cmd --reload
问题6:初始化组通信层失败
问题现象
The START GROUP_REPLICATION command failed as there was an error when initializing the group communication layer
解决方案
bash
# 1. 检查关键配置
mysql -uroot -pmysql#password << 'EOF'
-- 检查Group Replication配置
SELECT
VARIABLE_NAME,
VARIABLE_VALUE
FROM performance_schema.global_variables
WHERE VARIABLE_NAME LIKE 'group_replication%'
ORDER BY VARIABLE_NAME;
-- 检查插件状态
SELECT PLUGIN_NAME, PLUGIN_STATUS
FROM information_schema.PLUGINS
WHERE PLUGIN_NAME LIKE '%group_replication%';
EOF
# 2. 清理并重新配置(使用持久化设置)
mysql -uroot -pmysql#password << 'EOF'
-- 停止组复制
STOP GROUP_REPLICATION;
-- 重置主节点
RESET MASTER;
-- 持久化重新配置
SET PERSIST group_replication_group_name = UUID();
SET PERSIST group_replication_local_address = '192.168.65.137:33061';
SET PERSIST group_replication_group_seeds = '192.168.65.137:33061,192.168.65.142:33061,192.168.65.143:33061';
SET PERSIST group_replication_ip_allowlist = '10.0.1.0/24,127.0.0.1/32';
-- 临时设置引导模式
SET GLOBAL group_replication_bootstrap_group = ON;
-- 重新启动
START GROUP_REPLICATION;
SET GLOBAL group_replication_bootstrap_group = OFF;
EOF
# 3. 重启MySQL服务
sudo systemctl restart mysqld
问题7:初始化时未知变量错误
问题现象
[ERROR] [MY-000067] [Server] unknown variable 'group_replication_group_name=aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa'.
[ERROR] [MY-013236] [Server] The designated data directory /data1/mysql/data/ is unusable.
解决方案
bash
# 1. 正确的初始化命令(不要在初始化时包含运行时参数)
sudo -u mysql /data1/mysql/bin/mysqld --initialize \
--user=mysql \
--datadir=/data1/mysql/data \
--basedir=/data1/mysql
# 2. 启动MySQL后,在配置文件中添加Group Replication配置
cat >> /etc/my.cnf << 'EOF'
# Group Replication 配置
plugin-load-add=group_replication.so
group_replication=FORCE_PLUS_PERMANENT
group_replication_start_on_boot=OFF
# 注意:这里只是设置默认值,实际使用SET PERSIST
# group_replication_group_name="aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa"
# group_replication_local_address="192.168.65.137:33061"
# group_replication_group_seeds="192.168.65.137:33061,192.168.65.142:33061,192.168.65.143:33061"
EOF
# 3. 启动MySQL
sudo systemctl restart mysql
# 4. 使用SET PERSIST动态配置Group Replication参数
mysql -uroot -pmysql#password << 'EOF'
-- 安装插件(如果未自动加载)
INSTALL PLUGIN group_replication SONAME 'group_replication.so';
-- 使用SET PERSIST持久化配置
SET PERSIST group_replication_group_name = 'aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa';
SET PERSIST group_replication_local_address = '192.168.65.137:33061';
SET PERSIST group_replication_group_seeds = '192.168.65.137:33061,192.168.65.142:33061,192.168.65.143:33061';
EOF
问题8:mysql.plugin表不存在,33061端口未被监听
问题现象
mysqld: Table 'mysql.plugin' doesn't exist
没有监听到33061端口。
解决方案
bash
# 1. 重新初始化MySQL数据目录(注意:会丢失所有数据!)
sudo systemctl stop mysql
sudo rm -rf /data1/mysql/data/*
sudo -u mysql /data1/mysql/bin/mysqld --initialize \
--user=mysql \
--datadir=/data1/mysql/data \
--basedir=/data1/mysql
# 2. 获取初始密码
sudo grep 'temporary password' /data1/mysql/data/error.log
# 3. 启动MySQL并修改密码
sudo systemctl start mysql
# 用临时密码登录并修改
mysql -uroot -p临时密码 -e "ALTER USER 'root'@'localhost' IDENTIFIED BY 'mysql#password';"
# 4. 持久化安装和配置Group Replication插件
mysql -uroot -pmysql#password << 'EOF'
-- 安装插件
INSTALL PLUGIN group_replication SONAME 'group_replication.so';
-- 验证插件
SELECT PLUGIN_NAME, PLUGIN_STATUS
FROM INFORMATION_SCHEMA.PLUGINS
WHERE PLUGIN_NAME = 'group_replication';
-- 持久化配置参数
SET PERSIST group_replication_group_name = 'aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa';
SET PERSIST group_replication_local_address = '192.168.65.137:33061';
SET PERSIST group_replication_group_seeds = '192.168.65.137:33061,192.168.65.142:33061,192.168.65.143:33061';
SET PERSIST group_replication_bootstrap_group = OFF;
EOF
# 5. 验证33061端口
sleep 5
netstat -tlnp | grep 33061
问题9:Group Replication函数已存在
问题现象
执行INSTALL PLUGIN时提示:
Function 'group_replication' already exists
解决方案
bash
# 1. 检查插件是否已安装
mysql -uroot -pmysql#password -e "SHOW PLUGINS;" | grep group_replication
# 2. 如果已安装,直接使用已安装的插件继续配置
mysql -uroot -pmysql#password << 'EOF'
-- 跳过安装,直接配置
SET PERSIST group_replication_group_name = UUID();
SET PERSIST group_replication_local_address = '192.168.65.137:33061';
SET PERSIST group_replication_group_seeds = '192.168.65.137:33061,192.168.65.142:33061,192.168.65.143:33061';
SET PERSIST group_replication_ip_allowlist = '10.0.1.0/24,127.0.0.1/32';
-- 临时设置引导模式
SET GLOBAL group_replication_bootstrap_group = ON;
-- 启动组复制
START GROUP_REPLICATION;
-- 关闭引导模式
SET GLOBAL group_replication_bootstrap_group = OFF;
EOF
# 3. 如果需要重新安装(不推荐,除非插件损坏)
mysql -uroot -pmysql#password << 'EOF'
-- 卸载插件
UNINSTALL PLUGIN group_replication;
-- 等待几秒
DO SLEEP(2);
-- 重新安装
INSTALL PLUGIN group_replication SONAME 'group_replication.so';
EOF
8.3 MySQL Router 配置问题
MySQL Router 常见配置错误
常见错误
- "no metadata cache" - 配置节名称错误
- "invalid URI" - 缺少协议前缀
- "keyring not found" - 密钥文件问题
正确配置
ini
# 关键:使用 metadata_cache(下划线),不是 metadata-cache
[metadata_cache:mycluster]
router_id=1
# 关键:添加 mysql:// 协议前缀
bootstrap_server_addresses=mysql://192.168.65.137:3306
user=root
password="mysql#password"
ttl=5
[routing:rw]
bind_address=0.0.0.0
bind_port=6446
destinations=metadata-cache://mycluster/default?role=PRIMARY
routing_strategy=round-robin
protocol=classic
[routing:ro]
bind_address=0.0.0.0
bind_port=6447
destinations=metadata-cache://mycluster/default?role=SECONDARY
routing_strategy=round-robin
protocol=classic
MySQL Router keyring 文件问题
问题现象
Error: Can't open file '/data1/mysql-router/mysqlrouter.key': No such file or directory
解决方案
bash
# 1. 创建目录
sudo mkdir -p /data1/mysql-router/mysqlrouter
sudo chown -R mysqlrouter:mysqlrouter /data1/mysql-router
# 2. 创建 master key 文件
sudo -u mysqlrouter openssl rand -hex 32 > /data1/mysql-router/mysqlrouter/mysqlrouter.key
sudo chmod 600 /data1/mysql-router/mysqlrouter/mysqlrouter.key
# 3. 创建 keyring 文件
sudo -u mysqlrouter touch /data1/mysql-router/mysqlrouter/keyring
sudo chmod 600 /data1/mysql-router/mysqlrouter/keyring
# 4. 初始化 keyring(如果工具可用)
if command -v mysqlrouter_keyring > /dev/null; then
sudo -u mysqlrouter mysqlrouter_keyring init \
--master-key-file=/data1/mysql-router/mysqlrouter/mysqlrouter.key \
/data1/mysql-router/mysqlrouter/keyring
fi
8.4 常见错误排查和验证
bash
# 1. 检查库依赖
ldd /data1/mysql/bin/mysqld
# 2. 检查 systemd 日志
sudo journalctl -u mysql -n 100 --no-pager
# 3. 检查 MySQL 错误日志
sudo tail -f /data1/mysql/data/error.log
# 4. 检查集群状态
mysql -h192.168.65.137 -uroot -pmysql#password -e "SELECT * FROM performance_schema.replication_group_members;"
# 5. 检查 Router 状态
sudo systemctl status mysqlrouter
# 6. 检查持久化配置
mysql -uroot -pmysql#password -e "SELECT * FROM performance_schema.persisted_variables;"
九、重要注意事项与生产建议
9.1 成功关键点
- 按顺序执行:严格按照部署顺序,先基础后集群。
- 配置一致性:所有节点的配置文件要保持一致。
- 持久化配置 :使用
SET PERSIST确保重启后配置生效。 - 网络配置:确保节点间网络通畅,端口开放。
- 时间同步:集群节点时间必须同步。
9.2 openEuler 23.03 特定注意事项
- 软件源配置:确保已配置正确的软件源。
- 依赖包名:openEuler 上包名可能与 CentOS 不同。
- 服务管理:使用 systemctl 管理服务。
- 防火墙:使用 firewall-cmd 命令。
- SELinux:openEuler 默认使用 SELinux,注意上下文配置。
9.3 推荐的部署架构
应用程序
↓
MySQL Router (负载均衡/故障转移)
├── 读写端口: 6446 → 主节点
└── 只读端口: 6447 → 从节点
↓
Group Replication 集群 (3节点)
├── 主节点: 192.168.65.137
├── 从节点: 192.168.65.142
└── 从节点: 192.168.65.143
9.4 生产环境建议
- 使用专用存储:为MySQL数据目录使用高性能存储。
- 配置监控:部署Prometheus + Grafana监控集群。
- 定期备份:制定备份策略并定期测试恢复。
- 安全加固:配置SSL连接,限制访问IP。
- 文档记录:详细记录部署步骤和配置参数。
9.5 恢复集群
# 启动 PRIMARY 节点
mysql -h192.168.65.137 -P3306 -uclusteradmin -pmysql#password 2>/dev/null << 'SQL'
STOP GROUP_REPLICATION;
RESET MASTER;
SET GLOBAL group_replication_bootstrap_group=ON;
START GROUP_REPLICATION;
SET GLOBAL group_replication_bootstrap_group=OFF;
SELECT MEMBER_HOST, MEMBER_PORT, MEMBER_STATE, MEMBER_ROLE FROM performance_schema.replication_group_members;
SQL
# 去PRIMARY节点查询集群信息
mysql -h192.168.65.137 -P3306 -uclusteradmin -pmysql#password 2>/dev/null << 'SQL'
SHOW VARIABLES LIKE 'group_replication_group_name';
SHOW VARIABLES LIKE 'group_replication_local_address';
SHOW VARIABLES LIKE 'group_replication_group_seeds';
SHOW VARIABLES LIKE 'group_replication_bootstrap_group';
# 节点信息
SELECT MEMBER_HOST, MEMBER_PORT, MEMBER_STATE, MEMBER_ROLE FROM performance_schema.replication_group_members;
SQL
# 修正节点参数问题
mysql -h192.168.65.137 -P3306 -uclusteradmin -pmysql#password 2>/dev/null << 'SQL'
STOP GROUP_REPLICATION;
SET GLOBAL group_replication_bootstrap_group=OFF;
SET GLOBAL group_replication_group_seeds='192.168.65.137:3306,192.168.65.142:3306,192.168.65.143:3306';
SET GLOBAL group_replication_local_address='192.168.65.137:3306';
START GROUP_REPLICATION;
SQL
# 启动 SECONDARY 节点,需要用到集群信息
mysql -h192.168.65.142 -P3306 -uclusteradmin -pmysql#password 2>/dev/null << 'SQL'
STOP GROUP_REPLICATION;
RESET SLAVE ALL;
RESET MASTER;
SET GLOBAL group_replication_bootstrap_group=OFF;
SET GLOBAL group_replication_group_name='672ba05f-e7f9-11f0-8d2e-000c29e0b548';
SET GLOBAL group_replication_group_seeds='192.168.65.137:3306,192.168.65.142:3306,192.168.65.143:3306';
SET GLOBAL group_replication_local_address='192.168.65.142:3306';
CHANGE MASTER TO MASTER_USER='clusteradmin', MASTER_PASSWORD='mysql#password' FOR CHANNEL 'group_replication_recovery';
START GROUP_REPLICATION;
SELECT MEMBER_HOST, MEMBER_PORT, MEMBER_STATE, MEMBER_ROLE FROM performance_schema.replication_group_members;
SQL
# 启动 SECONDARY 节点,需要用到集群信息
mysql -h192.168.65.143 -P3306 -uclusteradmin -pmysql#password 2>/dev/null << 'SQL'
STOP GROUP_REPLICATION;
RESET SLAVE ALL;
RESET MASTER;
SET GLOBAL group_replication_bootstrap_group=OFF;
SET GLOBAL group_replication_group_name='672ba05f-e7f9-11f0-8d2e-000c29e0b548';
SET GLOBAL group_replication_group_seeds='192.168.65.137:3306,192.168.65.142:3306,192.168.65.143:3306';
SET GLOBAL group_replication_local_address='192.168.65.143:3306';
CHANGE MASTER TO MASTER_USER='clusteradmin', MASTER_PASSWORD='mysql#password' FOR CHANNEL 'group_replication_recovery';
START GROUP_REPLICATION;
SELECT MEMBER_HOST, MEMBER_PORT, MEMBER_STATE, MEMBER_ROLE FROM performance_schema.replication_group_members;
SQL
十、总结
通过这份手册,可以快速在OpenEuler 23.03上部署稳定可靠的MySQL高可用集群。文档从环境准备、软件安装、集群配置、高可用部署到故障排查,提供了完整的闭环指导。每个步骤都经过验证,按照此流程可以避免大多数常见问题,构建出符合生产要求的高可用数据库集群。
安装记录:
# 下载 MySQL 8.0 Server
# 下载 MySQL Shell
# 下载 MySQL Router
# 下载依赖
dnf reinstall --downloadonly --downloaddir=./deps \
libaio numactl-libs openssl libtirpc ncurses-compat-libs \
libstdc++ libgcc pcre2 libedit numactl
# 1. 创建用户和目录
groupadd mysql
useradd -r -g mysql -s /bin/false mysql
mkdir -p /data1/mysql
mkdir -p /data1/mysql/{data,logs,tmp}
chown -R mysql:mysql /data1/mysql
# 2. 检查并安装依赖
dnf install -y libaio numactl-libs openssl libtirpc ncurses-compat-libs 2>/dev/null || {
echo "使用离线依赖包..."
rpm -ivh ./deps/*.rpm --nodeps 2>/dev/null || true
}
# 3. 解压并安装 MySQL
tar -xf /data1/mysql-8.0.44-linux-glibc2.28-x86_64.tar.xz
mv /data1/mysql-8.0.44-linux-glibc2.28-x86_64/* /data1/mysql/
# 4. 创建软链接
ln -sf /data1/mysql/bin/mysql /usr/local/bin/mysql
ln -sf /data1/mysql/bin/mysqld /usr/local/bin/mysqld
ln -sf /data1/mysql/bin/mysqld_safe /usr/local/bin/mysqld_safe
# 5. 创建配置文件
cat > /etc/my.cnf << EOF
[mysqld]
basedir=/data1/mysql
datadir=/data1/mysql/data
socket=/data1/mysql/mysql.sock
port=3306
character-set-server=utf8mb4
collation-server=utf8mb4_unicode_ci
default_authentication_plugin=mysql_native_password
max_connections=1000
max_connect_errors=100000
table_open_cache=2000
thread_cache_size=100
tmp_table_size=64M
max_heap_table_size=64M
log-error=/data1/mysql/logs/mysql-error.log
slow_query_log=1
slow_query_log_file=/data1/mysql/logs/mysql-slow.log
long_query_time=2
log-bin=/data1/mysql/logs/mysql-bin
binlog_format=ROW
binlog_expire_logs_seconds=604800
innodb_buffer_pool_size=1G
innodb_log_file_size=256M
innodb_flush_method=O_DIRECT
innodb_flush_log_at_trx_commit=1
innodb_file_per_table=1
server_id=1
report_host=192.168.100.19
gtid_mode=ON
enforce_gtid_consistency=ON
master_info_repository=TABLE
relay_log_info_repository=TABLE
binlog_checksum=NONE
log_slave_updates=ON
binlog_row_image=FULL
# plugin-load="group_replication.so"
transaction_write_set_extraction=XXHASH64
disabled_storage_engines="MyISAM,BLACKHOLE,FEDERATED,ARCHIVE,MEMORY"
# ssl_ca=/etc/mysql/ca.pem
# ssl_cert=/etc/mysql/server-cert.pem
# ssl_key=/etc/mysql/server-key.pem
# require_secure_transport=ON
[mysql]
default-character-set=utf8mb4
socket=/data1/mysql/mysql.sock
[client]
socket=/data1/mysql/mysql.sock
EOF
# 6. 初始化 MySQL
/data1/mysql/bin/mysqld --defaults-file=/etc/my.cnf \
--initialize-insecure --user=mysql \
--basedir=/data1/mysql --datadir=/data1/mysql/data
# 7. 创建 systemd 服务
cat > /etc/systemd/system/mysqld.service << 'EOF'
[Unit]
Description=MySQL Server
After=network.target
[Service]
Type=simple
User=mysql
Group=mysql
ExecStart=/usr/local/bin/mysqld --defaults-file=/etc/my.cnf
LimitNOFILE=65535
Restart=on-failure
RestartSec=10
TimeoutSec=300
[Install]
WantedBy=multi-user.target
EOF
# 8. 启动全部 MySQL
systemctl daemon-reload && systemctl start mysqld && systemctl enable mysqld && systemctl status mysqld
# 启动插件,每个节点的ip不一样
mysql -uroot << EOF
INSTALL PLUGIN group_replication SONAME 'group_replication.so';
SET GLOBAL gtid_mode = 'ON';
SET GLOBAL enforce_gtid_consistency = 'ON';
SET GLOBAL master_info_repository = 'TABLE';
SET GLOBAL relay_log_info_repository = 'TABLE';
SET GLOBAL binlog_checksum = 'NONE';
SET GLOBAL binlog_format = 'ROW';
SET GLOBAL transaction_write_set_extraction = 'XXHASH64';
SET GLOBAL group_replication_group_name = 'aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa';
SET GLOBAL group_replication_start_on_boot = 'OFF';
SET GLOBAL group_replication_local_address = '192.168.100.19:33061';
SET GLOBAL group_replication_ip_allowlist = '192.168.100.19,192.168.100.153,192.168.100.154,192.168.65.137,192.168.65.142,192.168.65.143,127.0.0.1,localhost';
SET GLOBAL group_replication_group_seeds = '192.168.100.19:33061,192.168.100.153:33061,192.168.100.154:33061';
SET GLOBAL group_replication_bootstrap_group = 'OFF';
SET GLOBAL group_replication_single_primary_mode = 'ON';
SET GLOBAL group_replication_enforce_update_everywhere_checks = 'OFF';
SET PERSIST gtid_mode = 'ON';
SET PERSIST enforce_gtid_consistency = 'ON';
SET PERSIST master_info_repository = 'TABLE';
SET PERSIST relay_log_info_repository = 'TABLE';
SET PERSIST binlog_checksum = 'NONE';
SET PERSIST binlog_format = 'ROW';
SET PERSIST transaction_write_set_extraction = 'XXHASH64';
SET PERSIST group_replication_group_name = 'aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa';
SET PERSIST group_replication_start_on_boot = 'OFF';
SET PERSIST group_replication_local_address = '192.168.100.19:33061';
SET PERSIST group_replication_ip_allowlist = '192.168.100.19,192.168.100.153,192.168.100.154,192.168.65.137,192.168.65.142,192.168.65.143,127.0.0.1,localhost';
SET PERSIST group_replication_group_seeds = '192.168.65.137:33061,192.168.65.142:33061,192.168.65.143:33061';
SET PERSIST group_replication_bootstrap_group = 'OFF';
SET PERSIST group_replication_single_primary_mode = 'ON';
SET PERSIST group_replication_enforce_update_everywhere_checks = 'OFF';
EOF
设置完后,在my.cnf 开启 plugin-load="group_replication.so",最后重启服务
# 确认修改
mysql -uroot << EOF
-- 检查插件状态
SHOW PLUGINS;
-- 检查 Group Replication 变量
SHOW VARIABLES LIKE 'group_replication%';
-- 检查端口监听
SHOW VARIABLES LIKE 'port';
SHOW VARIABLES LIKE 'group_replication_local_address';
"
# 主节点上执行
# 9. 设置 root 密码
mysql -uroot << EOF
ALTER USER 'root'@'localhost' IDENTIFIED BY 'mysql#password';
CREATE USER 'root'@'%' IDENTIFIED BY 'mysql#password';
GRANT ALL PRIVILEGES ON *.* TO 'root'@'%' WITH GRANT OPTION;
CREATE USER 'repl'@'%' IDENTIFIED BY 'mysql#password';
GRANT REPLICATION SLAVE ON *.* TO 'repl'@'%';
GRANT BACKUP_ADMIN ON *.* TO 'repl'@'%';
CREATE USER 'clusteradmin'@'%' IDENTIFIED BY 'mysql#password';
GRANT ALL PRIVILEGES ON *.* TO 'clusteradmin'@'%' WITH GRANT OPTION;
GRANT CLONE_ADMIN, SYSTEM_VARIABLES_ADMIN ON *.* TO 'clusteradmin'@'%';
GRANT GROUP_REPLICATION_ADMIN ON *.* TO 'clusteradmin'@'%';
FLUSH PRIVILEGES;
EOF
# 3. 配置Group Replication
mysql -uroot -pmysql#password << EOF
-- 设置恢复通道
SET GLOBAL group_replication_bootstrap_group=ON;
CHANGE MASTER TO MASTER_USER='repl', MASTER_PASSWORD='mysql#password'
FOR CHANNEL 'group_replication_recovery';
-- 启动组复制
START GROUP_REPLICATION;
-- 关闭引导模式
SET GLOBAL group_replication_bootstrap_group=OFF;
EOF
# 4. 验证主节点状态
mysql -uroot -pmysql#password << EOF
SELECT * FROM performance_schema.replication_group_members;
EOF
# 其他节点
# 2. 加入集群
mysql -uroot -pmysql#password << EOF
-- 设置恢复通道
CHANGE MASTER TO MASTER_USER='repl', MASTER_PASSWORD='mysql#password'
FOR CHANNEL 'group_replication_recovery';
-- 启动组复制
START GROUP_REPLICATION;
EOF
# 3. 验证状态
mysql -uroot -pmysql#password << EOF
SELECT * FROM performance_schema.replication_group_members;
EOF
Group Replication(GR) 集群创建到这就行
