当前位置:   article > 正文

验证Centos7.5 基于MySQL5.7 的 InnoDB Cluster 高可用环境部署_cluster is online and can tolerate up to one failu

cluster is online and can tolerate up to one failure

前言

分布式MySQL主要有InnoDB和NDB模式, NDB是基于集群的引擎-数据,被自动切分,并复制到数个机器上(数据节点), 适合于那些需要极高查询性能,和高可用性的应用, 原来是为爱立信的电信应用设计的。 NDB提供了高达99.999%的可靠性,在读操作多的应用中表现优异。 对于有很多并发写操作的应用, 还是推荐用InnoDB。

采用InnoDB Cluster, 每台服务器实例,都运行MySQL Group Replication (即冗余复制机制,内置failover), MGR有两种模式,一种是Single-Primary,一种是Multi-Primary,即单主或者多主。

需求注意:模式Multi-Primary中,所有的节点都是主节点,都可以同时被读写,看上去这似乎更好,但是因为多主的复杂性,在功能上如果设置了多主模式,则会有一些使用的限制,比如不支持Foreign Keys with Cascading Constraints。

Mysql InnoDB Cluster 工作原理和流程

MySQL InnoDB集群提供了一个集成的,本地的,HA解决方案。Mysq Innodb Cluster是利用组复制的 pxos协议,保障数据一致性,组复制支持单主模式和多主模式。

MySQL InnoDB集群由以下几部分组成:

  • MySQL Servers with Group Replication:向集群的所有成员复制数据,同时提供容错、自动故障转移和弹性。MySQL Server 5.7.17或更高的版本。
  • MySQL Router:确保客户端请求是负载平衡的,并在任何数据库故障时,路由到正确的服务器。MySQL Router 2.1.3或更高的版本。
  • MySQL Shell:通过内置的管理API,创建及管理Innodb集群。MySQL Shell 1.0.9或更高的版本。

各个组件的关系和工作流程如下:

MySQL5.7 的 InnoDB Cluster 高可用环境部署

环境准备

准备了4台centos7版本的服务器,用来部署innodb cluster多节点集群环境 (至少也要需要3台服务器), 其中:
1) node1、node2、node3 作为 cluster 节点服务器, 三个节点都要安装 mysql5.7.x mysql-shell
2) node1 作为管理节点服务器,用来负责创建 cluster,并作为 cluster 的路由, 该节点需要安装mysql-shell、mysql-router

ip地址     主机名     角色                  安装软件
172.16.7.1 node1 管理节点1+cluster节点1Mysql5.7, mysql-shell,mysql-route
172.16.7.2 node2 cluster节点2          Mysql5.7, mysql-shell
172.16.7.3 node3 cluster节点3     

3) 所有节点的python版本要在2.7以上

  1. [root@node1 ~]# cat /etc/redhat-release
  2. CentOS Linux release 7.5.1804 (Core)
  3. [root@node1 ~]# python -V
  4. Python 2.7.5

系统优化

配置每个节点的/etc/hosts主机映射, 方便通过节点的hostname进行连接
这一步很重要,否则可能会出现无法同步的情况,因为数据库需要根据member_host同步,如果不配置,默认就是localhost,这样时无法通信的!!!

  1. cat /etc/hosts
  2. 172.16.7.1  node1
  3. 172.16.7.2  node2
  4. 172.16.7.3  node3 

所有节点进行如下的相关优化配置

sysctl.conf内核配置

  1. [root@node1 ~]# cat>>/etc/sysctl.conf <<EOF
  2. fs.aio-max-nr = 1048576 \
  3. fs.file-max = 681574400 \
  4. kernel.shmmax = 137438953472 \
  5. kernel.shmmni = 4096 \
  6. kernel.sem = 250 32000 100 200 \
  7. net.ipv4.ip_local_port_range = 9000 65000 \
  8. net.core.rmem_default = 262144 \
  9. net.core.rmem_max = 4194304 \
  10. net.core.wmem_default = 262144 \
  11. net.core.wmem_max = 1048586 \
  12. EOF
  13. [root@node1 ~]# sysctl -p

修改进程数和打开文件数

  1. [root@node1 ~]# cat>>/etc/security/limits.conf <<EOF
  2. mysql soft nproc 65536 \
  3. mysql hard nproc 65536 \
  4. mysql soft nofile 65536 \
  5. mysql hard nofile 65536 \
  6. EOF

限制用户会话

  1. [root@node1 ~]# cat >>/etc/pam.d/login <<EOF
  2. session required /lib/security/pam_limits.so
  3. session required pam_limits.so
  4. EOF
  1. [root@node1 ~]# cat >>/etc/profile <<EOF
  2. if [ $USER = "mysql" ]; then \
  3. ulimit -u 16384 -n 65536 \
  4. fi \
  5. EOF
  6. [root@node1 ~]# source /etc/profile

