ClickHouse整理

1、什么是ClickHouse?

ClickHouse是一个用于联机分析(OLAP)的列式数据库管理系统(DBMS)。

在传统的行式数据库(如mysql)系统中,数据按如下顺序存储:

Row WatchID JavaEnable Title GoodEvent EventTime
#0 89354350662 1 Investor Relations 1 2016-05-18 05:19:20
#1 90329509958 0 Contact us 1 2016-05-18 08:10:20
#2 89953706054 1 Mission 1 2016-05-18 07:38:00
#N

处于同一行中的数据总是被物理的存储在一起。

在列式数据库系统中,数据按如下的顺序存储:

Row: #0 #1 #2 #N
WatchID: 89354350662 90329509958 89953706054
JavaEnable: 1 0 1
Title: Investor Relations Contact us Mission
GoodEvent: 1 1 1
EventTime: 2016-05-18 05:19:20 2016-05-18 08:10:20 2016-05-18 07:38:00

这些示例只显示了数据的排列顺序。来自不同列的值被单独存储,来自同一列的数据被存储在一起。

2、为什么是ClickHouse?

我们来看一下OLAP场景的几个关键特征:

  • 绝大多数是读请求
  • 数据以相当大的批次(> 1000行)更新,而不是单行更新;或者根本没有更新。
  • 已添加到数据库的数据不能修改。
  • 对于读取,从数据库中提取相当多的行,但只提取列的一小部分。
  • 宽表,即每个表包含着大量的列
  • 查询相对较少(通常每台服务器每秒查询数百次或更少)
  • 对于简单查询,允许延迟大约50毫秒
  • 列中的数据相对较小:数字和短字符串(例如,每个URL 60个字节)
  • 处理单个查询时需要高吞吐量(每台服务器每秒可达数十亿行)
  • 事务不是必须的
  • 对数据一致性要求低
  • 每个查询有一个大表。除了他以外,其他的都很小。
  • 查询结果明显小于源数据。换句话说,数据经过过滤或聚合,因此结果适合于单个服务器的RAM中

很容易可以看出,OLAP场景与其他通常业务场景(例如,OLTP或K/V)有很大的不同, 因此想要使用OLTP或Key-Value数据库去高效的处理分析查询场景,并不是非常完美的适用方案。

为什么列式数据库在OLAP中具有更大的优势?

如下图所示:

img

行式

Row oriented

列式

Column oriented

1)分析场景中往往需要读大量行但是少数几个列。在行存模式下,数据按行连续存储,所有列的数据都存储在一个block中,不参与计算的列在IO时也要全部读出,读取操作被严重放大。而列存模式下,只需要读取参与计算的列即可,极大的减低了IO开销,加速了查询。

2)同一列中的数据属于同一类型,压缩效果显著。列存往往有着高达十倍甚至更高的压缩比,节省了大量的存储空间,降低了存储成本。

3)更高的压缩比意味着更小的data size,从磁盘中读取相应数据耗时更短。

4)自由的压缩算法选择。不同列的数据具有不同的数据类型,适用的压缩算法也就不尽相同。可以针对不同列类型,选择最合适的压缩算法。

5)高压缩比,意味着同等大小的内存能够存放更多数据,系统cache效果更好。

官方数据显示,通过使用列存,在某些分析场景下,能够获得100倍甚至更高的加速效应。

