```basic |
1、一个彻底开源的,面向企业应用开发的大数据库集群 |
2、支持事务、ACID、可以替代MySQL的加强版数据库 |
3、一个可以视为MySQL集群的企业级数据库,用来替代昂贵的Oracle集群 |
4、一个融合内存缓存技术、NoSQL技术、HDFS大数据的新型SQL Server |
5、结合传统数据库和新型分布式数据仓库的新一代企业级数据库产品 |
6、一个新颖的数据库中间件产品 |
``` |
|
|
|
## Mycat原理 |
|
|
|
|
然后将此SQL发往后端的真实数据库,并将返回的结果做适当的处理,最终再返回给用户。 |
如下图: |
|
因此你可以用一台到N台服务器来分片,分片规则为(sharding rule)典型的字符串枚举分片规则,一个规则的定义是分片字段(sharding column)+分片函数(rule function), |
|
|
|
然后将SQL发往这些分片去执行,最后收集和处理所有分片返回的结果数据,并输出到客户端。以select * from Orders where prov=?语句为例,查到prov=wuhan,按照分片函数,wuhan返回dn1, |
于是SQL就发给了MySQL1,去取DB1上的查询结果,并返回给用户。 |
|
如果上述SQL改为select * from Orders where prov in (‘wuhan’,‘beijing’),那么,SQL就会发给MySQL1与MySQL2去执行,然后结果集合并后输出给用户。但通常业务中我们的SQL会有Order By |
以及Limit翻页语法,此时就涉及到结果集在Mycat端的二次处理,这部分的代码也比较复杂,而最复杂的则属两个表的Jion问题, |
|
为此,Mycat提出了创新性的ER分片、全局表、HBT(Human Brain Tech)人工智能的Catlet、以及结合Storm/Spark引擎等十八般武艺的解决办法,从而成为目前业界最强大的方案,这就是开源的力量! |
|
1.png |
|
## 为什么使用Mycat |
|
如今随着互联网的发展,数据的量级也是撑指数的增长,从GB到TB到PB。对数据的各种操作也是愈加的困难,传统的关系性数据库已经无法满足快速查询与插入数据的需求; |
|
|
|
一些折衷是无法满足使用场景的,就比如有些使用场景是绝对要有事务与安全指标的。这个时候NoSQL肯定是无法满足的,所以还是需要使用关系性数据库。 |
|
如何使用关系型数据库解决海量存储的问题呢?此时就需要做数据库集群,为了提高查询性能将一个数据库的数据分散到不同的数据库中存储,为应对此问题就出现了——MyCat |
|
核心技术(分库分表) |
|
数据库分片指:通过某种特定的条件,将我们存放在一个数据库中的数据分散存放在不同的多个数据库(主机)中,这样来达到分散单台设备的负载,根据切片规则,可分为以下两种切片模式 |
MyCAT通过定义表的分片规则来实现分片,每个表格可以捆绑一个分片规则,每个分片规则指定一个分片字段并绑定一个函数,来实现动态分片算法 |
|
1 . Schema:逻辑库,与MySQL中的Database(数据库)对应,一个逻辑库中定义了所包括的Table。 |
2 . Table:逻辑表,即物理数据库中存储的某一张表,与传统数据库不同,这里的表格需要声明其所存储的逻辑数据节点DataNode。在此可以指定表的分片规则。 |
3 . DataNode:MyCAT的逻辑数据节点,是存放table的具体物理节点,也称之为分片节点,通过DataSource来关联到后端某个具体数据库上 |
4.DataSource:定义某个物理库的访问地址,用于捆绑到Datanode上 |
5 . 分片规则:前面讲了数据切分,一个大表被分成若干个分片表,就需要一定的规则,这样按照某种业务规则把数据分到某个分片的规则就是分片规则,数据切分选择合适的分片规则非常重要,将极大的避免后续数据处理的难 |
|
## Mycat读写分离 |
|
· 基础架构图 |
|
|
|
2.png |
|
### 环境准备 |
|
|
|
|
|
|
|
|
|
|
|
|
### 二进制安装mysql |
|
1.创建目录初始化数据 |
|
```bash |
mkdir /data/33{07..10}/data -p |
mysqld --initialize-insecure --user=mysql --datadir=/data/3307/data --basedir=/app/mysql |
mysqld --initialize-insecure --user=mysql --datadir=/data/3308/data --basedir=/app/mysql |
mysqld --initialize-insecure --user=mysql --datadir=/data/3309/data --basedir=/app/mysql |
mysqld --initialize-insecure --user=mysql --datadir=/data/3310/data --basedir=/app/mysql |
``` |
|
|
2.准备配置文件和启动脚本 |
|
```bash |
db01====== |
cat >/data/3307/my.cnf<<EOF |
[mysqld] |
basedir=/app/mysql |
datadir=/data/3307/data |
socket=/data/3307/mysql.sock |
port=3307 |
log-error=/data/3307/mysql.log |
log_bin=/data/3307/mysql-bin |
binlog_format=row |
skip-name-resolve |
server-id=7 |
gtid-mode=on |
enforce-gtid-consistency=true |
log-slave-updates=1 |
EOF |
|
cat >/data/3308/my.cnf<<EOF |
[mysqld] |
basedir=/app/mysql |
datadir=/data/3308/data |
port=3308 |
socket=/data/3308/mysql.sock |
log-error=/data/3308/mysql.log |
log_bin=/data/3308/mysql-bin |
binlog_format=row |
skip-name-resolve |
server-id=8 |
gtid-mode=on |
enforce-gtid-consistency=true |
log-slave-updates=1 |
EOF |
|
cat >/data/3309/my.cnf<<EOF |
[mysqld] |
basedir=/app/mysql |
datadir=/data/3309/data |
socket=/data/3309/mysql.sock |
port=3309 |
log-error=/data/3309/mysql.log |
log_bin=/data/3309/mysql-bin |
binlog_format=row |
skip-name-resolve |
server-id=9 |
gtid-mode=on |
enforce-gtid-consistency=true |
log-slave-updates=1 |
EOF |
cat >/data/3310/my.cnf<<EOF |
[mysqld] |
basedir=/app/mysql |
datadir=/data/3310/data |
socket=/data/3310/mysql.sock |
port=3310 |
log-error=/data/3310/mysql.log |
log_bin=/data/3310/mysql-bin |
binlog_format=row |
skip-name-resolve |
server-id=10 |
gtid-mode=on |
enforce-gtid-consistency=true |
log-slave-updates=1 |
EOF |
|
cat >/etc/systemd/system/mysqld3307.service<<EOF |
[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 |
ExecStart=/app/mysql/bin/mysqld --defaults-file=/data/3307/my.cnf |
LimitNOFILE = 5000 |
EOF |
|
cat >/etc/systemd/system/mysqld3308.service<<EOF |
[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 |
ExecStart=/app/mysql/bin/mysqld --defaults-file=/data/3308/my.cnf |
LimitNOFILE = 5000 |
EOF |
|
cat >/etc/systemd/system/mysqld3309.service<<EOF |
[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 |
ExecStart=/app/mysql/bin/mysqld --defaults-file=/data/3309/my.cnf |
LimitNOFILE = 5000 |
EOF |
cat >/etc/systemd/system/mysqld3310.service<<EOF |
[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 |
ExecStart=/app/mysql/bin/mysqld --defaults-file=/data/3310/my.cnf |
LimitNOFILE = 5000 |
EOF |
db02======= |
cat >/data/3307/my.cnf<<EOF |
[mysqld] |
basedir=/app/mysql |
datadir=/data/3307/data |
socket=/data/3307/mysql.sock |
port=3307 |
log-error=/data/3307/mysql.log |
log_bin=/data/3307/mysql-bin |
binlog_format=row |
skip-name-resolve |
server-id=17 |
gtid-mode=on |
enforce-gtid-consistency=true |
log-slave-updates=1 |
EOF |
cat >/data/3308/my.cnf<<EOF |
[mysqld] |
basedir=/app/mysql |
datadir=/data/3308/data |
port=3308 |
socket=/data/3308/mysql.sock |
log-error=/data/3308/mysql.log |
log_bin=/data/3308/mysql-bin |
binlog_format=row |
skip-name-resolve |
server-id=18 |
gtid-mode=on |
enforce-gtid-consistency=true |
log-slave-updates=1 |
EOF |
cat >/data/3309/my.cnf<<EOF |
[mysqld] |
basedir=/app/mysql |
datadir=/data/3309/data |
socket=/data/3309/mysql.sock |
port=3309 |
log-error=/data/3309/mysql.log |
log_bin=/data/3309/mysql-bin |
binlog_format=row |
skip-name-resolve |
server-id=19 |
gtid-mode=on |
enforce-gtid-consistency=true |
log-slave-updates=1 |
EOF |
|
|
cat >/data/3310/my.cnf<<EOF |
[mysqld] |
basedir=/app/mysql |
datadir=/data/3310/data |
socket=/data/3310/mysql.sock |
port=3310 |
log-error=/data/3310/mysql.log |
log_bin=/data/3310/mysql-bin |
binlog_format=row |
skip-name-resolve |
server-id=20 |
gtid-mode=on |
enforce-gtid-consistency=true |
log-slave-updates=1 |
EOF |
|
cat >/etc/systemd/system/mysqld3307.service<<EOF |
[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 |
ExecStart=/app/mysql/bin/mysqld --defaults-file=/data/3307/my.cnf |
LimitNOFILE = 5000 |
EOF |
|
cat >/etc/systemd/system/mysqld3308.service<<EOF |
[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 |
ExecStart=/app/mysql/bin/mysqld --defaults-file=/data/3308/my.cnf |
LimitNOFILE = 5000 |
EOF |
|
cat >/etc/systemd/system/mysqld3309.service<<EOF |
[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 |
ExecStart=/app/mysql/bin/mysqld --defaults-file=/data/3309/my.cnf |
LimitNOFILE = 5000 |
EOF |
cat >/etc/systemd/system/mysqld3310.service<<EOF |
[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 |
ExecStart=/app/mysql/bin/mysqld --defaults-file=/data/3310/my.cnf |
LimitNOFILE = 5000 |
EOF |
``` |
|
|
3.修改权限启动多实例 |
|
```bash |
chown -R mysql.mysql /data/* |
systemctl start mysqld3307 |
systemctl start mysqld3308 |
systemctl start mysqld3309 |
systemctl start mysqld3310 |
|
mysql -S /data/3307/mysql.sock -e "show variables like 'server_id'" |
mysql -S /data/3308/mysql.sock -e "show variables like 'server_id'" |
mysql -S /data/3309/mysql.sock -e "show variables like 'server_id'" |
mysql -S /data/3310/mysql.sock -e "show variables like 'server_id'" |
``` |
|
|
4.主从配置 |
|
```bash |
箭头指向谁是主库 |
10.0.0.51:3307 <-----> 10.0.0.52:3307 |
10.0.0.51:3309 ------> 10.0.0.51:3307 |
10.0.0.52:3309 ------> 10.0.0.52:3307 |
|
10.0.0.52:3308 <-----> 10.0.0.51:3308 |
10.0.0.52:3310 -----> 10.0.0.52:3308 |
10.0.0.51:3310 -----> 10.0.0.51:3308 |
``` |
|
|
5.分片规划 |
|
```bash |
shard1: |
Master:10.0.0.51:3307 |
slave1:10.0.0.51:3309 |
Standby Master:10.0.0.52:3307 |
slave2:10.0.0.52:3309 |
shard2: |
Master:10.0.0.52:3308 |
slave1:10.0.0.52:3310 |
Standby Master:10.0.0.51:3308 |
slave2:10.0.0.51:3310 |
``` |
|
|
6.配置操作 |
|
```bash |
# db02 |
mysql -S /data/3307/mysql.sock -e "grant replication slave on . to repl@'10.0.0.%' identified by '123';" |
mysql -S /data/3307/mysql.sock -e "grant all on . to root@'10.0.0.%' identified by '123' with grant option;" |
|
# db01 |
mysql -S /data/3307/mysql.sock -e "CHANGE MASTER TO MASTER_HOST='10.0.0.52', MASTER_PORT=3307, MASTER_AUTO_POSITION=1, MASTER_USER='repl', MASTER_PASSWORD='123';" |
mysql -S /data/3307/mysql.sock -e "start slave;" |
mysql -S /data/3307/mysql.sock -e "show slave status\G" |
|
|
# db02 |
mysql -S /data/3307/mysql.sock -e "CHANGE MASTER TO MASTER_HOST='10.0.0.51', MASTER_PORT=3307, MASTER_AUTO_POSITION=1, MASTER_USER='repl', MASTER_PASSWORD='123';" |
mysql -S /data/3307/mysql.sock -e "start slave;" |
mysql -S /data/3307/mysql.sock -e "show slave status\G" |
|
# db01 |
mysql -S /data/3309/mysql.sock -e "CHANGE MASTER TO MASTER_HOST='10.0.0.51', MASTER_PORT=3307, MASTER_AUTO_POSITION=1, MASTER_USER='repl', MASTER_PASSWORD='123';" |
mysql -S /data/3309/mysql.sock -e "start slave;" |
mysql -S /data/3309/mysql.sock -e "show slave status\G" |
|
# db02 |
mysql -S /data/3309/mysql.sock -e "CHANGE MASTER TO MASTER_HOST='10.0.0.52', MASTER_PORT=3307, MASTER_AUTO_POSITION=1, MASTER_USER='repl', MASTER_PASSWORD='123';" |
mysql -S /data/3309/mysql.sock -e "start slave;" |
mysql -S /data/3309/mysql.sock -e "show slave status\G" |
|
# db01 |
mysql -S /data/3308/mysql.sock -e "grant replication slave on . to repl@'10.0.0.%' identified by '123';" |
mysql -S /data/3308/mysql.sock -e "grant all on . to root@'10.0.0.%' identified by '123' with grant option;" |
|
# db02 |
mysql -S /data/3308/mysql.sock -e "CHANGE MASTER TO MASTER_HOST='10.0.0.51', MASTER_PORT=3308, MASTER_AUTO_POSITION=1, MASTER_USER='repl', MASTER_PASSWORD='123';" |
mysql -S /data/3308/mysql.sock -e "start slave;" |
mysql -S /data/3308/mysql.sock -e "show slave status\G" |
|
# db01 |
mysql -S /data/3308/mysql.sock -e "CHANGE MASTER TO MASTER_HOST='10.0.0.52', MASTER_PORT=3308, MASTER_AUTO_POSITION=1, MASTER_USER='repl', MASTER_PASSWORD='123';" |
mysql -S /data/3308/mysql.sock -e "start slave;" |
mysql -S /data/3308/mysql.sock -e "show slave status\G" |
|
# db02 |
mysql -S /data/3310/mysql.sock -e "CHANGE MASTER TO MASTER_HOST='10.0.0.52', MASTER_PORT=3308, MASTER_AUTO_POSITION=1, MASTER_USER='repl', MASTER_PASSWORD='123';" |
mysql -S /data/3310/mysql.sock -e "start slave;" |
mysql -S /data/3310/mysql.sock -e "show slave status\G" |
|
# db01 |
mysql -S /data/3310/mysql.sock -e "CHANGE MASTER TO MASTER_HOST='10.0.0.51', MASTER_PORT=3308, MASTER_AUTO_POSITION=1, MASTER_USER='repl', MASTER_PASSWORD='123';" |
mysql -S /data/3310/mysql.sock -e "start slave;" |
mysql -S /data/3310/mysql.sock -e "show slave status\G" |
|
Copy |
7.主从状态检测 |
mysql -S /data/3307/mysql.sock -e "show slave status\G" |
mysql -S /data/3308/mysql.sock -e "show slave status\G" |
mysql -S /data/3309/mysql.sock -e "show slave status\G" |
mysql -S /data/3310/mysql.sock -e "show slave status\G" |
注:如果中间出现错误,在每个节点进行执行以下命令 |
mysql -S /data/3307/mysql.sock -e "stop slave; reset slave all;" |
mysql -S /data/3308/mysql.sock -e "stop slave; reset slave all;" |
mysql -S /data/3309/mysql.sock -e "stop slave; reset slave all;" |
mysql -S /data/3310/mysql.sock -e "stop slave; reset slave all;" |
``` |
|
|
## mysql分布式架构介绍 |
|
3.png |
分布式架构介绍 |
|
|
|
## mycat基础应用 |
|
```bash |
|
|
|
range |
取模 |
枚举 |
hash |
时间 |
等等 |
``` |
|
### 主要配置文件介绍 |
|
```basic |
rule.xml |
schema.xml *****,主配置文件 |
server.xml |
log4j2.xml *** ,记录日志有关 |
*.txt |
``` |
|
|
## mycat安装 |
|
### 安装Mycat |
|
```basic |
# 预先安装Java运行环境 |
yum install -y java |
|
# 下载 |
Mycat-server-xxxxx.linux.tar.gz |
http://dl.mycat.io/ |
|
# 解压文件 |
[root@db01 application]# tar xf Mycat-server-1.6.7.1-release-20190627191042-linux.tar.gz |
|
# 软件目录结构 |
ls |
bin catlet conf lib logs version.txt |
|
# 启动和连接 |
配置环境变量 |
vim /etc/profile.d/mycat.sh |
export PATH=/application/mycat/bin:$PATH |
source /etc/profile |
启动 |
mycat start |
连接mycat: |
mysql -uroot -p123456 -h 127.0.0.1 -P8066 |
``` |
|
|
### 数据导入 |
|
```basic |
# 这里仅作为参考,也可以用其他数据 |
[root@db01 ~]# mysql -uroot -p123 |
mysql> source /root/world.sql; |
[root@db07 ~]# mysql -uroot -p123 |
mysql> source /root/world.sql; |
``` |
|
### mycat配置文件浓缩 |
|
```basic |
# mycat配置文件有很多多余的,可以进行浓缩 |
cd /application/mycat/conf |
mv schema.xml schema.xml.bak |
vim schema.xml |
|
|
<mycat:schema xmlns:mycat="http://io.mycat/"> |
|
|
|
|
select user() |
|
|
|
|
</mycat:schema> |
``` |
|
|
### 配置文件介绍 |
|
```xml |
# 前期介绍: |
逻辑库schema: |
|
|
|
数据节点: |
|
|
数据主机: |
|
select user() |
|
|
|
|
|
TESTDB:逻辑库名 |
balance属性 |
负载均衡类型,目前的取值有3种: |
1. balance="0", 不开启读写分离机制,所有读操作都发送到当前可用的writeHost上。 |
2. balance="1",全部的readHost与standby writeHost参与select语句的负载均衡,简单的说, |
当双主双从模式(M1->S1,M2->S2,并且M1与 M2互为主备),正常情况下,M2,S1,S2都参与select语句的负载均衡。 |
3. balance="2",所有读操作都随机的在writeHost、readhost上分发。 |
|
writeType属性 |
负载均衡类型,目前的取值有2种: |
1. writeType="0", 所有写操作发送到配置的第一个writeHost, |
第一个挂了切到还生存的第二个writeHost,重新启动后已切换后的为主,切换记录在配置文件中:dnindex.properties . |
2. writeType=“1”,所有写操作都随机的发送到配置的writeHost,但不推荐使用 |
|
|
switchType属性 |
-1 表示不自动切换 |
1 默认值,自动切换 |
2 基于MySQL主从同步的状态决定是否切换 ,心跳语句为 show slave status |
datahost其他配置 |
|
|
|
maxCon="1000":最大的并发连接数 |
minCon="10" :mycat在启动之后,会在后端节点上自动开启的连接线程 |
|
tempReadHostAvailable="1" |
这个一主一从时(1个writehost,1个readhost时),可以开启这个参数,如果2个writehost,2个readhost时 |
select user() 监测心跳 |
``` |
|
## Mycat使用 |
|
### 读写分离配置 |
|
```xml |
vim schema.xml |
|
|
|
<mycat:schema xmlns:mycat="http://io.mycat/"> |
|
|
|
|
select user() |
|
|
|
|
</mycat:schema> |
|
重启mycat |
mycat restart |
|
读写分离测试 |
mysql -uroot -p -h 127.0.0.1 -P8066 |
show variables like 'server_id'; |
begin; |
show variables like 'server_id'; |
|
总结: |
|
``` |
|
|
### 读写分离和高可用 |
|
```xml |
[root@db01 conf]# mv schema.xml schema.xml.rw |
[root@db01 conf]# vim schema.xml |
|
|
|
<mycat:schema xmlns:mycat="http://io.mycat/"> |
|
|
|
|
select user() |
|
|
|
|
|
|
|
</mycat:schema> |
|
真正的 writehost:负责写操作的writehost |
standby writeHost :和readhost一样,只提供读服务 |
|
当写节点宕机后,后面跟的readhost也不提供服务,这时候standby的writehost就提供写服务, |
后面跟的readhost提供读服务 |
|
测试: |
mysql -uroot -p123456 -h 127.0.0.1 -P 8066 |
show variables like 'server_id'; |
读写分离测试 |
mysql -uroot -p -h 127.0.0.1 -P8066 |
show variables like 'server_id'; |
show variables like 'server_id'; |
show variables like 'server_id'; |
begin; |
show variables like 'server_id'; |
对db01 3307节点进行关闭和启动,测试读写操作 |
``` |
|
|
### 垂直分表 |
|
```xml |
mv schema.xml schema.xml.ha |
vim schema.xml |
|
|
<mycat:schema xmlns:mycat="http://io.mycat/"> |
|
|
|
|
|
select user() |
|
|
|
|
|
|
|
|
select user() |
|
|
|
|
|
|
|
</mycat:schema> |
|
创建测试库和表: |
[root@db01 conf]# mysql -S /data/3307/mysql.sock -e "create database taobao charset utf8;" |
[root@db01 conf]# mysql -S /data/3308/mysql.sock -e "create database taobao charset utf8;" |
[root@db01 conf]# mysql -S /data/3307/mysql.sock -e "use taobao;create table user(id int,name varchar(20))"; |
[root@db01 conf]# mysql -S /data/3308/mysql.sock -e "use taobao;create table order_t(id int,name varchar(20))" |
|
# 测试: |
可登陆到mycat中对表中插入数据,看是否对插入不同表时,数据放入到不同服务器中 |
``` |
|
|
### 分片(水平拆分) |
|
```xml |
1.前期说明 |
分片:对一个"bigtable",比如说t3表 |
|
(1)行数非常多,800w |
(2)访问非常频繁 |
|
分片的目的: |
(1)将大数据量进行分布存储 |
(2)提供均衡的访问路由 |
|
分片策略: |
范围 range 800w 1-400w 400w01-800w |
取模 mod 取余数 |
枚举 |
哈希 hash |
时间 流水 |
|
优化关联查询 |
全局表 |
ER分片 |
|
Copy |
2.配置操作 |
比如说t3表 |
(1)行数非常多,2000w(1-1000w:sh1 1000w01-2000w:sh2) |
(2)访问非常频繁,用户访问较离散 |
mv schema.xml schema.xml.1 |
vim schema.xml |
|
|
|
|
|
vim rule.xml |
|
|
id |
rang-long |
|
<function name="rang-long" |
class="io.mycat.route.function.AutoPartitionByLong"> |
autopartition-long.txt |
|
=================================== |
vim autopartition-long.txt |
0-10=0 |
11-20=1 |
|
创建测试表: |
mysql -S /data/3307/mysql.sock -e "use taobao;create table t3 (id int not null primary key auto_increment,name varchar(20) not null);" |
|
mysql -S /data/3308/mysql.sock -e "use taobao;create table t3 (id int not null primary key auto_increment,name varchar(20) not null);" |
|
测试: |
重启mycat |
mycat restart |
mysql -uroot -p123456 -h 127.0.0.1 -P 8066 |
insert into t3(id,name) values(1,'a'); |
insert into t3(id,name) values(2,'b'); |
insert into t3(id,name) values(3,'c'); |
insert into t3(id,name) values(4,'d'); |
insert into t3(id,name) values(11,'aa'); |
insert into t3(id,name) values(12,'bb'); |
insert into t3(id,name) values(13,'cc'); |
insert into t3(id,name) values(14,'dd'); |
``` |
|
|
### 取模分片(mod-long) |
|
```xml |
取余分片方式:分片键(一个列)与节点数量进行取余,得到余数,将数据写入对应节点 |
vim schema.xml |
vim rule.xml |
2 |
|
准备测试环境 |
|
创建测试表: |
mysql -S /data/3307/mysql.sock -e "use taobao;create table t4 (id int not null primary key auto_increment,name varchar(20) not null);" |
mysql -S /data/3308/mysql.sock -e "use taobao;create table t4 (id int not null primary key auto_increment,name varchar(20) not null);" |
|
重启mycat |
mycat restart |
|
测试: |
mysql -uroot -p123456 -h10.0.0.52 -P8066 |
|
use TESTDB |
insert into t4(id,name) values(1,'a'); |
insert into t4(id,name) values(2,'b'); |
insert into t4(id,name) values(3,'c'); |
insert into t4(id,name) values(4,'d'); |
|
分别登录后端节点查询数据 |
mysql -S /data/3307/mysql.sock |
use taobao |
select * from t4; |
|
mysql -S /data/3308/mysql.sock |
use taobao |
select * from t4; |
``` |
|
|
### 枚举分片 |
|
```xml |
t5 表 |
id name telnum |
1 bj 1212 |
2 sh 22222 |
3 bj 3333 |
4 sh 44444 |
5 bj 5555 |
|
sharding-by-intfile |
vim schema.xml |
|
vim rule.xml |
|
name |
hash-int |
|
|
|
|
partition-hash-int.txt |
1 |
0 |
|
|
partition-hash-int.txt 配置: |
bj=0 |
sh=1 |
DEFAULT_NODE=1 |
columns 标识将要分片的表字段,algorithm 分片函数, 其中分片函数配置中,mapFile标识配置文件名称 |
|
准备测试环境 |
mysql -S /data/3307/mysql.sock -e "use taobao;create table t5 (id int not null primary key auto_increment,name varchar(20) not null);" |
|
mysql -S /data/3308/mysql.sock -e "use taobao;create table t5 (id int not null primary key auto_increment,name varchar(20) not null);" |
重启mycat |
mycat restart |
mysql -uroot -p123456 -h10.0.0.51 -P8066 |
use TESTDB |
insert into t5(id,name) values(1,'bj'); |
insert into t5(id,name) values(2,'sh'); |
insert into t5(id,name) values(3,'bj'); |
insert into t5(id,name) values(4,'sh'); |
insert into t5(id,name) values(5,'tj'); |
|
``` |
|
|
### Mycat全局表 |
|
```xml |
a b c d |
join |
t |
|
select t1.name ,t.x from t1 |
join t |
select t2.name ,t.x from t2 |
join t |
select t3.name ,t.x from t3 |
join t |
|
# 使用场景: |
如果你的业务中有些数据类似于数据字典,比如配置文件的配置, |
常用业务的配置或者数据量不大很少变动的表,这些表往往不是特别大, |
而且大部分的业务场景都会用到,那么这种表适合于Mycat全局表,无须对数据进行切分, |
要在所有的分片上保存一份数据即可,Mycat 在Join操作中,业务表与全局表进行Join聚合会优先选择相同分片内的全局表join, |
避免跨库Join,在进行数据插入操作时,mycat将把数据分发到全局表对应的所有分片执行,在进行数据读取时候将会随机获取一个节点读取数据。 |
|
vim schema.xml |
|
后端数据准备 |
mysql -S /data/3307/mysql.sock |
use taobao |
create table t_area (id int not null primary key auto_increment,name varchar(20) not null); |
|
mysql -S /data/3308/mysql.sock |
use taobao |
create table t_area (id int not null primary key auto_increment,name varchar(20) not null); |
|
重启mycat |
mycat restart |
|
测试: |
mysql -uroot -p123456 -h10.0.0.52 -P8066 |
|
use TESTDB |
insert into t_area(id,name) values(1,'a'); |
insert into t_area(id,name) values(2,'b'); |
insert into t_area(id,name) values(3,'c'); |
insert into t_area(id,name) values(4,'d'); |
``` |
|
|
### E-R分片 |
|
```xml |
A |
join |
B |
为了防止跨分片join,可以使用E-R模式 |
A join B |
on a.xx=b.yy |
join C |
on A.id=C.id |
|
``` |
|
1 |
|
|
|
|
|
|