在管理节点安装mysql shell 和 mysql-route

  1. [root@node1 src]# ll
  2. 总用量 21648
  3. -rw-r--r--. 1 root root 15526654 8月  28 09:52 mysql-router-2.1.4-linux-glibc2.12-x86-64bit.tar.gz
  4. -rw-r--r--. 1 root root  6635831 8月  28 09:52 mysql-shell-1.0.9-linux-glibc2.12-x86-64bit.tar.gz
  5. [root@node1 src]# tar -zvxf mysql-shell-1.0.9-linux-glibc2.12-x86-64bit.tar.gz
  6. [root@node1 src]# tar -zvxf mysql-router-2.1.4-linux-glibc2.12-x86-64bit.tar.gz
  7. [root@node1 src]#  mv mysql-router-2.1.4-linux-glibc2.12-x86-64bit mysql-router
  8. [root@node1 src]# mv mysql-shell-1.0.9-linux-glibc2.12-x86-64bit mysql-shell
  9. [root@node1 src]# mv mysql-router /usr/local/
  10. [root@node1 src]# mv mysql-shell /usr/local/
  1. [root@node1 local]#cat >> /etc/profile <<EOF
  2. export PATH=$PATH:/usr/local/mysql-shell/bin/:/usr/local/mysql-route/bin/
  3. EOF
  4. [root@node1 local]# source /etc/profile
  5. [root@node1 ~]# mysqlprovision --version
  6. mysqlprovision version 2.0.0
  7. [root@node1 ~]# mysqlsh --version
  8. MySQL Shell Version 1.0.9
  9. [root@node1 ~]# mysqlrouter --version
  10. MySQL Router v2.1.4 on Linux (64-bit) (GPL community edition)

在三个cluster节点安装和部署Mysql5.7及 mysql-shell

安装mysql-shell  (三个节点同样操作)

  1. [root@node1 ~]# cd /usr/local/src/
  2. [root@node1 src]# ll mysql-shell-1.0.9-linux-glibc2.12-x86-64bit.tar.gz
  3. -rw-r--r-- 1 root root 6635831 Mar 22  2017 mysql-shell-1.0.9-linux-glibc2.12-x86-64bit.tar.gz
  4.  
  5. [root@node1 src]# tar -zvxf mysql-shell-1.0.9-linux-glibc2.12-x86-64bit.tar.gz
  6. [root@node1 src]# mv mysql-shell-1.0.9-linux-glibc2.12-x86-64bit mysql-shell
  7. [root@node1 src]# mv mysql-shell /usr/local/
  8.  
  9. [root@node1 src]# echo "export PATH=$PATH:/usr/local/mysql-shell/bin/" >> /etc/profile
  10. [root@node1 src]# source /etc/profile
  11.  
  12. [root@node1 ~]# mysqlprovision --version                          
  13. mysqlprovision version 2.0.0
  14.  
  15. [root@node1 ~]# mysqlsh --version      
  16. MySQL Shell Version 1.0.9

安装mysql5.7  (三个节点同样操作)

使用RPM包方式安装

1)卸载系统自带的 mysql和mariadb-lib

  1. [root@node1 src]# /bin/rpm -e $(/bin/rpm -qa | grep mysql|xargs) --nodeps
  2. [root@node1 src]# /bin/rpm -e $(/bin/rpm -qa | grep mariadb|xargs) --nodeps

2)下载mysql5.7.21 rpm安装包
下载地址:http://ftp.ntu.edu.tw/MySQL/Downloads/MySQL-5.7/

  1. [root@node1 src]# tar -vxf mysql-5.7.27-1.el7.x86_64.rpm-bundle.tar
  2. [root@node1 src]# ll
  3. 总用量 1058872
  4. -rw-r--r--. 1 root root  531056640 8月  28 12:05 mysql-5.7.27-1.el7.x86_64.rpm-bundle.tar
  5. -rw-r--r--. 1 7155 31415  25365436 6月  12 14:42 mysql-community-client-5.7.27-1.el7.x86_64.rpm
  6. -rw-r--r--. 1 7155 31415    281248 6月  12 14:42 mysql-community-common-5.7.27-1.el7.x86_64.rpm
  7. -rw-r--r--. 1 7155 31415   3833396 6月  12 14:42 mysql-community-devel-5.7.27-1.el7.x86_64.rpm
  8. -rw-r--r--. 1 7155 31415  47074656 6月  12 14:42 mysql-community-embedded-5.7.27-1.el7.x86_64.rpm
  9. -rw-r--r--. 1 7155 31415  24079736 6月  12 14:42 mysql-community-embedded-compat-5.7.27-1.el7.x86_64.rpm
  10. -rw-r--r--. 1 7155 31415 129991352 6月  12 14:42 mysql-community-embedded-devel-5.7.27-1.el7.x86_64.rpm
  11. -rw-r--r--. 1 7155 31415   2272032 6月  12 14:42 mysql-community-libs-5.7.27-1.el7.x86_64.rpm
  12. -rw-r--r--. 1 7155 31415   2116432 6月  12 14:42 mysql-community-libs-compat-5.7.27-1.el7.x86_64.rpm
  13. -rw-r--r--. 1 7155 31415 173500088 6月  12 14:43 mysql-community-server-5.7.27-1.el7.x86_64.rpm
  14. -rw-r--r--. 1 7155 31415 122530756 6月  12 14:43 mysql-community-test-5.7.27-1.el7.x86_64.rpm
  15. -rw-r--r--. 1 root root   15526654 8月  28 09:52 mysql-router-2.1.4-linux-glibc2.12-x86-64bit.tar.gz
  16. -rw-r--r--. 1 root root    6635831 8月  28 09:52 mysql-shell-1.0.9-linux-glibc2.12-x86-64bit.tar.gz

依次执行(几个包有依赖关系,所以执行有先后)下面命令安装 

  1. [root@node1 src]# rpm -ivh mysql-community-common-5.7.27-1.el7.x86_64.rpm --force
  2. [root@node1 src]# rpm -ivh mysql-community-libs-5.7.27-1.el7.x86_64.rpm --force
  3. [root@node1 src]# rpm -ivh mysql-community-client-5.7.27-1.el7.x86_64.rpm --force
  4. [root@node1 src]# rpm -ivh mysql-community-server-5.7.27-1.el7.x86_64.rpm --force

