MyCat + MySQL(3实例)实现数据的分库分表Centos7

本机环境是Centos7,使用的MySQL版本是mysql-community 5.7.29-1.el7

安装MySQL

1、准备了三台虚拟机:192.168.56.102,192.168.56.103,192.168.56.104

2、MyCat安装在192.168.56.103上,首先安装MyCat的机器必须要装jdk

每台机器依次运行以下命令,我的机器上安装的板本是:mysql-community 5.7.29-1.el7,下载量很大等待进度条跑完

yum -y install mysql
yum -y instll mysql-server
yum -y install mysql-devel

MySQL安装完成之后会默认生成一个随机密码,使用命令查看,后面改成自己的密码就可以了(这里偷了点懒,直接用了root用户)

cat /var/log/mysqld.log | grep 'password'

配置字符集及启动MySQL

修改所有机器上的/etc/my.cnf文件,在最后添加编码设置

具体配置查看官方文档:https://dev.mysql.com/doc/refman/5.7/en/server-system-variables.html

[client]
default-character-set=utf8       #默认是utf8

[connection]
default-character-set=utf8   #默认是utf8

[database]
default-character-set=utf8     #默认是latin1

[results]
default-character-set=utf8      #默认是utf8

将MySQL服务设置为开机启动(CentOS 7.x开始,CentOS开始使用systemd服务来代替daemon,原来管理系统启动和管理系统服务的相关命令全部由systemctl命令来代替),启动MySQL服务

systemctl enable mysqld
systemctl start mysqld

登录MySQL查看配置文件是否生效,图中证明配置文件生效了

使用MySQL语句更新root用的远程访问权限,更新为所有IP均能访问(存在一定安全隐患);新增用户mycat,给予权限;

使用mycat用户登录数据库,在每台机器上创建一个数据库,名字不一样(例如:db1、db2、db3)

use mysql;
update user set host='%' where user='root' and host='localhost';
create user 'mycat'@'%' identified by '123456';
grant all privileges on *.* to 'mycat'@'%' identified by '123456';

安装MyCat

下载MyCat Linux的压缩包并解压,这里我把解压厚的文件夹重命名为了MyCat-1.6.7.4

cd /usr/local

wget http://dl.mycat.io/1.6.7.4/Mycat-server-1.6.7.4-release/Mycat-server-1.6.7.4-release-20200105164103-linux.tar.gz

tar -xvf Mycat-server-1.6.7.4-release-20200105164103-linux.tar.gz

 

将MyCat加入Linux的环境变量中(/etc/profile文件)

#编辑文件
vim /etc/profile

#加入以下内容
export MYCAT_HOME=/usr/local/MyCat-1.6.7.4
export PATH=$PATH:$MYCAT_HOME/bin


#保存文件之后执行命令
source /etc/profile

创建用户组mycat,新建mycat用户并加入用户组mycat

group mycat
useradd -g mycat mycat
passwd mycat

配置MySQL及MyCat

首先推荐MyCat官方文档,这里面讲述得非常详细,本文配置基本是按照文档里面来的(自己也做了一些小修改):MyCat权威指南

配置schema.xml,配置schema以及对应的数据节点的信息,三台机器上的schema依次是seckill_102,seckill_103,seckill_104,分片策略选择的是mod_long:

