ClickHouse - 多卷存储扩大存储容量(生产环境必备)_DataFlow范式的博客-CSDN博客


本站和网页 https://blog.csdn.net/jiangshouzhuang/article/details/103650360 的作者无关,不对其内容负责。快照谨为网络故障时之索引,不代表被搜索网站的即时页面。

ClickHouse - 多卷存储扩大存储容量(生产环境必备)_DataFlow范式的博客-CSDN博客
ClickHouse - 多卷存储扩大存储容量(生产环境必备)
DataFlow范式
于 2019-12-21 17:59:42 发布
8668
收藏
33
版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
本文链接:https://blog.csdn.net/jiangshouzhuang/article/details/103650360
版权
笔者最近工作有点忙,加上培训较多,近期文章更新慢了一拍。不过,今天为 ClickHouse 的爱好者带来一篇非常不错的文章,部分内容来自 Altinity,以及笔者补充和整理而成。
长期使用 ClickHouse 的用户都知道,每个 ClickHouse 服务都是单个进程,可访问位于单个存储设备上的数据。该设计提供了操作简便性,这是一个很大的优点,但将用户使用的所有数据限制在单一存储类中。缺点是难以选择成本/性能,特别是对于大型集群。
在 2019 年期间,Altinity 和 ClickHouse 社区一直在努力使 ClickHouse 表能够将存储划分为包含多个设备的卷,并在它们之间自动移动数据。从 19.15 版本开始,ClickHouse 开始实现多卷存储的功能。它具有多种用途,其中最重要的用途是将热数据和冷数据存储在不同类型的存储中。这种配置被称为分层存储,正确使用它可以极大地提高 ClickHouse 服务的经济性。
在接下来的文章中,笔者将介绍 ClickHouse 的多卷存储并展示其具体的工作方式。为了提供生产环境实战的参考,笔者将演示如何实现分层存储,并说明其他用途。
多卷存储的目的
假设有一个 ClickHouse 集群来处理保留30天数据的服务日志。用户从当天开始对数据进行 95% 的交互式查询。其余 5% 是用于趋势分析和机器学习的长期运行的批查询。因此,这里的选择是:使用快速的 SSD 存储在 3% 的数据上快速运行常见查询,或者使用便宜的 HDD 来满足其他 97% 的数据。快速的或便宜的,而不是两者兼而有之。
幸运的是,ClickHouse 提供了一个更好的方案:分层存储。
该想法是将新数据存储在 NVMe SSD 等快速存储中,然后再将其移动到速度较慢的存储(例如 HDD)中。这不仅节省了存储空间,而且通常可以减少服务器的总数而不牺牲性能,这是效率的双赢,可以将硬件成本降低多达80%。毫不奇怪,多年来分层存储一直是最重要的功能要求。
在多卷存储功能实现之前,用户借助 Merge 引擎和部分手动操作将一个逻辑表的数据存储在多个物理磁盘上。这种方法允许用户解决多层存储的问题,但这是一个非常不方便的解决方法。
ClickHouse 多卷存储使分层存储成为可能,甚至非常方便。我们可以将表数据存储在多个设备上,分为多个卷,甚至可以自动跨卷移动数据。多卷存储也解决了其他问题,例如,多卷存储还提供了一种简单的机制,可以通过附加新设备来扩展服务器容量。
ClickHouse 多卷存储架构
在进入示例之前,笔者先介绍一下 ClickHouse 中多卷存储的工作原理。一图胜千言,如图所示。 
该方案看似复杂,但实际上非常简单。每个 MergeTree 表都与一个存储策略( storage_policy)相关联。策略只是用于编写 MergeTree 表数据的规则,将磁盘分为一个或多个卷。它们还定义了每个卷中磁盘的写顺序,以及有多个卷时数据在卷之间的移动方式。
存储策略与旧表向后兼容。ClickHouse 始终有一个名为 default 的磁盘,该磁盘指向 config.xml 中的数据目录路径。还有一个相应的策略称为 default。如果 MergeTree 表没有存储策略,则 ClickHouse 将使用默认策略并写入默认磁盘。
接下来,笔者将通过示例来进行说明。
服务器设置
接下来,我们将多卷安装在具有多个块设备的 ClickHouse 服务器上。
首先,需要一台具有多个硬盘驱动器的服务器。对于此特定测试,我在 Ubuntu 18.04 (笔者生产环境为 CentOS)上连接了三个附加存储卷:
2 x SSD 400GB1 x HDD 1000GB
可以使用方便的 lsblk 命令查看额外的块设备。
$ lsblk
NAME MAJ:MIN RM SIZE RO TYPE MOUNTPOINT
...
nvme0n1 259:0 0 400G 0 disk
nvme2n1 259:1 0 10G 0 disk
└─nvme2n1p1 259:3 0 10G 0 part /
nvme1n1 259:2 0 1000G 0 disk
nvme3n1 259:4 0 400G 0 disk
笔者生产环境磁盘数超过4块,官方建议使用 RAID-6 或 RAID-50,但是综合考虑实际情况笔者使用 RAID5。
使用 ext4 文件系统格式化磁盘并挂载它们。
sudo mkfs -t ext4 /dev/nvme0n1
sudo mkfs -t ext4 /dev/nvme1n1
sudo mkfs -t ext4 /dev/nvme3n1
sudo mkdir /mnt/ebs_gp2_1
sudo mkdir /mnt/ebs_gp2_2
sudo mkdir /mnt/ebs_sc1_1
sudo mount -o noatime,nobarrier /dev/nvme0n1 /mnt/ebs_gp2_1
sudo mount -o noatime,nobarrier /dev/nvme3n1 /mnt/ebs_gp2_2
sudo mount -o noatime,nobarrier /dev/nvme1n1 /mnt/ebs_sc1_1
为了使本示例简单起见,我们将跳过将卷添加到 fstab 的操作,因此重新启动后将不会自动挂载它们。
现在,我们来安装 ClickHouse。当前,笔者建议您使用最新的 19.17 稳定版本进行测试。(也可以使用更高版本,介于原作者实验,本文中的示例基于版本 19.16.3.6)
sudo apt-get install dirmngr
sudo apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv E0C56BD4
echo "deb http://repo.yandex.ru/clickhouse/deb/stable/ main/" | sudo tee /etc/apt/sources.list.d/clickhouse.list
sudo apt-get update
sudo apt-get install -y clickhouse-server clickhouse-client
sudo systemctl start clickhouse-server
sudo systemctl status clickhouse-server
clickhouse-client --query='SELECT version()'
19.16.3.6
配置 ClickHouse 存储磁盘
安装完成后,ClickHouse 会使用默认配置,并将数据默认存储在 /var/lib/clickhouse/data 文件夹的根分区中。为了验证默认存储位置,我们可以使用 system.disks 表,该表显示 ClickHouse 使用的磁盘:
SELECT
name,
path,
formatReadableSize(free_space) AS free,
formatReadableSize(total_space) AS total,
formatReadableSize(keep_free_space) AS reserved
FROM system.disks
┌─name────┬─path─────────────────┬─free─────┬─total────┬─reserved─┐
│ default │ /var/lib/clickhouse/ │ 7.49 GiB │ 9.63 GiB │ 0.00 B │
└─────────┴──────────────────────┴──────────┴──────────┴──────────┘
由于我们有可用的额外磁盘,因此现在配置 ClickHouse 并使用它们。我们将以下配置添加到 /etc/clickhouse-server/config.d/storage.xml。
注意:
将存储配置放在 config.d 中,这可以防止它在升级时被删除。
<yandex>
<storage_configuration>
<disks>
<!--
default disk is special, it always
exists even if not explicitly
configured here, but you can't change
it's path here (you should use <path>
on top level config instead)
-->
<default>
<!--
You can reserve some amount of free space
on any disk (including default) by adding
keep_free_space_bytes tag
-->
<keep_free_space_bytes>1024</keep_free_space_bytes>
</default>
<ebs_gp2_1>
<!--
disk path must end with a slash,
folder should be writable for clickhouse user
-->
<path>/mnt/ebs_gp2_1/</path>
</ebs_gp2_1>
<ebs_gp2_2>
<path>/mnt/ebs_gp2_2/</path>
</ebs_gp2_2>
<ebs_sc1_1>
<path>/mnt/ebs_sc1_1/</path>
</ebs_sc1_1>
</disks>
</storage_configuration>
</yandex>
要应用更改,必须重新启动 ClickHouse。每次我们更改存储配置时都需要这样做。
$ sudo systemctl restart clickhouse-server
$ sudo systemctl status clickhouse-server
● clickhouse-server.service - ClickHouse Server (analytic DBMS for big data)
Loaded: loaded (/etc/systemd/system/clickhouse-server.service; enabled; vendor preset: enabled)
Active: activating (auto-restart) (Result: exit-code) since Mon 2019-11-04 15:02:06 UTC; 4s ago
Process: 3146 ExecStart=/usr/bin/clickhouse-server --config=/etc/clickhouse-server/config.xml --pid-file=/run/clickhouse-server/clickhouse-server.pid (code=exited, status=70)
Main PID: 3146 (code=exited, status=70)
糟糕,ClickHouse 无法启动,不过不要紧张,让我们检查一下日志:
sudo tail -n 10 /var/log/clickhouse-server/clickhouse-server.err.log
...
<Error> Application: DB::Exception: There is no RW access to disk ebs_gp2_1
错误提示很明显,就是忘记了将存储文件夹的权限授予 ClickHouse 用户。修复一下权限问题:
sudo chown clickhouse:clickhouse -R /mnt/ebs_gp2_1 /mnt/ebs_gp2_2 /mnt/ebs_sc1_1
sudo systemctl restart clickhouse-server
sudo systemctl status clickhouse-server
再次重启后,查看 ClickHouse 服务状态。
sudo systemctl status clickhouse-server
● clickhouse-server.service - ClickHouse Server (analytic DBMS for big data)
Loaded: loaded (/etc/systemd/system/clickhouse-server.service; enabled; vendor preset: enabled)
Active: active (running) since Mon 2019-11-04 15:10:55 UTC; 2s ago
Main PID: 3714 (clickhouse-serv)
Tasks: 40 (limit: 4633)
CGroup: /system.slice/clickhouse-server.service
└─3714 /usr/bin/clickhouse-server --config=/etc/clickhouse-server/config.xml --pid-file=/run/clickhouse-server/clickhouse-server.pid
... systemd[1]: Started ClickHouse Server (analytic DBMS for big data).
好的,现在 ClickHouse 正在运行,我们可以看到所有的存储磁盘:
SELECT
name,
path,
formatReadableSize(free_space) AS free,
formatReadableSize(total_space) AS total,
formatReadableSize(keep_free_space) AS reserved
FROM system.disks
┌─name──────┬─path─────────────────┬─free───────┬─total──────┬─reserved─┐
│ default │ /var/lib/clickhouse/ │ 7.49 GiB │ 9.63 GiB │ 1.00 KiB │
│ ebs_gp2_1 │ /mnt/ebs_gp2_1/ │ 366.06 GiB │ 392.72 GiB │ 0.00 B │
│ ebs_gp2_2 │ /mnt/ebs_gp2_2/ │ 372.64 GiB │ 392.72 GiB │ 0.00 B │
│ ebs_sc1_1 │ /mnt/ebs_sc1_1/ │ 933.21 GiB │ 983.30 GiB │ 0.00 B │
└───────────┴──────────────────────┴────────────┴────────────┴──────────┘
此时,我们有4个可用磁盘用于存储数据。
接下来笔者将正式介绍 ClickHouse 存储策略,并从简单配置扩展到复杂配置,这将帮助我们达到配置分层存储的目标。
存储策略
上面,笔者已经讲解了如何配置多个磁盘。但是,为了使用多卷存储还有更多工作要做。此时,表 MergeTree 数据仍存储在默认磁盘上(即 /var/lib/clickhouse/)。可以从 system.tables 查询信息:
CREATE TABLE sample1 (id UInt64) Engine=MergeTree ORDER BY id;
INSERT INTO sample1 SELECT * FROM numbers(1000000);
SELECT name, data_paths FROM system.tables WHERE name = 'sample1'\G
Row 1:
──────
name: sample1
data_paths: ['/var/lib/clickhouse/data/default/sample1/']
SELECT name, disk_name, path FROM system.parts
WHERE (table = 'sample1') AND active\G
Row 1:
──────
name: all_1_1_0
disk_name: default
path: /var/lib/clickhouse/data/default/sample1/all_1_1_0/
在不同磁盘上存储数据的规则由存储策略设置。在新安装或升级的 ClickHouse 服务中,有一个存储策略,称为 default,表示所有数据都应放置在默认磁盘上。此策略可确保对现有表的向后兼容性。我们可以通过从 system.storage_policies 表中查询来查看定义,该表用于帮助管理分层存储。
SELECT policy_name, volume_name, disks
FROM system.storage_policies
┌─policy_name────┬─volume_name─────────┬─disks─────────────────────┐
│ default │ default │ ['default'] │
└────────────────┴─────────────────────┴───────────────────────────┘
单磁盘策略
笔者将带大家从一个非常简单的示例开始,我们将引入名称为 ebs_gp2_1_only 的存储策略,该策略将所有数据存储在包含 ebs_gp2_1 磁盘的 ebs_gp2_1_volume 上。
我们已经所有与存储相关的配置放在文件 /etc/clickhouse-server/config.d/storage.xml 中。
以下示例显示了之前创建的磁盘配置:
<yandex>
<storage_configuration>
<disks>
<!--
default disk is special, it always
exists even if not explicitly
configured here, but you can't change
it's path here (you should use <path>
on top level config instead)
-->
<default>
<!--
You can reserve some amount of free space
on any disk (including default) by adding
keep_free_space_bytes tag
-->
<keep_free_space_bytes>1024</keep_free_space_bytes>
</default>
<ebs_gp2_1>
<!--
disk path must end with a slash,
folder should be writable for clickhouse user
-->
<path>/mnt/ebs_gp2_1/</path>
</ebs_gp2_1>
<ebs_gp2_2>
<path>/mnt/ebs_gp2_2/</path>
</ebs_gp2_2>
<ebs_sc1_1>
<path>/mnt/ebs_sc1_1/</path>
</ebs_sc1_1>
</disks>
<policies>
<ebs_gp2_1_only> <!-- name for new storage policy -->
<volumes>
<ebs_gp2_1_volume> <!-- name of volume -->
<!--
we have only one disk in that volume
and we reference here the name of disk
as configured above in <disks> p
-->
<disk>ebs_gp2_1</disk>
</ebs_gp2_1_volume>
</volumes>
</ebs_gp2_1_only>
</policies>
</storage_configuration>
</yandex>
重新启动 ClickHouse 以应用配置更改并检查配置的新策略是否可见:
SELECT policy_name, volume_name, disks
FROM system.storage_policies
┌─policy_name────┬─volume_name─────────┬─disks─────────────────────┐
│ default │ default │ ['default'] │
│ ebs_gp2_1_only │ ebs_gp2_1_volume │ ['ebs_gp2_1'] │
└────────────────┴─────────────────────┴───────────────────────────┘
太酷了,那么我们现在如何使用它们呢?
其实针对用户来说,使用起来很简单,只需在新表上添加即可:
SETTINGS storage_policy = 'ebs_gp2_1_only'
创建表的完整示例如下:
CREATE TABLE sample2 (id UInt64) Engine=MergeTree
ORDER BY id SETTINGS storage_policy = 'ebs_gp2_1_only';
INSERT INTO sample2 SELECT * FROM numbers(1000000);
现在我们可以看到该表具有存储策略 ebs_gp2_1_only,并且所有 parts 都存储在 /mnt/ebs_gp2_1 上:
SELECT name, data_paths, metadata_path, storage_policy
FROM system.tables
WHERE name LIKE 'sample%'
Row 1:
──────
name: sample1
data_paths: ['/var/lib/clickhouse/data/default/sample1/']
metadata_path: /var/lib/clickhouse/metadata/default/sample1.sql
storage_policy: default
Row 2:
──────
name: sample2
data_paths: ['/mnt/ebs_gp2_1/data/default/sample2/']
metadata_path: /var/lib/clickhouse/metadata/default/sample2.sql
Storage_policy: ebs_gp2_1_only
根据查询 system.tables 显示的结果,可以看到两个表具有不同的数据路径和不同的存储策略。
请注意,表元数据保留在默认磁盘上。
我们还可以检查每个 part 的存储位置:
SELECT table, disk_name, path
FROM system.parts
WHERE table LIKE 'sample%'
Row 1:
──────
table: sample1
disk_name: default
path: /var/lib/clickhouse/data/default/sample1/all_1_1_0/
Row 2:
──────
table: sample2
disk_name: ebs_gp2_1
path: /mnt/ebs_gp2_1/data/default/sample2/all_1_1_0/
到此,我们知道了如何在另一个磁盘上存储表。
当然,无论源表和目标表位于何处,都可以使用常规的 INSERT ... SELECT 将数据从一个表复制到另一表。
JBOD:具有多个磁盘的单层卷
在前面的示例中,我们将数据存储在一个磁盘上。那么我们如何将数据存储在多个磁盘上?
我们可以使用存储策略在一个卷中将两个或多个磁盘分组。当我们这样做时,数据将以轮循(round-robin)方式在磁盘之间分配:
每次 insert(或 merge)都会在卷中的下一个磁盘上创建 part。parts 的一半存储在一个磁盘上,其余部分存储在另一个磁盘上。这个概念通常称为 JBOD,它是 “Just a Bunch of Disks” 的缩写。
JBOD 卷组织提供了以下好处:
1. 通过附加磁盘来扩展存储的简便方法,这比迁移到 RAID 简单得多。
2. 在某些情况下(例如,当多个线程并行使用不同的磁盘时),读/写速度会提高。
3. 由于每个磁盘上的 parts 数较少,因此表加载速度更快。
请注意,当使用 JBOD 时,一个磁盘的故障将导致数据丢失。添加更多磁盘会增加丢失至少一些数据的机会。当要求系统有容错能力时,请始终使用复制方式。
现在,让我们尝试将两个 SSD 磁盘连接到一个 JBOD 卷中。我们将以下存储策略添加到 storage.xml 文件中:
<ebs_gp2_jbod> > <!-- name for new storage policy -->
<volumes>
<ebs_gp2_jbod_volume> <!-- name of volume -->
<!--
the order of listing disks inside
volume defines round-robin sequence
-->
<disk>ebs_gp2_1</disk>
<disk>ebs_gp2_2</disk>
</ebs_gp2_jbod_volume>
</volumes>
</ebs_gp2_jbod>
我们重新启动 ClickHouse 并检查 system.storage_policies 中的存储策略。
SELECT policy_name, volume_name, disks
FROM system.storage_policies
┌─policy_name────┬─volume_name─────────┬─disks─────────────────────┐
│ default │ default │ ['default'] │
│ ebs_gp2_1_only │ ebs_gp2_1_volume │ ['ebs_gp2_1'] │
│ ebs_gp2_jbod │ ebs_gp2_jbod_volume │ ['ebs_gp2_1','ebs_gp2_2'] │
└────────────────┴─────────────────────┴───────────────────────────┘
让我们使用新的策略创建另外一张表:
CREATE TABLE sample3 (id UInt64) Engine=MergeTree ORDER BY id SETTINGS storage_policy = 'ebs_gp2_jbod';
SELECT
name,
data_paths,
metadata_path,
storage_policy
FROM system.tables
WHERE name = 'sample3'
Row 1:
──────
name: sample3
data_paths: ['/mnt/ebs_gp2_1/data/default/sample3/','/mnt/ebs_gp2_2/data/default/sample3/']
metadata_path: /var/lib/clickhouse/metadata/default/sample3.sql
storage_policy: ebs_gp2_jbod
接着,我们可以添加数据并检查 parts 存储的位置:
insert into sample3 select * from numbers(1000000);
insert into sample3 select * from numbers(1000000);
insert into sample3 select * from numbers(1000000);
insert into sample3 select * from numbers(1000000);
select name, disk_name, path from system.parts where table = 'sample3';
┌─name──────┬─disk_name─┬─path───────────────────────────────────────────┐
│ all_1_1_0 │ ebs_gp2_1 │ /mnt/ebs_gp2_1/data/default/sample3/all_1_1_0/ │
│ all_2_2_0 │ ebs_gp2_2 │ /mnt/ebs_gp2_2/data/default/sample3/all_2_2_0/ │
│ all_3_3_0 │ ebs_gp2_1 │ /mnt/ebs_gp2_1/data/default/sample3/all_3_3_0/ │
│ all_4_4_0 │ ebs_gp2_2 │ /mnt/ebs_gp2_2/data/default/sample3/all_4_4_0/ │
└───────────┴───────────┴────────────────────────────────────────────────┘
后台合并可以从不同磁盘上的 parts 收集数据,并将合并完成的新的较大 part 放在该卷的其中一个磁盘上(根据轮询算法)。我们可以通过运行 OPTIMIZE TABLE 强制合并来查看此示例中的行为。
OPTIMIZE TABLE sample3
Ok.
0 rows in set. Elapsed: 0.240 sec.
SELECT
name,
disk_name,
path
FROM system.parts
WHERE (table = 'sample3') AND active
┌─name──────┬─disk_name─┬─path───────────────────────────────────────────┐
│ all_1_4_1 │ ebs_gp2_1 │ /mnt/ebs_gp2_1/data/default/sample3/all_1_4_1/ │
└───────────┴───────────┴────────────────────────────────────────────────┘
后台合并往往会随着时间的流逝创建越来越大的 parts,从而将每个生成的 part 移至其中一个磁盘。因此,我们的存储策略不能保证数据将均匀地分布在磁盘上,它也不能保证 JBOD 上的 I/O 吞吐量要比最慢的磁盘上的 I/O 吞吐量更好。为了获得这样的保证,应该改用 RAID。
使用 JBOD 存储策略的最明显原因是通过添加其他存储而不移动现有数据来增加 ClickHouse 服务的容量。
多层存储:具有不同优先级的卷
现在,我们准备研究多卷功能最有趣的用例,即分层存储的配置。
让我们回到本篇文章开始讨论的问题。我们有新插入的数据,这些数据被认为是热数据,并且经常访问,这需要快速但昂贵的存储。接下来,我们有冷数据。在批处理查询之外很少访问它,并且查询性能不是一个很大的考虑因素。冷数据可以存储在速度更慢、价格更低的存储上。
要在存储策略中实施此操作,我们需要定义以下内容:
在初始插入时新数据应该存储在哪里何时将它移到较慢的存储空间
ClickHouse 19.15 版本使用基于 part 大小的启发式方法来确定何时在卷之间移动 part。在 ClickHouse 中,part 大小和 part 寿命通常是紧密相关的。MergeTree 引擎一直在进行后台合并,将新插入的数据和小的 part 随时间合并为越来越大的 part。这意味着大的 part 会在几次合并后出现,因此通常情况下,part 越大就越老。
注意:
我们还在研究另一种 age-based 的方法来跨层移动数据。它扩展了 TTL 机制,该机制目前用于删除 MergeTree 中的旧表行,例如30天之后。当该功能完成时,我们将能够使用 TTL 表达式在卷之间移动数据。
现在,使用以下存储策略配置分层存储。与之前操作一样,我们需要重新启动才能生效。
<ebs_hot_and_cold>
<volumes>
<hot_volume>
<disk>ebs_gp2_2</disk>
<!--
that volume allowed to store only parts which
size is less or equal 200Mb
-->
<max_data_part_size_bytes>200000000</max_data_part_size_bytes>
</hot_volume>
<cold_volume>
<disk>ebs_sc1_1</disk>
<!--
that volume will be used only when the first
has no space of if part size doesn't satisfy
the max_data_part_size_bytes requirement of the
first volume, i.e. if part size is greater
than 200Mb
-->
</cold_volume>
</volumes>
</ebs_hot_and_cold>
上述策略中卷的顺序非常重要。将新的 part 存储在磁盘上时,ClickHouse 首先尝试将其放置在第一个卷中,然后放置在第二个卷中,依此类推。
SELECT *
FROM system.storage_policies
WHERE policy_name = 'ebs_hot_and_cold'
Row 1:
──────
policy_name: ebs_hot_and_cold
volume_name: hot_volume
volume_priority: 1
disks: ['ebs_gp2_2']
max_data_part_size: 200000000
move_factor: 0.1
Row 2:
──────
policy_name: ebs_hot_and_cold
volume_name: cold_volume
volume_priority: 2
disks: ['ebs_sc1_1']
Max_data_part_size: 0
move_factor: 0.1
为了验证效果,创建一个使用新的分层存储配置的表。
CREATE TABLE sample4 (id UInt64) Engine=MergeTree ORDER BY id SETTINGS storage_policy = 'ebs_hot_and_cold';
INSERT INTO sample4 SELECT rand() FROM numbers(10000000);
-- repeat 10 times
SELECT
disk_name,
formatReadableSize(bytes_on_disk) AS size
FROM system.parts
WHERE (table = 'sample4') AND active
┌─disk_name─┬─size───────┐
│ ebs_gp2_2 │ 121.30 MiB │
│ ebs_gp2_2 │ 123.53 MiB │
│ ebs_gp2_2 │ 131.84 MiB │
│ ebs_gp2_2 │ 5.04 MiB │
│ ebs_gp2_2 │ 2.74 MiB │
└───────────┴────────────┘
目前,所有数据都是热数据,并存储在 SSD 上。
-- 重复执行该 INSERT 操作至少 8 次
INSERT INTO sample4 SELECT rand() FROM numbers(10000000);
SELECT
disk_name,
formatReadableSize(bytes_on_disk) AS size
FROM system.parts
WHERE (table = 'sample4') AND active
┌─disk_name─┬─size───────┐
│ ebs_sc1_1 │ 570.56 MiB │
│ ebs_gp2_2 │ 26.90 MiB │
│ ebs_gp2_2 │ 29.08 MiB │
│ ebs_gp2_2 │ 26.90 MiB │
│ ebs_gp2_2 │ 5.04 MiB │
│ ebs_gp2_2 │ 5.04 MiB │
│ ebs_gp2_2 │ 5.04 MiB │
│ ebs_gp2_2 │ 5.04 MiB │
│ ebs_gp2_2 │ 2.74 MiB │
└───────────┴────────────┘
可以看到合并时创建了一个很大的 part,该 part 被放置在冷的存储中。
根据新 part 大小的估计来确定放置新 part 的位置,可能与实际 part 大小不同。对于 insert 操作,使用未压缩的方式估算 part 大小。对于 merge 操作,ClickHouse 使用合并 parts 的压缩大小之和 + 10%。该估计值是近似值,可能并非在所有情况下都完全准确。我们可能会看到某些 parts 比慢速存储上的限制小一些,或者有些 parts 在快速存储上大一些。
手动移动 parts
除了后台合并过程中发生的自动移动之外,还可以使用新的 ALTER 命令语法手动移动 parts 和 partitions。
ALTER TABLE sample4 MOVE PART 'all_570_570_0' TO VOLUME 'cold_volume'
ALTER TABLE sample4 MOVE PART 'all_570_570_0' TO DISK 'ebs_gp2_1'
ALTER TABLE sample4 MOVE PARTITION tuple() TO VOLUME 'cold_volume'
同样,当一个卷的可用空间不足 10% 时,ClickHouse 在后台尝试通过将不足空间中的 part 移动到下一个卷来释放空间。我们可以通过更改 move_factor 来调整它,默认情况下为 0.1 = 10%。我们还可以通过使用 move_factor 为 0 来完全禁用自动后台移动。
后台移动以与后台合并相同的方式执行。当前,我们看不到正在运行某个移动,但是可以在 system.part_log 中看到移动的日志。
让我们看看它是如何工作的。
我们将启用 part_log 并设置一个很高的 move_factor 来查看会发生什么。
切记:
请勿在生产中这样做!
<ebs_hot_and_cold_movefactor99>
<volumes>
<hot_volume>
<disk>ebs_gp2_2</disk>
<max_data_part_size_bytes>200000000</max_data_part_size_bytes>
</hot_volume>
<cold_volume>
<disk>ebs_sc1_1</disk>
</cold_volume>
</volumes>
<move_factor>0.9999</move_factor>
</ebs_hot_and_cold_movefactor99>
如果想知道如何启用 part_log 表,请将以下配置添加到 /etc/clickhouse-server/config.d/part_log.xml 中:
<yandex>
<part_log>
<database>system</database>
<table>part_log</table>
<flush_interval_milliseconds>7500</flush_interval_milliseconds>
</part_log>
</yandex>
现在创建一个表并加载一些数据。
CREATE TABLE sample5 (id UInt64) Engine=MergeTree ORDER BY id SETTINGS storage_policy = 'ebs_hot_and_cold_movefactor99';
INSERT INTO sample5 SELECT rand() FROM numbers(100);
SELECT event_type, path_on_disk
FROM system.part_log
┌─event_type─┬─path_on_disk───────────────────────────────────┐
│ NewPart │ /mnt/ebs_gp2_2/data/default/sample5/all_1_1_0/ │
│ MovePart │ /mnt/ebs_sc1_1/data/default/sample5/all_1_1_0/ │
└────────────┴────────────────────────────────────────────────┘
根据上面输出结果可以可以看到,insert 内容将新 part 放置在第1个磁盘上,但是后台进程看到,根据移动因子将 part 移动并将其移动到第2个磁盘上。
结合 JBOD 和分层存储
到目前为止,我们已经看到了如何使用一组磁盘(JBOD)创建卷以及如何在单个磁盘之间创建分层存储。在最后一个示例中,我们可以将这些概念组合起来以创建多个分层卷,每个分层卷都包含多个磁盘。
<three_tier>
<volumes>
<hot_volume>
<disk>superfast_ssd1</disk>
<disk>superfast_ssd2</disk>
<max_data_part_size_bytes>200000000</max_data_part_size_bytes>
</hot_volume>
<jbod_volume>
<disk>normal_hdd1</disk>
<disk>normal_hdd2</disk>
<disk>normal_hdd3</disk>
<max_data_part_size_bytes>80000000000</max_data_part_size_bytes>
</jbod_volume>
<archive_volume>
<disk>slow_and_huge</disk>
</archive_volume>
</volumes>
</three_tier>
总结
本文介绍了如何构建存储策略并应用它们以不同方式分发 MergeTree 表数据。笔者建议最有用的配置是启用分层存储。另外,正如我们所看到的,也可以使用存储策略来解决其他问题。
后续笔者将讨论多卷操作管理以及一些在多卷配置中可能遇到的特殊情况和问题。
参考
https://clickhouse.yandex/docs/en/single/#table_engine-mergetree-multiple-volumeshttps://www.altinity.com/blog/2019/11/27/amplifying-clickhouse-capacity-with-multi-volume-storage-part-1?rq=multi%20userhttps://www.altinity.com/blog/2019/11/29/amplifying-clickhouse-capacity-with-multi-volume-storage-part-2
DataFlow范式
关注
关注
点赞
33
收藏
打赏
评论
ClickHouse - 多卷存储扩大存储容量(生产环境必备)
笔者最近工作有点忙,加上培训较多,近期文章更新慢了一拍。不过,今天为 ClickHouse 的爱好者带来一篇非常不错的文章,部分内容来自 Altinity,以及笔者补充和整理而成。长期使...
复制链接
扫一扫
了解Settings-Storage
wlia的专栏
12-29
1917
背景
由于项目需要在产品设置中增加storage功能,故对系统原生实现进行学习
settings_header
packages/apps/Settings/src/com/android/settings/Settings.java
loadHeadersFromResource(R.xml.settings_headers, headers);
通过查看settings_h
启动系统服务clickhouse报错clickhouse-server.service: main process exited, code=exited, status=232/ADDRESS_FA
wulitaotao96的博客
06-30
7049
错误:
使用
systemctl start clickhouse-server
启动失败,报错信息如下:
[root@hantest mysql]# systemctl status clickhouse-server
● clickhouse-server.service - ClickHouse Server (analytic DBMS for big data)
Loaded: loaded (/etc/systemd/system/clickhouse-server.serv.
评论 1
您还未登录,请先
登录
后发表或查看评论
CentOS 7生产环境离线安装Clickhouse
最新发布
stone5751的专栏
11-01
66
CentOS 7生产环境如何离线安装Clickhouse
Clickhouse多磁盘存储
三思的博客
02-26
1162
文章目录一、配置多磁盘存储1、默认情况下,ck单磁盘存储2、配置多磁盘3、多磁盘系统信息查询二、配置多磁盘策略1、默认磁盘存储策略2、配置多磁盘存储策略3、磁盘存储策略系统信息查询三、多磁盘存储使用1、多磁盘存储表2、多磁盘数据迁移
一、配置多磁盘存储
默认情况下,我们会子在配置文件config.xml文件中指定的xxx/目录为我们的数据目录,该磁盘在ck中为default存储设备。所有的建表、数据写入默认都写入到我们指定的default目录下。
从19.15版本开始,ck开始支持多卷存储的功能,我们可以将
clickhouse MergeTree序列表引擎
qq_32323239的博客
03-05
261
1、MergeTree
1.1数据TTL
1.1.1列级别TTL
-- 创建一张包含列级别TTL的表
create table test.ttl_table_v1 ( \
id String, \ -- 主键字段不能被声明TTL表达式
create_time DateTime, \ -- 需要依托对某个DateTime或Date类型字段的INTERVAL操作,来表达TTL的过期时间
code String TTL create_time + INTERVAL 10 SECOND, \ -- 当系统
ClickHouse高可用集群的配置
weixin_34125592的博客
07-23
6450
上一篇文章写过centos 7下clickhouse rpm包安装和基本的目录结构,这里主要介绍clickhouse高可用集群的部署方案,因为对于默认的分布式表的配置,每个分片只有一份,这样如果挂掉一个节点,则查询分布式表的时候直接会报错,这个是基于clickhouse自己实现的多分片单副本集群,配置也比较简单,这里说的高可用是指,每个分片具有2个或以上副本,当某个节点挂掉时,该节点分片仍...
Clickhouse 集群部署安装
爱摄影的小章同学的博客
07-20
452
clickhouse 集群搭建部署
ClickHouse多卷存储策略
style_boy的博客
03-12
832
从 19.15 版本开始,ClickHouse 开始实现多卷存储的功能。
主要是将数据分层存储,比如冷热数据分层存储,数据分不同卷存储等等。话不多说,开干~
1 准备环境
添加三块新磁盘:
/dev/sdb20G
/dev/sdc20G
/dev/sdd30G
echo "- - -" > /sys/class/scsi_host/host1/scan
echo "- - -" > /sys/class/scsi_host/host0/scan
echo "- - -" >
centos上安装clickhouse和启动使用
感谢关注点赞,笔芯啾咪!
08-19
1263
官网文件下载地址:去官网https://packages.clickhouse.com/deb/pool/stable/下载四个关键包。
分别是client包,static包,static-dbg包和server包,四个包版本要一致,这里以22.3.2.2-2版本举例。
ClickHouse启动失败
冰川的博客
02-26
1万+
启动操作
sudo systemctl start clickhouse-server
sudo systemctl stop clickhouse-server
sudo systemctl status clickhouse-server
不要使用service clickhouse-server或/etc/init.d/clickhouse-service
报错信息
[root@clickhouse04 ~]# systemctl status clickhouse-server
● clickho
docker启动报错(code=exited, status=1/FAILURE)
纳川的博客
07-15
1万+
报错详情:
docker.service - Docker Application Container Engine
Loaded: loaded (/usr/lib/systemd/system/docker.service; enabled; vendor preset: disabled)
Active: failed (Result: start-limit) sinc...
clickhouse系列之二:clickhouse遇到的报错问题及解决方法
热门推荐
a904364908的博客
08-20
3万+
问题一,启动报错
启动参数:sudo clickhouse-server --config-file=/etc/clickhouse-server/config.xml
2020.08.20 18:49:28.189321 [ 29338 ] {} <Error> Application: DB::Exception: Effective user of the process (root) does not match the owner of the data (clickhouse). R
clickhouse安装说明
zzy7075的专栏
06-28
334
下载clickhouse相关安装文件:
下载地址: https://repo.yandex.ru/clickhouse/rpm/stable/x86_64/
Linux执行安装指令
rpm -ivh +包名
注意:先执行安装common-static。因为server和client安装时需要依赖common中的文件。
客户端与服务端启动
服务端启动sudo /etc/init.d/clickhouse-server start
注意事项:如果linux报: init script
clickhouse MergeTree引擎的多路径存储配置及支持HDFS等外部存储
penriver的博客
10-13
546
多路径存储策略
多路径存储策略介绍
使用多块设备存储数据配置官方说明
clickhouse从19.15开始,MergeTree族表引擎可以在多个块设备上存储数据。
例如,当某个表的数据隐式地划分为“热”和“冷”时,它可能很有用。
最近的数据经常请求,但只需要少量的空间。
历史数据很少被请求,但需要大量的空间。
如果有几个可用的磁盘,“热”数据可能位于快速磁盘(例如,NVMe ssd或内存),而“冷”数据位于相对较慢的磁盘(例如,HDD)。
支持的策略
MergeTree支持的存储策略如下:
JBOD策
clickhouse环境搭建
QTT_CSDN的博客
12-14
624
clickhouse 下载安装 环境搭建
【ClickHouse】优化
qq_41466440的博客
12-23
90
clickhouse优化
ClickHouse守护进程
一条大河
10-26
209
#!/bin/bash
status=`ps -ef | grep "/usr/bin/clickhouse-server" | egrep ^clickho`
let flag=$?
if [[ $flag = 0 ]]
then
echo "success!"
echo $flag
else
echo "fail."
echo $flag
sleep 5
/usr/bin/clickhouse start.
【clickhouse】clickhouse配置多块磁盘
九师兄
12-04
932
1.概述
转载:clickhouse配置多块磁盘
最近让运维同学新搭了一个clickhouse集群,每台服务器都配置了多块磁盘,但是使用的时候还是按照以前的方式是使用的,导致系统盘空间不够。特此记录一下配置和使用方法。
2.集群配置
执行lsblk命令,可以看到本地机器的磁盘信息:
主要需要修改的地方是config.xml文件,在配置文件中插入以下格式的语句:
<!-- 存储路径 -->
<storage_configuration>
<disks>
<d.
用TensorFlow预测纽约市AirBnB租赁价格
TensorFlowNews
11-03
754
作者|TIMOTHY102
编译|VK
来源|Analytics Vidhya
介绍
Airbnb是一个在线市场,允许人们将自己的房产或空余房间出租给客人。每预订3位客人,收取12%和6%的佣金。
该公司自2009年成立以来,已从每年帮助2.1万名客人找到住处,发展到每年帮助600万人度假,目前在90个不同国家的34000个城市列出了惊人的80万套房产。
在本文中,我将使用Kaggle-newyorkcityairbnb开放数据集,尝试用TensorFlow建立一个神经网络模型来进行预测。
目标是建立一个合
“相关推荐”对你有帮助么?
非常没帮助
没帮助
一般
有帮助
非常有帮助
提交
©️2022 CSDN
皮肤主题:大白
设计师:CSDN官方博客
返回首页
DataFlow范式
CSDN认证博客专家
CSDN认证企业博客
码龄13年
暂无认证
286
原创
1万+
周排名
69万+
总排名
139万+
访问
等级
1万+
积分
738
粉丝
218
获赞
176
评论
703
收藏
私信
关注
热门文章
新一代Hive客户端工具:Beeline
25013
深入理解ClickHouse-本地表和分布式表
23144
解决镜像无法删除的问题
23051
Harbor部署和使用
22822
HBase客户端访问超时原因及参数优化
22620
分类专栏
Apache Kylin实战
13篇
ClickHouse从0到1
1篇
Python梦工厂
8篇
HBase实战
9篇
Hive实战
19篇
Greenplum/DeepGreen实战
16篇
Python
11篇
Shell
15篇
MySQL
38篇
Oracle
17篇
Perl
9篇
Vertica
6篇
SybaseIQ
4篇
Greenplum
26篇
Hadoop
16篇
Linux
22篇
PostgreSQL
1篇
DataMiner
10篇
Others
1篇
Java
5篇
Flume
Kafka
1篇
Hive
28篇
Hbase
11篇
Data Warehouse
3篇
Oozie
1篇
Impala
2篇
Storm
1篇
Spark
14篇
Scala
7篇
Tachyon
3篇
Redis
4篇
Kylin
20篇
Sqoop
2篇
ElasticSearch
7篇
Phoenix
7篇
Presto
1篇
Docker
8篇
Flink
3篇
Neo4j
1篇
CDH
1篇
Embulk
1篇
ClickHouse
2篇
最新评论
问题以及解决办法:hadoop 不在 sudoers 文件中。此事将被报告
晴一子:
请问怎么保存退出呢?我直接点了❌
ClickHouse - 多卷存储扩大存储容量(生产环境必备)
陈盼盼110:
顶呱呱 学习了
Delta Lake - 增删改事务操作之大结局
weixin_44161946:
代码都是一整行,有没有格式化好的啊?
NFS 官方资料
zuofeng1988:
http://nfs.sourceforge.net/
Greenplum或DeepGreen数据库查看表倾斜的方法总结
zwbaga:
这个存储过程创建的视图是有问题的,具体原因可查看 https://blog.csdn.net/mingli_a/article/details/100130757
您愿意向朋友推荐“博客详情页”吗?
强烈不推荐
不推荐
一般般
推荐
强烈推荐
提交
最新文章
非你想的那个 CDC,实为我这个 CDC 也
来,换个轻松话题,深度学习
Hadoop 3.x 时代,EC 露个脸呗!
2020年20篇
2019年20篇
2018年6篇
2017年15篇
2016年123篇
2015年109篇
2014年13篇
2013年29篇
2012年5篇
目录
目录
分类专栏
Apache Kylin实战
13篇
ClickHouse从0到1
1篇
Python梦工厂
8篇
HBase实战
9篇
Hive实战
19篇
Greenplum/DeepGreen实战
16篇
Python
11篇
Shell
15篇
MySQL
38篇
Oracle
17篇
Perl
9篇
Vertica
6篇
SybaseIQ
4篇
Greenplum
26篇
Hadoop
16篇
Linux
22篇
PostgreSQL
1篇
DataMiner
10篇
Others
1篇
Java
5篇
Flume
Kafka
1篇
Hive
28篇
Hbase
11篇
Data Warehouse
3篇
Oozie
1篇
Impala
2篇
Storm
1篇
Spark
14篇
Scala
7篇
Tachyon
3篇
Redis
4篇
Kylin
20篇
Sqoop
2篇
ElasticSearch
7篇
Phoenix
7篇
Presto
1篇
Docker
8篇
Flink
3篇
Neo4j
1篇
CDH
1篇
Embulk
1篇
ClickHouse
2篇
目录
评论 1
被折叠的 条评论
为什么被折叠?
到【灌水乐园】发言
查看更多评论
打赏作者
DataFlow范式
你的鼓励将是我创作的最大动力
¥2
¥4
¥6
¥10
¥20
输入1-500的整数
余额支付
(余额:-- )
扫码支付
扫码支付:¥2
获取中
扫码支付
您的余额不足,请更换扫码支付或充值
打赏作者
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额
抵扣说明:
1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。 2.余额无法直接购买下载,可以购买VIP、C币套餐、付费专栏及课程。
余额充值