=============================================================================================================
可能在安装mysql-community-server-5.7.27-1.el7.x86_64.rpm的时候会有如下报错:

  1. [root@kevin ~]# rpm -ivh mysql-community-server-5.7.21-1.el7.x86_64.rpm --force
  2. warning: mysql-community-server-5.7.27-1.el7.x86_64.rpm: Header V3 DSA/SHA1 Signature, key ID 5072e1f5: NOKEY 
  3. error: Failed dependencies: 
  4. libaio.so.1()(64bit) is needed by mysql-community-server-5.7.27-1.el7.x86_64 
  5. libaio.so.1(LIBAIO_0.1)(64bit) is needed by mysql-community-server-5.7.27-1.el7.x86_64 
  6. libaio.so.1(LIBAIO_0.4)(64bit) is needed by mysql-community-server-5.7.27-1.el7.x86_64 
  7. net-tools is needed by mysql-community-server-5.7.27-1.el7.x86_64 

这个报错的意思是需要安装libaio包和net-tools包:
 
安装libaio-0.3.107-10.el6.x86_64.rpm 

  1. [root@node1 src]# wget http://mirror.centos.org/centos/6/os/x86_64/Packages/libaio-0.3.107-10.el6.x86_64.rpm 
  2. [root@node1 src]# rpm -ivh libaio-0.3.107-10.el6.x86_64.rpm --force

安装net-tools  

[root@node1 src]# yum install net-tools 

=============================================================================================================

使用rpm安装方式安装mysql,安装的路径如下:
数据库目录

/var/lib/mysql/

配置文件

  1. /usr/share/mysql(mysql.server命令及配置文件)
  2. /etc/my.cnf

相关命令

/usr/bin(mysqladmin mysqldump等命令)

启动脚本

/etc/rc.d/init.d/(启动脚本文件mysql的目录)

3)数据库初始化 
为了保证数据库目录为与文件的所有者为 mysql 登陆用户,如果你是以 root 身份运行 mysql 服务,需要执行下面的命令初始化

  1. //必须指定datadir,执行后会生成~/.mysql_secret密码文件
  2. [root@node1 src]# mysql_install_db --datadir=/var/lib/mysql
  3. //新版的推荐此方法,执行生会在/var/log/mysqld.log生成随机密码。
  4. //如果是以mysql身份运行,则可以去掉--user选项。
  5. [root@node1 src]# mysqld --initialize --user=mysql

4)更改mysql数据库目录的所属用户及其所属组,然后启动mysql数据库

  1. [root@node1 src]# chown mysql:mysql /var/lib/mysql -R
  2. [root@node1 src]# systemctl start mysqld.service
  3. //启动mysql数据库服务
  4. [root@node1 src]# systemctl enable mysqld.service

5)根据第3步中的密码登录到mysql,更改root用户的密码,新版的mysql在第一次登录后,更改密码前是不能执行任何命令的。
 另外--initialize 选项,默认以“安全”模式来初始化,则会为 root 用户,生成一个密码,并将该密码标记为过期,登陆后你需要设置一个新的密码,
而使用--initialize-insecure命令,则不使用安全模式,则不会为 root 用户,生成一个密码。 
   
这里演示使用的--initialize初始化的,会生成一个 root 账户密码,密码在log文件里,如下最后的"F;HNq*thK2hb",即为随即生成的root密码

  1. [root@node1 src]# cat /var/log/mysqld.log|grep 'A temporary password'
  2. .......
  3. T05:57:00.021884Z 1 [Note] A temporary password is generated for root@localhost: F;HNq*thK2hb
  4.  
  5. [root@kevin ~]# mysql -uroot -p'F;HNq*thK2hb'
  6. mysql> set password=password('sagis@123');
  7. mysql> GRANT ALL PRIVILEGES ON *.* TO 'root'@'%' IDENTIFIED BY 'sagis@123' WITH  GRANT OPTION;
  8. mysql> flush privileges;

配置my.cnf

先配置node1节点的my.cnf

  1. [root@node1 ~]# cp /etc/my.cnf /etc/my.cnf.bak
  2. [root@node1 ~]# >/etc/my.cnf
  3. [root@node1 ~]# vim /etc/my.cnf
  4. [mysqld]
  5. datadir = /var/lib/mysql
  6. socket = /var/lib/mysql/mysql.sock
  7. port=23306
  8. symbolic-links = 0
  9.           
  10. log-error = /var/log/mysqld.log
  11. pid-file = /var/run/mysqld/mysqld.pid
  12.   
  13. #复制框架
  14. server_id=2
  15. gtid_mode=ON
  16. enforce_gtid_consistency=ON
  17. binlog_checksum=NONE
  18.   
  19. log_bin=binlog
  20. log_slave_updates=ON
  21. binlog_format=ROW
  22. master_info_repository=TABLE
  23. relay_log_info_repository=TABLE
  24.   
  25. #组复制设置
  26. #server必须为每个事务收集写集合,并使用XXHASH64哈希算法将其编码为散列
  27. transaction_write_set_extraction=XXHASH64
  28. #告知插件加入或创建组命名,UUID
  29. loose-group_replication_group_name="aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa"
  30. #server启动时不自启组复制,为了避免每次启动自动引导具有相同名称的第二个组,所以设置为OFF。
  31. loose-group_replication_start_on_boot=off
  32. #告诉插件使用IP地址,端口24901用于接收组中其他成员转入连接
  33. loose-group_replication_local_address="172.16.7.2:24902"
  34. #启动组server,种子server,加入组应该连接这些的ip和端口;其他server要加入组得由组成员同意
  35. loose-group_replication_group_seeds="172.16.7.1:24901,172.16.7.2:24902,172.16.7.3:24903"
  36. loose-group_replication_bootstrap_group=off
  37. loose-group_replication_ip_whitelist="172.16.7.1,172.16.7.2,172.16.7.3"
  38. # 使用MGR的单主模式
  39. loose-group_replication_single_primary_mode = on 
  40. disabled_storage_engines = MyISAM,BLACKHOLE,FEDERATED,CSV,ARCHIVE
  41. report_port=23306