此外ClickHouse还具有其他优点,

  • 分布式负载均衡、高扩展性:采用分布式多主架构提高并发性能,可以将读请求随机分配到多个节点,均衡读压力(BalancedClickHouseDataSource类)。

  • 数据有序存储:ClickHouse支持在建表时,指定数据按照某些列进行排序。排序后,保证了相同sort key的数据在磁盘上连续存储,且有序摆放。在进行等值、范围查询时,where条件命中的数据都紧密存储在一个或若干个连续的Block中,而不是分散的存储在任意多个Block, 大幅减少需要IO的block数量。另外,连续IO也能够充分利用操作系统page cache的预取能力,减少page fault。

  • 分区:支持PARTITION BY子句,在建表时可以指定按照任意合法表达式进行数据分区操作,比如通过toYYYYMM()将数据按月进行分区、toMonday()将数据按照周几进行分区、对Enum类型的列直接每种取值作为一个分区等。

  • 分片:ClickHouse集群由分片shard组成,每个分片又可以通过副本replication组成,这种分层概念在分布式系统中比较常见。

  • 副本:数据存储副本,提高容灾能力。

  • 数据TTL:在分析场景中,数据的价值随着时间流逝而不断降低,多数业务出于成本考虑只会保留最近几个月的数据,ClickHouse通过TTL提供了数据生命周期管理的能力。

    ClickHouse支持几种不同粒度的TTL:

    1) 列级别TTL:当一列中的部分数据过期后,会被替换成默认值;当全列数据都过期后,会删除该列。

    2)行级别TTL:当某一行过期后,会直接删除该行。

    3)分区级别TTL:当分区过期后,会直接删除该分区。

  • 高吞吐写入能力:ClickHouse采用类LSM Tree(Log Structured Merge Tree,是一种分层,有序,面向磁盘的数据结构,其核心思想是充分利用了磁盘批量顺序写要远比随机写性能高出很多)的结构,数据写入后定期在后台Compaction。通过类LSM tree的结构,ClickHouse在数据导入时全部是顺序append写,写入后数据段不可更改,在后台compaction时也是多个段merge sort后顺序写回磁盘。顺序写的特性,充分利用了磁盘的吞吐能力,即便在HDD上也有着优异的写入性能。

    官方公开benchmark测试显示能够达到50MB-200MB/s的写入吞吐能力,按照每行100Byte估算,大约相当于50W-200W条/s的写入速度。

  • 有限支持delete、update:在分析场景中,删除、更新操作并不是核心需求。ClickHouse没有直接支持delete、update操作,而是变相支持了mutation操作,语法为alter table delete where filter_expr,alter table update col=val where filter_expr。目前主要限制为删除、更新操作为异步操作,需要后台compation之后才能生效。

  • 多核并行:ClickHouse将数据划分为多个partition,每个partition再进一步划分为多个index granularity,然后通过多个CPU核心分别处理其中的一部分来实现并行数据处理。

    在这种设计下,单条Query就能利用整机所有CPU。极致的并行处理能力,极大的降低了查询延时。

  • 分布式计算:除了优秀的单机并行处理能力,ClickHouse还提供了可线性拓展的分布式计算能力。ClickHouse会自动将查询拆解为多个task下发到集群中,然后进行多机并行处理,最后把结果汇聚到一起。

  • 向量引擎:ClickHouse实现了向量引擎(vectorized execution engine):

    • 通过CPU寄存器访问存放在内存中的待计算数据,速度是从内存访问的300倍,是从磁盘中访问的3000万倍。

    • 向量化执行方式:利用CPU的SIMD指令,即用单条指令操作多条数据,采用数据级并行的方式以提高性能。

      比如计算1000次的a[i] = b[i]+c[i]
      普通计算:循环发出1000次加法指令。
      数据级并行计算:b[i]和c[i]是两个天然的向量,因此只需要执行一次向量加法即可,即只下发一次加法指令,以同步方式,在同一时间对存储着的b[1]、b[2]、b[3]······b[1000],c[1]、c[2]、c[3]······c[1000]数据集执行同一条指令。
      
      SIMD全称Single Instruction Multiple Data,单指令多数据流,能够复制多个操作数,并把它们打包在大型寄存器的一组指令集。
      
  • 动态代码:ClickHouse实现了Expression级别的runtime codegen,动态地根据当前SQL直接生成代码,然后编译执行。

  • 分布式计算:除了优秀的单机并行处理能力,ClickHouse还提供了可线性拓展的分布式计算能力。ClickHouse会自动将查询拆解为多个task下发到集群中,然后进行多机并行处理,最后把结果汇聚到一起。

    注意,高性能会带来高要求,因为大量适用并行计算,大量使用数据压缩,ClickHouse对于CPU资源是非常敏感的。当集群中单个节点的CPU占用到50%就会发生ClickHouse性能抖动,到了70%,ClickHouse的大部分查询都会卡住或者失效,所以需要密切监控CPU占用。
    

可以简单看一下ClickHouse与其他存储数据库的性能对比:https://ClickHouse.com/benchmark/dbms/

3、怎么用ClickHouse?

安装过程省略。

3.1、配置

clickhouse支持多配置文件管理,主配置文件是/etc/clickhouse-server/config.xml。
在这里插入图片描述
config.xml可以指定单独的配置文件用于配置用户设置、配置文件及配额,默认值是users.xml,用users_config元素指定相对路径也是可以的,或者忽略该元素,直接在config.xml中设置用户属性也可。
在这里插入图片描述
如果集群情况复杂,可以在config.d和users.d文件夹下创建单独的配置文件,然后在主配置文件中通过include_from元素读取这些独立配置。(默认情况下,替换文件的路径为/etc/metrika.xml,也是目前我们使用的方式。这使得我们不需声明文件路径,即可在主配置中的具有incl属性的元素中使用该配置。)

举例:
在这里插入图片描述
在这里插入图片描述
我们在/etc/metrika.xml中配置了zookeeper-servers,macros元素,在/etc/clickhouse-server/config.xml中用incl引入即可使用这项配置。

服务器跟踪配置文件中的修改,动态重新加载用户和集群设置,因此可以在不重启服务器的情况下修改集群、用户设置。

目前我们使用的集群配置主要是配置端口、zk、密码还有内存以及分布式复制表相关的配置,其余性能方面的配置基本保持默认。当然也有一些

服务器支持的配置清单:https://clickhouse.com/docs/zh/operations/server-configuration-parameters/settings/

用户配置清单:https://clickhouse.com/docs/zh/operations/settings/settings-users/

3.2、日志

3.2.1、服务日志

clickhouse服务默认的日志存储位置是/var/log/clickhouse-server/目录。

该路径可以通过修改config.xml配置变更:
在这里插入图片描述

3.2.2、查询日志

clickhouse也会记录查询情况,记录在system.query_log中,可以用来监控一些慢sql。

在这里插入图片描述

3.3、SQL

ClickHouse使用一种声明式的SQL语言,基本语法跟ANSI SQL语法相同。ANSI兼容性清单:https://clickhouse.com/docs/zh/sql-reference/ansi/

3.3.1、建表

ClickHouse的建表语句比较特别,不同的引擎(3.4内容)对应的建表语句模板也不同,需要特别注意,下面是两个例子:

-- 例子1:
CREATE TABLE table_name
(
    EventDate DateTime,
    CounterID UInt32,
    UserID UInt32
) ENGINE = ReplicatedMergeTree('/clickhouse/tables/{layer}-{shard}/table_name', '{replica}')
PARTITION BY toYYYYMM(EventDate)
ORDER BY (CounterID, EventDate, intHash32(UserID))
SAMPLE BY intHash32(UserID)

-- 例子2:
CREATE TABLE IF NOT EXISTS test.member_info_local ON CLUSTER '{cluster}' 
(
    `id` bigint comment 'id',
    `member_id` bigint comment '用户id',
    `level` String comment '用户等级'`create_time` Datetime comment '生成时间'
)
ENGINE = ReplacingMergeTree
  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值