首先说明此S3并非ClickHouse支持的S3表引擎,而是可以使用MergeTree表引擎直接将数据存到S3中。
可能被第一句话绕蒙了,先来大致了解下这两种方式:S3表引擎和DiskS3
S3表引擎
创建S3表,注意原生S3表引擎只支持S3的公有读写,不支持配置AK/SK
CREATE TABLE s3_test (
dt Date,
id Int64,
data String
) ENGINE = S3('http://{s3url}/{bucket}/{file}', 'CSV');
插入数据
INSERT INTO s3_test VALUES (NOW(),1,'A'),(NOW(),2,'B'),(NOW(),3,'C'),(NOW(),4,'D'),(NOW(),5,'E'),(NOW(),6,'F');
查询数据
SELECT *
FROM s3_test
┌─────────dt─┬─id─┬─data─┐
│ 2020-08-14 │ 1 │ A │
│ 2020-08-14 │ 2 │ B │
│ 2020-08-14 │ 3 │ C │
│ 2020-08-14 │ 4 │ D │
│ 2020-08-14 │ 5 │ E │
│ 2020-08-14 │ 6 │ F │
└────────────┴────┴──────┘
6 rows in set. Elapsed: 0.040 sec.
这种方式是建立S3表引擎,利用该引擎打通的S3接口来实现S3的读写(S3表引擎不支持S3的追加写),简单来说就是实现S3的基本接口。
DiskS3
DiskS3是真正用S3实现了底层存储,和表引擎无关,可以在S3存储的基础上使用MergTree表引擎,即MergeTree表引擎既有其本身的特性,而且将数据都用S3进行了存储。
配置方法
当然使用这个方式就需要进行一些特殊的配置,如下,可将该配置文件放在/etc/clickhouse-server/config.d
目录下
<yandex>
<storage_configuration>
<disks>
<s3>
<type>s3</type>
<endpoint>http://{s3url}/{bucket}/{path}/</endpoint>
<access_key_id>{ak}</access_key_id>
<secret_access_key>{sk}</secret_access_key>
</s3>
</disks>
<policies>
<s3>
<volumes>
<main>
<disk>s3</disk>
</main>
</volumes>
</s3>
</policies>
</storage_configuration>
</yandex>
其实DiskS3也是借助了ClickHouse灵活的存储策略支持,比如可以配置多块盘,配置冷热数据分离存储等等。
扩展内容
冷热数据分离存储配置方法
<yandex> <storage_configuration> <disks> <ssd> <path>/ssd/clickhouse</path> </ssd> <hdd> <path>/hdd/clickhouse</path> <keep_free_space_bytes>10485760</keep_free_space_bytes> </hdd> </disks> <policies> <ssd_to_hdd> <volumes> <hot> <disk>ssd</disk> <max_data_part_size_bytes>1073741824</max_data_part_size_bytes> </hot> <cold> <disk>hdd</disk> </cold> <move_factor>0.2</move_factor> </volumes> </ssd_to_hdd> </policies> </storage_configuration> </yandex>
其中
/ssd/clickhouse
挂载ssd,/hdd/clickhouse
挂载hdd,move_factor
移动因子表示如果还剩20%的空间就进行ssd到hdd的数据移动。
多块盘的情况和上述配置类似,不做过多扩展。
建表及数据操作
当配置完DiskS3后可以通过系统表查看,如下,可见move_factor
默认为0.1.
SELECT *
FROM system.storage_policies
WHERE policy_name = 's3'
Row 1:
──────
policy_name: s3
volume_name: main
volume_priority: 1
disks: ['s3']
max_data_part_size: 0
move_factor: 0.1
1 rows in set. Elapsed: 0.001 sec.
创建MergeTree表
CREATE TABLE disks3_test (
dt Date,
id Int64,
data String,
INDEX min_max (id) TYPE minmax GRANULARITY 3
) ENGINE=MergeTree()
PARTITION BY dt
ORDER BY (dt, id)
SETTINGS
storage_policy='s3',
old_parts_lifetime=0,
index_granularity=512;
插入数据
INSERT INTO disks3_test VALUES (NOW(),1,'A'),(NOW(),2,'B'),(NOW(),3,'C'),(NOW(),4,'D'),(NOW(),5,'E'),(NOW(),6,'F');
查询数据
SELECT *
FROM disks3_test
┌─────────dt─┬─id─┬─data─┐
│ 2020-08-14 │ 1 │ A │
│ 2020-08-14 │ 2 │ B │
│ 2020-08-14 │ 3 │ C │
│ 2020-08-14 │ 4 │ D │
│ 2020-08-14 │ 5 │ E │
│ 2020-08-14 │ 6 │ F │
└────────────┴────┴──────┘
6 rows in set. Elapsed: 0.147 sec.
表数据文件
DiskS3的数据文件不在默认的data数据目录了,而是在/var/lib/clickhouse/disks/s3/data/
目录。比如disks3_test,目录为/var/lib/clickhouse/disks/s3/data/default/disks3_test
,具体目录结构为:
[root@ck disks3_test]# tree
.
├── 20200814_1_1_0
│ ├── checksums.txt
│ ├── columns.txt
│ ├── count.txt
│ ├── data.bin
│ ├── data.mrk2
│ ├── dt.bin
│ ├── dt.mrk2
│ ├── id.bin
│ ├── id.mrk2
│ ├── minmax_dt.idx
│ ├── partition.dat
│ ├── primary.idx
│ ├── skp_idx_min_max.idx
│ └── skp_idx_min_max.mrk2
├── detached
└── format_version.txt
看一下dt.bin
和dt.mrk2
[root@ck 20200814_1_1_0]# cat dt.bin
1
1 38
38 ck/ubkprtqwgjlyyobbwbaizgxdrtrysxxa
0
[root@ck 20200814_1_1_0]# cat dt.mrk2
1
1 48
48 ck/caiylwqkiipxvbphxuosgcwpppilxixp
0
发现这些文件并不是二进制文件,都是数字和字符串,其中的字符串就是对应在S3上的文件,如ubkprtqwgjlyyobbwbaizgxdrtrysxxa,可以通过s3cmd验证一下:
[root@ck 20200814_1_1_0]# s3cmd ls s3://ck/ubkprtqwgjlyyobbwbaizgxdrtrysxxa
2020-08-14 10:19 38 s3://ck/ubkprtqwgjlyyobbwbaizgxdrtrysxxa
可以发现s3上确实已存在该文件,通过s3cmd ls
也可以发现.bin
和.mrk2
中的数字就是s3文件的大小,即38B。