<?xml version="1.0"?>
<!DOCTYPE mycat:schema SYSTEM "schema.dtd">
<mycat:schema xmlns:mycat="http://io.mycat/">
    <schema name="seckill" checkSQLschema="false" sqlMaxLimit="100">
        <table name="manager_user" primaryKey="id" autoIncrement="true" dataNode="seckill_$102-104" rule="mod-long"/>
        <table name="manager_merchant" primaryKey="id" autoIncrement="true" dataNode="seckill_$102-104" rule="mod-long"/>
        <table name="manager_shop" primaryKey="id" autoIncrement="true" dataNode="seckill_$102-104" rule="mod-long"/>
        <table name="manager_product_type" primaryKey="id" autoIncrement="true" dataNode="seckill_$102-104" rule="mod-long"/>
        <table name="manager_product_detail" primaryKey="id" autoIncrement="true" dataNode="seckill_$102-104" rule="mod-long"/>
        <table name="manager_product_info" primaryKey="id" autoIncrement="true" dataNode="seckill_$102-104" rule="mod-long"/>
        <table name="seckill_product" primaryKey="id" autoIncrement="true" dataNode="seckill_$102-104" rule="mod-long"/>
        <table name="seckill_user_result" primaryKey="id" autoIncrement="true" dataNode="seckill_$102-104" rule="mod-long"/>
        <table name="seckill_order" primaryKey="id" autoIncrement="true" dataNode="seckill_$102-104" rule="mod-long"/>
    </schema>

    <dataNode name="seckill_102" dataHost="slave_102" database="seckill_102" />
    <dataNode name="seckill_103" dataHost="master_103" database="seckill_103" />
    <dataNode name="seckill_104" dataHost="slave_104" database="seckill_104" />

    <dataHost name="master_103" maxCon="1000" minCon="10" balance="0" writeType="0" dbType="mysql" dbDriver="native">
        <heartbeat>select user()</heartbeat>
        <!-- MySQL数据库连接串 -->
        <writeHost host="hostM1" url="192.168.56.103:3306" user="mycat" password="123456"></writeHost>
    </dataHost>
    <dataHost name="slave_102" maxCon="1000" minCon="10" balance="0" writeType="0" dbType="mysql" dbDriver="native">
        <heartbeat>select user()</heartbeat>
        <!-- MySQL数据库连接串 -->
        <writeHost host="hostM2" url="192.168.56.102:3306" user="mycat" password="123456"></writeHost>
    </dataHost>
    <dataHost name="slave_104" maxCon="1000" minCon="10" balance="0" writeType="0" dbType="mysql" dbDriver="native">
        <heartbeat>select user()</heartbeat>
        <!-- MySQL数据库连接串 -->
        <writeHost host="hostM3" url="192.168.56.104:3306" user="mycat" password="123456"></writeHost>
    </dataHost>
</mycat:schema>

配置server.xml,图中红框是我修改的地方,主键自增方案我选择的是官方文档9.3节数据库全局序列号:

<!-- 使用数据库进行主键自增 -->
<property name="sequnceHandlerType">1</property>

<!-- Mycat连接数据库时使用的隔离级别    1 - 读未提交 2 - 读已提交 3 - 可重复读 4 - 串行化 当MyCat搭配MySQL使用的时候默认隔离级别是"可重复读"(摘自官方文档) -->
<property name="txIsolation">3</property>

<user name="mycat">
    <property name="password">123456</property>
    <property name="schemas">seckill</property>
    <privileges check="true">
    <!-- 设置了 schema , 但只设置了个别 table 或 未设置 table 的 DML,自动继承 schema 的 DML 属性 -->
        <schema name="seckill" dml="1111"></schema>
    </privileges>
</user>

配置sequence_db_conf.properties,这里面记录的是表中需要增加序列号的表名单的记录;表名一定要大写,seckill_103是MyCat安装的机器的dataNode的名称

#sequence stored in datanode
MANAGER_USER=seckill_103
MANAGER_MERCHANT=seckill_103
MANAGER_SHOP=seckill_103
MANAGER_PRODUCT_TYPE=seckill_103
MANAGER_PRODUCT_DETAIL=seckill_103
MANAGER_PRODUCT_INFO=seckill_103
SECKILL_PRODUCT=seckill_103
SECKILL_USER_RESULT=seckill_103
SECKILL_ORDER=seckill_103

创建数据表以及数据表function,需在MyCat安装的机器上的数据库里执行,完成之后插入需要自增长id的表的名称以及规则,这里我做了一点改动,current_value从INT类型改到了bigint,因为我数据库中的主键类型为bigint,数据库用户从root改成了mycat:

CREATE TABLE mycat_sequence (
    `name` VARCHAR(50) NOT NULL,
    `current_value` bigint NOT NULL,
    `increment` INT NOT NULL DEFAULT 1,
    PRIMARY KEY(name)
) ENGINE=InnoDB default character set utf8;