如上配置完成后, 将db-node01节点的/etc/my.cnf文件,拷贝到其他两个节点

  1. [root@node1 ~]# rsync -e "ssh -p60202" -avpgolr /etc/my.cnf root@172.16.7.2:/etc/
  2. [root@node1 ~]# rsync -e "ssh -p60203" -avpgolr /etc/my.cnf root@172.16.7.3:/etc/

3个cluster节点除了server_id、loose-group_replication_local_address 两个参数不一样外,其他保持一致。
所以待拷贝完成后, 分别修改node2和node3节点/etc/my.cnf文件的server_id、loose-group_replication_local_address两个参数。

配置完成后, 要依次重启三个节点的数据库,安装MGR插件,设置复制账号(所有MGR节点都要执行

[root@node1 ~]# systemctl restart mysqld

创建Innodb Cluster集群

在 node1 上创建集群,通过 node1 上的 shell 连接node1 的 mysql

  1. [root@node1 ~]# mysqlsh
  2. Welcome to MySQL Shell 1.0.9
  3. ...................
  4. # 执行配置命令,也需要密码
  5. # 然后需要输入MySQL配置文件路径,本示例中的路径是 /usr/local/data/s1/s1.cnf
  6. # 接下来需要创建供其他主机访问的用户,这里选择第1项,为root用户授权
  7. mysql-js> shell.connect('root@172.16.7.1:13306')
  8. Creating a session to 'root@172.16.7.1:13306'
  9. Please provide the password for 'root@172.16.7.1:13306': *********
  10. Save password for 'root@172.16.7.1:13306'? [Y]es/[N]o/Ne[v]er (default No): yes
  11. Fetching schema names for autocompletion... Press ^C to stop.
  12. Your MySQL connection id is 1424
  13. Server version: 5.7.27-log MySQL Community Server (GPL)
  14. No default schema selected; type \use <schema> to set one.
  15. <ClassicSession:root@172.16.7.1:13306>
  16. MySQL  172.16.7.1:13306  JS > dba.configureLocalInstance();
  17. Configuring local MySQL instance listening at port 13306 for use in an InnoDB cluster...
  18. This instance reports its own address as node1:13306
  19. Clients and other cluster members will communicate with it through this address by default. If this is not correct, the report_host MySQL system variable should be changed.
  20. The instance '172.16.7.1:13306' is valid for InnoDB cluster usage.
  21. The instance '172.16.7.1:13306' is already ready for InnoDB cluster usage.
  22. # 创建一个 cluster,命名为 'myCluster'
  23. MySQL  172.16.7.1:13306  JS > var cluster = dba.createCluster('myCluster');
  24. A new InnoDB cluster will be created on instance '172.16.7.1:13306'.
  25. Validating instance at 172.16.7.1:13306...
  26. This instance reports its own address as node1:13306
  27. Adding Seed Instance...
  28.  
  29. Cluster successfully created. Use Cluster.addInstance() to add MySQL instances.
  30. At least 3 instances are needed for the cluster to be able to withstand up to one server failure.

如上的信息, 如果创建成功, 则会输出的信息中会有类似“Cluster successfully created.”的语句

  1. #创建成功后,查看cluster状态
  2. mysql-js> cluster.status();
  3. {
  4.     "clusterName": "myCluster",
  5.     "defaultReplicaSet": {
  6.         "name": "default",
  7.         "primary": "172.16.7.1:3306",
  8.         "ssl": "DISABLED",
  9.         "status": "OK",
  10.         "statusText": "Cluster is ONLINE and can tolerate up to ONE failure.",
  11.         "topology": {
  12.             "172.16.7.1:3306": {
  13.                 "address": "172.16.7.1:3306",
  14.                 "mode": "R/W",
  15.                 "readReplicas": {},
  16.                 "role": "HA",
  17.                 "status": "ONLINE"
  18.         }
  19.     }
  20. }
  21. mysql-js> dba.getCluster();
  22. <Cluster:myCluster>

添加节点 node2到上面创建的"myCluster"集群中。
通过node2本机, mysql-shell 对 mysql 进行配置

  1. [root@node2 ~]# mysqlsh
  2. ................
  3. mysql-js> shell.connect('root@172.16.7.2:3306')
  4. Creating a session to 'root@172.16.7.2:3306'
  5. Please provide the password for 'root@172.16.7.2:3306': *********
  6. Save password for 'root@172.16.7.2:3306'? [Y]es/[N]o/Ne[v]er (default No): yes
  7. Fetching schema names for autocompletion... Press ^C to stop.
  8. Your MySQL connection id is 1424
  9. Server version: 5.7.27-log MySQL Community Server (GPL)
  10. No default schema selected; type \use <schema> to set one.
  11. <ClassicSession:root@172.16.7.2:3306>
  12. MySQL  172.16.7.2:3306  JS > dba.configureLocalInstance();
  13. Configuring local MySQL instance listening at port 3306 for use in an InnoDB cluster...
  14. This instance reports its own address as node2:3306
  15. Clients and other cluster members will communicate with it through this address by default. If this is not correct, the report_host MySQL system variable should be changed.
  16. The instance '172.16.7.2:3306' is valid for InnoDB cluster usage.
  17. The instance '172.16.7.2:3306' is already ready for InnoDB cluster usage.

接着修改 my.cnf,添加配置项:

  1. [root@node2 ~]# vim /etc/my.cnf
  2. ............
  3. loose-group_replication_allow_local_disjoint_gtids_join=on

重启mysql服务

[root@node2 ~]# systemctl restart mysqld

然后通过 node1 节点 的 mysql-shell 添加 172.16.7.2 到 "myCluster"集群中。
接着上面的node1的mysql-shell终端窗口  ,(注意这个终端窗口是上面执行后, 没有关闭一直开着的)
 

  1. mysql-js> cluster.addInstance('root@172.16.7.2:3306');
  2. A new instance will be added to the InnoDB cluster. Depending on the amount of
  3. data on the cluster this might take from a few seconds to several hours.
  4.  
  5. Please provide the password for 'root@172.16.7.2:3306':
  6. Adding instance to the cluster ...
  7.  
  8. The instance 'root@172.16.7.2:3306' was successfully added to the cluster.

上面信息表示172.16.7.2节点已经成功添加到"myCluster"集群中了. 如下查看集群状态

  1. mysql-js> cluster.status();
  2. {
  3.     "clusterName": "myCluster",
  4.     "defaultReplicaSet": {
  5.         "name": "default",
  6.         "primary": "172.16.7.1:3306",
  7.         "ssl": "DISABLED",
  8.         "status": "OK",
  9.         "statusText": "Cluster is ONLINE and can tolerate up to ONE failure.",
  10.         "topology": {
  11.             "172.16.7.1:3306": {
  12.                 "address": "172.16.7.1:3306",
  13.                 "mode": "R/W",
  14.                 "readReplicas": {},
  15.                 "role": "HA",
  16.                 "status": "ONLINE"
  17.             },
  18.             "172.16.7.2:3306": {
  19.                 "address": "172.16.7.2:3306",
  20.                 "mode": "R/O",
  21.                 "readReplicas": {},
  22.                 "role": "HA",
  23.                 "status": "ONLINE"
  24.             }
  25.         }
  26.     }
  27. }

同样, 上面操作后,这个172.16.7.1节点的mysql-shell,当前终端窗口不要关闭,继续保持在集群状态中, 下面添加172.16.7.3节点,到集群中会用到这里。(后面常用命令中会提到)
添加节点 node3到上面创建的"myCluster"集群中

通过node3本机 mysql-shell 对 mysql 进行配置

  1. [root@node3 ~]# mysqlsh
  2. ................
  3. mysql-js> shell.connect('root@172.16.7.3:3306')
  4. Creating a session to 'root@172.16.7.3:3306'
  5. Please provide the password for 'root@172.16.7.3:3306': *********
  6. Save password for 'root@172.16.7.3:3306'? [Y]es/[N]o/Ne[v]er (default No): yes
  7. Fetching schema names for autocompletion... Press ^C to stop.
  8. Your MySQL connection id is 1424
  9. Server version: 5.7.27-log MySQL Community Server (GPL)
  10. No default schema selected; type \use <schema> to set one.
  11. <ClassicSession:root@172.16.7.3:3306>
  12. MySQL  172.16.7.3:3306  JS > dba.configureLocalInstance();
  13. Configuring local MySQL instance listening at port 3306 for use in an InnoDB cluster...
  14. This instance reports its own address as node3:3306
  15. Clients and other cluster members will communicate with it through this address by default. If this is not correct, the report_host MySQL system variable should be changed.
  16. The instance '172.16.7.3:3306' is valid for InnoDB cluster usage.
  17. The instance '172.16.7.3:3306' is already ready for InnoDB cluster usage.

接着修改 my.cnf,添加配置项:

  1. [root@node3 ~]# vim /etc/my.cnf
  2. ............
  3. loose-group_replication_allow_local_disjoint_gtids_join=on

重启mysql服务

[root@node3 ~]# systemctl restart mysqld

然后通过 node1 节点 的 mysql-shell 添加 172.16.7.3 到 "myCluster"集群中
接着上面的node1的mysql-shell终端窗口  (注意这个终端窗口是上面执行后, 没有关闭一直开着的)

  1. mysql-js> cluster.addInstance('root@172.16.7.3:3306');
  2. A new instance will be added to the InnoDB cluster. Depending on the amount of
  3. data on the cluster this might take from a few seconds to several hours.
  4.  
  5. Please provide the password for 'root@172.16.7.3:3306':
  6. Adding instance to the cluster ...
  7.  
  8. The instance 'root@172.16.7.3:3306' was successfully added to the cluster.

上面信息表示172.16.7.3节点已经成功添加到"myCluster"集群中了. 如下查看集群状态

  1. mysql-js> cluster.status();
  2. {
  3.     "clusterName": "myCluster",
  4.     "defaultReplicaSet": {
  5.         "name": "default",
  6.         "primary": "172.16.7.1:3306",
  7.         "ssl": "DISABLED",
  8.         "status": "OK",
  9.         "statusText": "Cluster is ONLINE and can tolerate up to ONE failure.",
  10.         "topology": {
  11.             "172.16.7.1:3306": {
  12.                 "address": "172.16.7.1:3306",
  13.                 "mode": "R/W",
  14.                 "readReplicas": {},
  15.                 "role": "HA",
  16.                 "status": "ONLINE"
  17.             },
  18.             "172.16.7.2:3306": {
  19.                 "address": "172.16.7.2:3306",
  20.                 "mode": "R/O",
  21.                 "readReplicas": {},
  22.                 "role": "HA",
  23.                 "status": "ONLINE"
  24.             },
  25.             "172.16.7.3:3306": {
  26.                 "address": "172.16.7.3:3306",
  27.                 "mode": "R/O",
  28.                 "readReplicas": {},
  29.                 "role": "HA",
  30.                 "status": "ONLINE"
  31.             }
  32.         },
  33.         "topologyMode": "Single-Primary"
  34.     },
  35.     "groupInformationSourceMember": "172.16.7.1:3306"
  36. }

通过上面cluster集群信息可知,  172.16.7.1节点是主节点, 具有R/W读写权限, 其他两个节点是从节点, 具有R/O 只读权限
启动管理节点的route
进入 172.16.7.1管理节点中mysql-router 安装目录,配置并启动 router

  1. [root@node1 ~]# ./bin/mysqlrouter --bootstrap root@172.16.7.1:3306 -d myrouter --user=root
  2. Please enter MySQL password for root:
  3.  
  4. Bootstrapping MySQL Router instance at /root/myrouter...
  5. MySQL Router  has now been configured for the InnoDB cluster 'myCluster'.
  6.  
  7. The following connection information can be used to connect to the cluster.
  8.  
  9. Classic MySQL protocol connections to cluster 'myCluster':
  10. - Read/Write Connections: localhost:6446             #读写端口
  11. - Read/Only Connections: localhost:6447              #只读端口
  12.  
  13. X protocol connections to cluster 'myCluster':
  14. - Read/Write Connections: localhost:64460
  15. - Read/Only Connections: localhost:64470

这里会在当前目录下产生mysql-router 目录, 并生成router配置文件,接着把配置文件修改一下:

  1. [root@node1 ~]# ls /root/myrouter/
  2. data  log  mysqlrouter.conf  mysqlrouter.key  run  start.sh  stop.sh
  3. //可以修改配置文件, 也可以默认不修改
  4. [root@node1 ~]# cat /root/myrouter/mysqlrouter.conf         
  5.  

默认通过route连接mysql后, 6446端口连接后可以进行读写操作. 6447端口连接后只能进行只读操作.
 
然后启动mysqlroute

  1. [root@node1 ~]# /root/myrouter/start.sh
  2. PID 28505 written to /root/myrouter/mysqlrouter.pid
  3.  
  4. [root@node1 ~]# ps -ef|grep myroute                 
  5. [root@node1 ~]# ps -ef|grep myroute
  6. root      7827  7755  0 10:49 pts/0    00:00:00 grep --color=auto myroute
  7. root     28505     1  0 03:55 ?        00:00:55 /usr/local/mysql-router/bin/mysqlrouter -c /usr/local/mysql-router/myrouter/mysqlrouter.conf
  8.  
  9. [root@node1 ~]# netstat -tunlp|grep 28505
  10. tcp        0      0 0.0.0.0:64460           0.0.0.0:*               LISTEN      28505/mysqlrouter  
  11. tcp        0      0 0.0.0.0:6446            0.0.0.0:*               LISTEN      28505/mysqlrouter  
  12. tcp        0      0 0.0.0.0:6447            0.0.0.0:*               LISTEN      28505/mysqlrouter  
  13. tcp        0      0 0.0.0.0:64470           0.0.0.0:*               LISTEN      28505/mysqlrouter 

这样就可以使用MySQL客户端连接router了.  下面验证下连接router:
 
a) 管理节点本机mysql-shell连接:

[root@node1 ~]# mysqlsh --uri root@localhost:6446

b) 管理节点本机mysql连接:

