Clickhouse副本分片以及分布式表机制
一、clickhouse实现二分片双备份案例如下
1、配置metrika.xml
<!--配置分片副本以及zookeeper-->
<remote_servers>
<!-- 2分片2备份,test_ck_cluster 为唯一ID-->
<test_ck_cluster>
<shard>
<internal_replication>true</internal_replication>
<replica>
<host>node1</host>
<port>9000</port>
<user>default</user>
<password>123456</password>
<compression>true</compression>
</replica>
<replica>
<host>node2</host>
<port>9000</port>
<user>default</user>
<password>123456</password>
<compression>true</compression>
</replica>
</shard>
<shard>
<internal_replication>true</internal_replication>
<replica>
<host>node3</host>
<port>9000</port>
<user>default</user>
<password>123456</password>
<compression>true</compression>
</replica>
<replica>
<host>node4</host>
<port>9000</port>
<user>default</user>
<password>123456</password>
<compression>true</compression>
</replica>
</shard>
</test_ck_cluster>
</remote_servers>
<!-- ZooKeeper 配置 -->
<zookeeper>
<node index="1">
<host>node1</host>
<port>2181</port>
</node>
<node index="2">
<host>node2</host>
<port>2181</port>
</node>
<node index="3">
<host>node3</host>
<port>2181</port>
</node>
<session_timeout_ms>30000</session_timeout_ms>
<operation_timeout_ms>10000</operation_timeout_ms>
</zookeeper>
<!--宏变量-->
<macros>
<shard>01</shard>
<replica>rep_1_1</replica>
</macros>
以上宏变量四台机器配置分别为:
node1
<macros>
<shard>01</shard>
<replica>rep_1_1</replica>
</macros>
node2
<macros>
<shard>01</shard>
<replica>rep_1_2</replica>
</macros>
node3
<macros>
<shard>02</shard>
<replica>rep_2_1</replica>
</macros>
node4
<macros>
<shard>02</shard>
<replica>rep_2_2</replica>
</macros>
参数解读
-
通过分布式表的方式实现数据副本时,写入我们配置的分布式表时,分布式表会往shard下的所有replica都写入一份数据.如果我们这里的replicaTest表改成ReplicatedMergeTree引擎,那么我们就只需要分布式表选择一个replica写入即可,由ReplicatedMergeTree完成数据同步,而不需要每个replica都要写入,这项配置需要添加 <internal_replication>true<internal_replication>
<shard> <internal_replication>true</internal_replication> ...... </shard>
-
权重配置
<shard>
<weight>2</weight>
</shard>
weight默认为1,既node1 node2 node3 都为1,那么总的权重为3,每个分片通过分布式表第四个参数sharding_key分配到数据的概率是一样.
至此,最适合生产的分片与副本机制就配置好了
2、数据测试
--创建本地ReplicatedMergeTree表(shard、replica为宏变量中的相应值),单台机器创建后回同步至其它机器
CREATE TABLE default.replicaTest2 on cluster test_ck_cluster(`id` Int32,`name` String) ENGINE = ReplicatedMergeTree('/clickhouse/tables/{shard_name}/replicaTest', '{replica_name}') ORDER BY id
--创建分布式表
create table dis_replicaTest2 on cluster test_ck_cluster(`id` Int32,`name` String) engine = Distributed(test_ck_cluster, default, replicaTest2, rand());
--分布式表插入数据
insert into dis_replicaTest2 values(1,'zhangsan'),(2,'lisi'),(3,'wangwu');
--分别查询分布式表以及本地表
分布式表中包含所有数据
node1:
SELECT *
FROM dis_replicaTest2
┌─id─┬─name─────┐
│ 1 │ zhangsan │
└────┴──────────┘
┌─id─┬─name───┐
│ 2 │ lisi │
│ 3 │ wangwu │
SELECT *
FROM replicaTest2
┌─id─┬─name─────┐
│ 1 │ zhangsan │
└────┴──────────┘
node2:
SELECT *
FROM dis_replicaTest2
┌─id─┬─name─────┐
│ 1 │ zhangsan │
└────┴──────────┘
┌─id─┬─name───┐
│ 2 │ lisi │
│ 3 │ wangwu │
SELECT *
FROM replicaTest2
┌─id─┬─name─────┐
│ 1 │ zhangsan │
└────┴──────────┘
node3:
SELECT *
FROM dis_replicaTest2
┌─id─┬─name─────┐
│ 1 │ zhangsan │
└────┴──────────┘
┌─id─┬─name───┐
│ 2 │ lisi │
│ 3 │ wangwu │
SELECT *
FROM replicaTest2
┌─id─┬─name───┐
│ 2 │ lisi │
│ 3 │ wangwu │
└────┴────────┘
node4:
SELECT *
FROM dis_replicaTest2
┌─id─┬─name─────┐
│ 1 │ zhangsan │
└────┴──────────┘
┌─id─┬─name───┐
│ 2 │ lisi │
│ 3 │ wangwu │
SELECT *
FROM replicaTest2
┌─id─┬─name───┐
│ 2 │ lisi │
│ 3 │ wangwu │
└────┴────────┘
以上可以看出,三条数据分为了两个分片
node1、node2为1分片互为副本存储
┌─id─┬─name─────┐
│ 1 │ zhangsan │
└────┴──────────┘
node3、node4为2分片互为副本存储
┌─id─┬─name───┐
│ 2 │ lisi │
│ 3 │ wangwu │
└────┴────────┘
停止node1、node3服务访问数据能够正常访问分布式表中的所有数据:
SELECT *
FROM dis_replicaTest2
┌─id─┬─name─────┐
│ 1 │ zhangsan │
└────┴──────────┘
┌─id─┬─name───┐
│ 2 │ lisi │
│ 3 │ wangwu │