INSERT INTO mycat_sequence(name,current_value,increment) VALUES ('manager_merchant', 1, 1);
INSERT INTO mycat_sequence(name,current_value,increment) VALUES ('manager_product_detail', 1, 1);
INSERT INTO mycat_sequence(name,current_value,increment) VALUES ('manager_product_info', 1, 1);
INSERT INTO mycat_sequence(name,current_value,increment) VALUES ('manager_product_type', 1, 1);
INSERT INTO mycat_sequence(name,current_value,increment) VALUES ('manager_shop', 1, 1);
INSERT INTO mycat_sequence(name,current_value,increment) VALUES ('manager_user', 1, 1);
INSERT INTO mycat_sequence(name,current_value,increment) VALUES ('seckill_order', 1, 1);
INSERT INTO mycat_sequence(name,current_value,increment) VALUES ('seckill_product', 1, 1);
INSERT INTO mycat_sequence(name,current_value,increment) VALUES ('seckill_user_result', 1, 1);
DROP FUNCTION IF EXISTS `mycat_seq_currval`;
DELIMITER ;;
CREATE DEFINER=`mycat`@`%` FUNCTION `mycat_seq_currval`(seq_name VARCHAR(50)) RETURNS varchar(64) CHARSET utf8
DETERMINISTIC
BEGIN
DECLARE retval VARCHAR(64);
SET retval="-999999999,null";
SELECT concat(CAST(current_value AS CHAR),",",CAST(increment AS CHAR) ) INTO retval FROM MYCAT_SEQUENCE WHERE name = seq_name;
RETURN retval ;
END
;;
DELIMITER ;


DROP FUNCTION IF EXISTS `mycat_seq_nextval`;
DELIMITER ;;
CREATE DEFINER=`mycat`@`%` FUNCTION `mycat_seq_nextval`(seq_name VARCHAR(50)) RETURNS varchar(64) CHARSET utf8
DETERMINISTIC
BEGIN
UPDATE MYCAT_SEQUENCE
SET current_value = current_value + increment WHERE name = seq_name;
RETURN mycat_seq_currval(seq_name);
END
;;
DELIMITER ;


DROP FUNCTION IF EXISTS `mycat_seq_setval`;
DELIMITER ;;
CREATE DEFINER=`mycat`@`%` FUNCTION `mycat_seq_setval`(seq_name VARCHAR(50), value INTEGER) RETURNS varchar(64) CHARSET utf8
DETERMINISTIC
BEGIN
UPDATE MYCAT_SEQUENCE
SET current_value = value
WHERE name = seq_name;
RETURN mycat_seq_currval(seq_name);
END
;;
DELIMITER ;

每次改动MyCat配置文件之后记得要重启MyCat

效果及展示

MyCat暴露出来的端口默认是8066,使用数据库连接到这个代理端口可以直接进行操作,通过这个连接插入数据实验主键是否能够自动增长以及数据会不会自动水平分片:

use seckill;


INSERT INTO seckill_product (product_id, seckill_num, seckill_price, seckill_inventory, create_time, start_time, end_time, shop_id, state, product_price, product_title, product_name, approve_time, seckill_version) VALUES (1, 1, 1999.99, 65, '2019-12-01 20:24:57', '2019-12-01 20:24:59', '2020-12-01 20:25:01', 1, 1, 6799.99, '三星s10 plus秒杀', '三星s10 plus 4+128g', '2019-12-01 20:26:18', 0);
INSERT INTO seckill_product (product_id, seckill_num, seckill_price, seckill_inventory, create_time, start_time, end_time, shop_id, state, product_price, product_title, product_name, approve_time, seckill_version) VALUES (1, 1, 1999.99, 65, '2019-12-01 20:24:57', '2019-12-01 20:24:59', '2020-12-01 20:25:01', 1, 1, 6799.99, '三星s10 plus秒杀', '三星s10 plus 4+128g', '2019-12-01 20:26:18', 0);
INSERT INTO seckill_product (product_id, seckill_num, seckill_price, seckill_inventory, create_time, start_time, end_time, shop_id, state, product_price, product_title, product_name, approve_time, seckill_version) VALUES (1, 1, 1999.99, 65, '2019-12-01 20:24:57', '2019-12-01 20:24:59', '2020-12-01 20:25:01', 1, 1, 6799.99, '三星s10 plus秒杀', '三星s10 plus 4+128g', '2019-12-01 20:26:18', 0);
INSERT INTO seckill_product (product_id, seckill_num, seckill_price, seckill_inventory, create_time, start_time, end_time, shop_id, state, product_price, product_title, product_name, approve_time, seckill_version) VALUES (1, 1, 1999.99, 65, '2019-12-01 20:24:57', '2019-12-01 20:24:59', '2020-12-01 20:25:01', 1, 1, 6799.99, '三星s10 plus秒杀', '三星s10 plus 4+128g', '2019-12-01 20:26:18', 0);

select * from seckill_product;

数据插入成功,返回的也是插入的四条数据

接下来看id自增长和数据的水平分片:id实现了自增长,数据也按照mod-long的策略进行了分片

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值