[root@node1 ~]# mysql -u root -h 127.0.0.1 -P 6446 -p

c) 远程客户机通过route连接mysql

[root@node1 ~]# mysql -u root -h 172.16.7.1 -P 6446 -p

测试cluster节点数据同步. 这里选择node3节点作为远程客户端连接router

  1. [root@node3 ~]# mysql -u root -h 172.16.7.3 -P 6446 -p
  2. Enter password:
  3. Welcome to the MySQL monitor.  Commands end with ; or \g.
  4. Your MySQL connection id is 1054
  5. Server version: 5.7.25-log MySQL Community Server (GPL)
  6.  
  7. Copyright (c) 2000, 2019, Oracle and/or its affiliates. All rights reserved.
  8.  
  9. Oracle is a registered trademark of Oracle Corporation and/or its
  10. affiliates. Other names may be trademarks of their respective
  11. owners.
  12.  
  13. Type 'help;' or '\h' for help. Type '\c' to clear the current input statement.
  14.  
  15. mysql> show databases;
  16. +-------------------------------+
  17. | Database                      |
  18. +-------------------------------+
  19. | information_schema            |
  20. | mysql                         |
  21. | mysql_innodb_cluster_metadata |
  22. | performance_schema            |
  23. | sys                           |
  24. +-------------------------------+
  25. 5 rows in set (0.00 sec)

