clickhouse相关概念

ClickHouse 核心概念精讲:分片、副本、表与引擎

一、 分片(Shard)与副本(Replica)的概念

在 ClickHouse 中,分片副本是实现分布式存储和高可用性的两大核心机制。

1. 分片(Shard)—— 解决“存不下”和“算得慢”的问题(水平扩展)

分片就是把一张大表的数据拆分成多份,分散存储在不同的服务器(节点)上。

  • 作用
    • 打破单机存储瓶颈:单台机器存不下海量数据,分散后就能存下。
    • 加速查询(并行计算):执行查询时,ClickHouse 会把查询分发给各台机器同时执行,然后合并结果。
  • 缺点:如果没有副本,某台机器宕机将导致该分片的数据丢失。

2. 副本(Replica)—— 解决“怕丢失”和“服务宕机”的问题(高可用)

副本就是对同一份数据做多份完全相同的拷贝,存储在不同的服务器上。

  • 作用
    • 高可用和容灾:当其中一台机器宕机时,另一台存有相同副本的机器可以无缝接管,保证数据不丢、服务不中断。
    • 分担读压力:查询请求可以分摊到多个副本节点上,提升系统的并发读取能力。

二、 本地表(Local Table)与分布式表(Distributed Table)

1. 核心概念

  • 本地表 (Local Table)真正存储数据的表。在一个分片集群中,某个节点的本地表只保存该分片对应的那一部分数据
  • 分布式表 (Distributed Table):一个逻辑上的“视图”或代理层,本身不存储任何实际数据。它像一个路由器,帮你把请求分发给各个分片的本地表。

2. 读写差异与最佳实践

写入数据(推荐:写本地表)

  • 写分布式表(不推荐):数据先写到某个节点,该节点再根据分片键把数据拆分并跨网络发送给其他节点。容易造成单点瓶颈、放大延迟,且出错时难以保证数据一致性。
  • 写本地表(最佳实践):由客户端(如 Flink/Spark)自己完成数据分片计算,然后建立多个连接,直接批量写入各个节点的本地表。性能最高,且容易控制失败重试。

读取数据(推荐:读分布式表)

  • 读本地表:只能查到当前节点(当前分片)上的部分数据,常用于排查数据倾斜或核对数据。
  • 读分布式表(标准做法):像查单机库一样发起查询。接收请求的节点(Initiator)会将查询下推到各分片并行计算,最后在 Initiator 节点汇总并返回完整结果。

3. 分片、本地表、分布式表的数量关系

假设一个 3 分片、2 副本 的集群(共 6 台机器用来存数据):

  • 分片(Shard)数:3 个(逻辑概念,完整数据被切成了 3 份)。
  • 本地表(Local Table)数:6 张(物理存在,每台机器各 1 张,其中每 2 张存着相同的分片数据互为副本)。
  • 分布式表(Distributed Table)数:通常也是 6 张(为了查询时的负载均衡,每台存放了本地表的机器上都会建 1 张分布式表作为查询入口)。

三、 常用的 MergeTree 家族引擎与数据更新

表引擎(Table Engine) 决定了数据如何存储和查询。ClickHouse 最核心的是 MergeTree(合并树)家族

1. 常用引擎介绍

  1. MergeTree:性能最强悍、最基础的引擎。完全不支持数据更新和删除
  2. ReplicatedMergeTree:分布式高可用集群的标配。在 MergeTree 基础上,借助 ZooKeeper 实现了节点间的数据自动同步(副本复制)。
  3. CollapsingMergeTree:通过插入 Sign=-1 的“折叠”数据来抵消旧数据,以此实现更新/删除。对业务侵入性较强。
  4. ReplacingMergeTree:最优雅、最常用的实现数据更新去重(Upsert)的方案。

2. ReplacingMergeTree 深度解析(支持更新的秘密)

在 ClickHouse 这种柱状数据库中,原地修改文件代价极高。因此 ReplacingMergeTree 采用的是“延迟更新(假更新)”机制。

工作原理:

  1. 更新即追加:当业务需要更新数据时,只需插入一条主键相同、但版本号(如 update_time)更新的新数据。新旧数据会同时存在于磁盘上。
  2. 后台异步合并(Merge):当 ClickHouse 在后台触发文件块合并时,它会发现这两条主键相同的数据,然后物理删除旧数据,只保留版本号最新的那一条

查询时的避坑指南(关键!):

因为后台合并是异步的,所以在合并发生之前直接查询,大概率会查出重复数据(旧快照和新快照都在)。

  • 错误解法:频繁使用 OPTIMIZE TABLE ... FINAL 手动强制合并,这会导致 CPU 和 IO 暴涨,直接压垮集群。
  • 正确解法:在查询语句加上 FINAL 关键字(如 SELECT * FROM table_name FINAL)。ClickHouse 会在查询的瞬间,在内存里动态帮你把重复数据去重,只返回最新结果。
posted on 2026-04-17 15:46  茶倌  阅读(8)  评论(0)    收藏  举报