测试测试库kevin

  1. mysql> CREATE DATABASE test CHARACTER SET utf8 COLLATE utf8_general_ci; 
  2. ERROR 1044 (42000): Access denied for user 'root'@'%' to database 'test'

这是因为'root@%'没有创建库的权限

  1. mysql> select host,user from mysql.user;
  2. +-----------+----------------------------------+
  3. | host      | user                             |
  4. +-----------+----------------------------------+
  5. | %         | mysql_innodb_cluster_rp496261783 |
  6. | %         | mysql_innodb_cluster_rp496457975 |
  7. | %         | mysql_innodb_cluster_rp496569258 |
  8. | %         | mysql_innodb_cluster_rp496629685 |
  9. | %         | mysql_router1_olzau3ltjqzx       |
  10. | %         | root                             |
  11. | localhost | mysql.session                    |
  12. | localhost | mysql.sys                        |
  13. | localhost | root                             |
  14. +-----------+----------------------------------+
  15. 9 rows in set (0.00 sec)
  16.  
  17. mysql> show grants for root@'%';
  18. +-----------------------------------------------------------------------------------------------------------------------------------------+
  19. | Grants for root@%                                                                                                                       |
  20. +-----------------------------------------------------------------------------------------------------------------------------------------+
  21. | GRANT RELOAD, SHUTDOWN, PROCESS, FILE, SUPER, REPLICATION SLAVE, REPLICATION CLIENT, CREATE USER ON *.* TO 'root'@'%' WITH GRANT OPTION |
  22. | GRANT SELECT, INSERT, UPDATE, DELETE ON `mysql`.* TO 'root'@'%' WITH GRANT OPTION                                                       |
  23. | GRANT SELECT ON `performance_schema`.* TO 'root'@'%' WITH GRANT OPTION                                                                  |
  24. | GRANT ALL PRIVILEGES ON `mysql_innodb_cluster_metadata`.* TO 'root'@'%' WITH GRANT OPTION                                               |
  25. +-----------------------------------------------------------------------------------------------------------------------------------------+
  26. 4 rows in set (0.00 sec)

登录主库, 创建一个具有管理权权限的用户

  1. [root@node1 ~]# mysql -psagis@123
  2. .............
  3. mysql> set global validate_password_policy=0;
  4. Query OK, 0 rows affected (0.00 sec)
  5.  
  6. mysql> set global validate_password_length=1;
  7. Query OK, 0 rows affected (0.00 sec)
  8.  
  9. mysql> grant all on *.* to hjh@'%' identified by "hjh@123" with grant option;
  10. Query OK, 0 rows affected, 1 warning (0.05 sec)

接着远程使用上面创建的新账号登录router操作

  1. [root@node3 ~]# mysql -u bobo -h 172.16.7.3 -P 6446 -p
  2. ........
  3. mysql> show grants for hjh@'%';
  4. +-------------------------------------------------------------+
  5. | Grants for hjh@%                                           |
  6. +-------------------------------------------------------------+
  7. | GRANT ALL PRIVILEGES ON *.* TO 'hjh'@'%' WITH GRANT OPTION |
  8. +-------------------------------------------------------------+
  9. 1 row in set (0.00 sec)

测试测试库test

  1. mysql> CREATE DATABASE test CHARACTER SET utf8 COLLATE utf8_general_ci; 
  2. Query OK, 1 row affected (0.06 sec)
  3.  
  4. mysql> use test;
  5. Database changed
  6. mysql> create table if not exists test (id int(10) PRIMARY KEY AUTO_INCREMENT,name varchar(50) NOT NULL);
  7. Query OK, 0 rows affected (0.22 sec)
  8.  
  9. mysql> insert into kevin.haha values(1,"hejianhui");
  10. Query OK, 1 rows affected (0.13 sec)
  11. Records: 1  Duplicates: 0  Warnings: 0
  12.  
  13. mysql> select * from test.test;
  14. +----+-----------+
  15. | id | name      |
  16. +----+-----------+
  17. |  1 | hejianhui |
  18. +----+-----------+
  19. 4 rows in set (0.00 sec)

分别登录三个cluster节点的mysql, 发现测试库test已经完成同步了, 其中:
写操作的数据会先写到172.16.7.1节点, 然后同步到172.16.7.2和172.16.7.3只读节点上.
 
注意: 上面使用6446端口连接的route, 可以进行读写操作. 但是使用6447端口连接后, 就只能进行只读操作了. 登录后可以执行" select @@hostname" 查看登录到哪个节点上.

  1. [root@node3 ~]# mysql -u hjh -h 172.16.7.3 -P 6447 -p
  2. .............
  3. mysql> select * from kevin.haha;
  4. +----+-----------+
  5. | id | name      |
  6. +----+-----------+
  7. |  1 | hejianhui |
  8. +----+-----------+
  9. 1 rows in set (0.00 sec)
  10.  
  11. mysql> delete from test.test where id=1;
  12. ERROR 1290 (HY000): The MySQL server is running with the --super-read-only option so it cannot execute this statement

此外, 还可以利用keepalived实现InnoDB Cluster的高可用, 即两台db-route管理节点, 通过VIP资源实现故障无感知切换.  这样需要准备5台节点, 其中3个cluster节点(安装mysql, mysql-shell), 2个route管理节点(安装keepalived, mysql-shell, mysql-route, mysql-client)

 InnoDB Cluster集群 日常维护命令

在各节点配置之后, 创建cluster集群之前, 可以依次检查下cluster各个节点是否可用

dba.checkInstanceConfiguration("root@172.16.7.1:3306");

比如在上面创建Innodb cluster集群过程中, 再次登录mysqlsh (从客户端远程登录, 或任意节点本地登录), 怎么获得并查看集群状态

  1. mysql-js> shell.connect("root@172.16.7.1:3306");
  2. Please provide the password for 'root@172.16.7.1:3306':
  3. Creating a Session to 'root@172.16.7.1:3306'
  4. Classic Session successfully established. No default schema selected.

查看集群状态

  1. mysql-js> cluster.status();
  2. ReferenceError: cluster is not defined

上面方式查看, 会报错说集群没有定义, 这时需要先执行下面这条语句之后,才看查看到集群状态!!!!!

  1. mysql-js> cluster.status();
  2. ReferenceError: cluster is not defined

然后就可以查看集群状态了

  1. mysql-js> cluster=dba.getCluster();
  2. <Cluster:myCluster>
  3. mysql-js> cluster.status();

查看已创建的集群名称

  1.  MySQL  172.16.60.214:6446 ssl  JS > dba.getCluster();
  2. <Cluster:myCluster>

=================================================

总结

  1. dba.getCluster();     #查看创建的集群
  2. cluster=dba.getCluster();    #获取当前集群
  3. cluster.status();         #查看集群状态

InnoDB Cluster集群维护的命令帮助

dba.help();

日常使用的几个重要命令 (mysqlsh的JS语法) 

  1. #检查节点配置实例,用于加入cluster之前
  2. dba.checkInstanceConfiguration("root@hostname:3306")     
  3. #重启
  4. dba.rebootClusterFromCompleteOutage('myCluster');        
  5. #删除schema
  6. dba.dropMetadataSchema();                               
  7. #获取当前集群 
  8. var cluster = dba.getCluster('myCluster')                
  9. #检查cluster里节点状态 
  10. cluster.checkInstanceState("root@hostname:3306")        
  11. #重新加入节点,我本地测试的时候发现rejoin一直无效,每次是delete后 
  12. cluster.rejoinInstance("root@hostname:3306")             
  13. #删除集群 
  14. addcluster.dissolve({force:true})                       
  15. #增加节点 
  16. cluster.addInstance("root@hostname:3306")                
  17. #删除节点 
  18. cluster.removeInstance("root@hostname:3306")             
  19. #强制删除节点 
  20. cluster.removeInstance('root@host:3306',{force:true})    
  21. #解散集群 
  22. cluster.dissolve({force:true})                           
  23. #集群描述 
  24. cluster.describe();                                      

集群节点状态

  1. - ONLINE:  The instance is online and participating in the cluster.
  2. - OFFLINE:  The instance has lost connection to the other instances.
  3. - RECOVERING:  The instance is attempting to synchronize with the cluster by retrieving transactions it needs before it can become an ONLINE member.
  4. - UNREACHABLE:  The instance has lost communication with the cluster.
  5. - ERROR:  The instance has encountered an error during the recovery phase or while applying a transaction

硬件物理部署集群

 

MySQL InnoDB Cluster 集群特性, 有什么好处

集成易用

MySQL InnoDB集群,紧密集成了MySQL Servers with Group Replication,MySQL Router,和MySQL Shell,所以不必依赖于外部工具,脚本或其他部件。 另外它利用了现有的MySQL特性,如:InnoDB, GTIDs, binary logs, multi-threaded slave execution, multi-source replication and Performance Schema。可以在五分钟内利用MySQL Shell中的脚本化的管理API,来创建及管理MySQL集群。

使用组复制的mysql server HA

组复制提供了内置的组成员管理、数据一致性保证、冲突检测和处理、节点故障检测和数据库故障转移相关操作的本地高可用性,无需人工干预或自定义工具

组复制同时,实现了带自动选主的单主模式及任意更新的多主模式。通过使用一个强大的新的组通信系统,它提供了流行的Paxos算法的内部实现,来自动协调数据复制、一致性、membership。这提供了使MySQL数据库高度可用所需的所有内置机制。

弹性

通过组复制,一组服务器协调在一起形成一个组。组成员是动态的,服务器可以自愿或强制的地离开及随时加入。组将根据需要自动重新配置自己,并确保任何加入成员与组同步。这样就可以方便地在需要时,快速地调整数据库的总容量

故障检测

组复制,实现了一个分布式故障检测器,来查找,并报告failed不再参与组的服务器,组中剩余成员将重新配置。

容错

组复制,基于流行的Paxos分布式算法,来提供服务器之间的分布式协调。为了使一个小组继续发挥作用,它要求大多数成员在线,并就每一个变化达成协议。这允许MySQL数据库在发生故障时安全地继续操作,而无需人工干预,不存在数据丢失或数据损坏的风险。

自愈

如果一个服务器加入该组,它将自动将其状态与现有成员同步。如果服务器离开该组,例如它被取下来进行维护,剩下的服务器将看到它已离开,并将自动重新配置组。当服务器后重新加入组,它会自动重新与组同步。

监测

MySQL Enterprise Monitor 3.4及以后的版本,全面支持组复制;监控每个节点的配置,健康,和性能。并且提供最佳实践建议和提醒,以及易于理解的可视化工具,允许您轻松地监控和管理您的组复制和InnoDB集群。

通过MySQL Router为mysql客户机应用程序实现HA

MySQL的路由器,允许您轻松迁移您的独立的MySQL实例,到本地分布式高可用集群,而不影响现有的应用程序。新metadata_cache插件,为Innodb 集群提供了透明的客户端连接路由、负载平衡和故障转移的能力。

简单易用的MySQL shell

MySQL Shell为所有MySQL相关的任务提供了一个直观、灵活、功能强大的接口。
新的adminapi,使得它很容易用一种自我描述的自然语言来创建,监控和管理包括MySQL Router在内的MySQL InnoDB集群,而不需要了解低层次的概念,配置选项,或其他复杂的方面。

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/人工智能uu/article/detail/1006234
推荐阅读
相关标签
  

闽ICP备14008679号