博客 / 工程

ClickHouse 23.1 版本发布

author avatar
ClickHouse 团队
2023年1月30日 - 10 分钟阅读

23.1 Release Post.png

新年快乐!同时,这也是 ClickHouse 的新版本发布。我们很高兴推出 23.x 系列的第一个版本 23.1。

像往常一样,我们举办了 ClickHouse 社区电话会议,讨论版本发布、提供现场演示并回答您的问题。

请留意 23.2 版本发布网络研讨会的公告。如果您想了解更多关于 ClickHouse 基础知识的信息,请查看即将到来的培训课程

版本摘要

  • 17 个新功能。
  • 17 项性能优化。
  • 78 个错误修复。

当然,还有大量的性能改进。

如果这还不足以让您有兴趣尝试一下。请查看一些重点内容

倒排全文索引 - Larry Luo, Harry Lee

是的,您没看错。在此版本中,我们为 ClickHouse 中的倒排索引添加了实验性支持,作为数据跳过索引。虽然这并没有使 ClickHouse 成为成熟的搜索引擎,但它为提高特定基于令牌的查询的性能引入了一些有趣的可能性。如果您有一个包含大型文本块的数据集,您需要在其上执行令牌匹配,则此功能非常适合您。

此索引可用于加速任何执行令牌匹配的字符串函数,特别是 multiSearchAnyhasToken 函数。这应该允许您构建如下所示的相当复杂的布尔条件。此外,诸如 LIKEIN== 等相等运算符都受益,例如:

SELECT * from tab WHERE s == 'Hello World';
SELECT * from tab WHERE s IN ('Hello', 'World');
SELECT * from tab WHERE s LIKE '%Hello%';

演示此功能的最简单方法是使用具有大量文本的数据集。有什么比我们最喜欢的 Hacker News 数据更好的呢?

考虑一下我们在 sql.clickhouse.com 环境中的这个查询,查找所有随时间推移提及 ClickHouse 的帖子

SELECT toYYYYMM(toDateTime(time)) AS monthYear, bar(count(), 0, 120, 20) AS count FROM hackernews WHERE (text ILIKE '%ClickHouse%') GROUP BY monthYear ORDER BY monthYear ASC │ 201910 │ ▊ │ │ 201911 │ ██▊ │ │ 201912 │ █▎ │ │ 202001 │ ███████████▏ │ │ 202002 │ ██████ │ │ 202003 │ ███████████▌ │ │ 202004 │ ███████▏ │ │ 202005 │ █████▋ │ │ 202006 │ █████▊ │ │ 202007 │ ███████▎ │ │ 202008 │ ███▌ │ │ 202009 │ ██▊ │ │ 202010 │ ████▌ │ │ 202011 │ ████▋ │ │ 202012 │ ███▏ │ │ 202101 │ ██▊ │ │ 202102 │ ████████▎ │ │ 202103 │ ████████████▏ │ │ 202104 │ ██▌ │ │ 202105 │ ████████████▏ │ │ 202106 │ ██▏ │ │ 202107 │ ████▏ │ │ 202108 │ ████ │ │ 202109 │ ████████████████▎ │ │ 202110 │ ████████████████████ │ │ 202111 │ ███████████▌ │ │ 202112 │ ███████████▏ │ │ 202201 │ ██████▊ │ │ 202202 │ ███████ │ │ 202203 │ ████▊ │ │ 202204 │ █████████▋ │ │ 202205 │ █████████████ │ │ 202206 │ █████████████▊ │ │ 202207 │ ████████████▌ │ │ 202208 │ ██████▊ │ │ 202209 │ █████████▊ │ │ 202210 │ ████████████████████ │ │ 202211 │ ██████▏ │ │ 202212 │ █▋ │ └───────────┴──────────────────────┘ 67 rows in set. Elapsed: 0.561 sec. Processed 33.95 million rows, 11.62 GB (60.53 million rows/s., 20.72 GB/s.)

除了我们变得越来越有新闻价值之外,请注意这里的时间安排。尽管速度很快,但就目前的形式而言,此查询需要对整个文档集进行线性扫描。我们可以使用跳过索引的正常语法将倒排索引添加到文本和标题字段

ALTER TABLE hackernews ADD INDEX inv_idx(text) TYPE inverted;
ALTER TABLE hackernews MATERIALIZE INDEX inv_idx;
SELECT
    toYYYYMM(toDateTime(time)) AS monthYear,
    bar(count(), 0, 120, 20) AS count
FROM hackernews_indexed
WHERE multiSearchAny(text, ['ClickHouse', 'Clickhouse', 'clickHouse', 'clickhouse'])
GROUP BY monthYear
ORDER BY monthYear ASC202210 │ ████████████████████ │
│    202211 │ ██████▏              │
│    202212 │ █▋                   │
└───────────┴──────────────────────┘

72 rows in set. Elapsed: 0.285 sec. Processed 6.07 million rows, 2.18 GB (21.27 million rows/s., 7.65 GB/s.)

要检查索引是否正在使用,您可以在查询前面加上 EXPLAIN indexes=,例如:

EXPLAIN indexes = 1
SELECT
    toYYYYMM(toDateTime(time)) AS monthYear,
    bar(count(), 0, 120, 20) AS count
FROM hackernews_indexed
WHERE text LIKE '%clickhouse%'
GROUP BY monthYear
ORDER BY monthYear ASC

┌─explain──────────────────────────────────────────────────────┐
│ Expression ((Projection + Before ORDER BY [lifted up part])) │
│   Sorting (Sorting for ORDER BY)                             │
│     Expression (Before ORDER BY)                             │
│       Aggregating                                            │
│         Expression (Before GROUP BY)                         │
│           ReadFromMergeTree (default.hackernews_indexed)     │
│           Indexes:                                           │
│             PrimaryKey                                       │
│               Condition: true                                │
│               Parts: 1/1                                     │
│               Granules: 4150/4150                            │
│             Skip                                             │
│               Name: inv_idx                                  │
│               Description: inverted GRANULARITY 1            │
│               Parts: 1/1                                     │
│               Granules: 4150/4150                            │
└──────────────────────────────────────────────────────────────┘

一些限制(毕竟是实验性的)

  • 我们不存储术语在帖子中的位置,从而阻止了短语匹配或诸如 multisearchallpositions 等函数的优化。
  • 我们没有相关性计算 - 为此,我们需要持久化术语统计信息,这在初始迭代中被认为超出了范围。目前,该索引纯粹用于加速匹配。
  • 文本要么通过在空格上拆分进行标记化,要么如果您需要子字符串匹配,则通过 可配置的 n-gram 大小进行标记化。文本处理是不可配置的,因此此功能无法与 Lucene 等自然语言引擎相媲美。

总之,如果您需要加速简单的令牌匹配,那么这非常适合您。“日志记录数据呢?”您可能会问?我们将在后续文章中作为我们的 可观测性系列的一部分进行讨论。

如果您需要相关性功能和更细致的文本匹配,例如电子商务,也许暂时不要替换您的搜索引擎......但请继续关注;我们希望在未来的版本中看到此功能的改进,并且 ClickHouse 的发展速度很快 :)

我们预计你们中的许多人会对这项功能的实现方式有疑问。预计很快会有一篇关于内部原理的后续博客。

参数化视图 - Smita Kulkarni

任何编写大量 SQL 的人都很快学会欣赏视图。它们允许用户抽象出复杂的查询,并使用表语法公开它们 - 允许从组件部分构建进一步更复杂的查询,而不会被大量的 SQL 代码淹没。到目前为止,用户只能创建静态视图。在 ClickHouse 23.1 版本中,我们可以创建基于查询时传递的参数的动态视图。

假设我们想要一个用于搜索 Stack Overflow 数据集的视图。此数据集可在 [https://archive.org/details/stackexchange] 中获得,并被描述为帖子 [https://meta.stackexchange.com/questions/2677/database-schema-documentation-for-the-public-data-dump-and-sede]。

我们的以下示例是静态的,仅限于搜索 ClickHouse 帖子。

CREATE VIEW search_clickhouse_stackoverflow AS SELECT Id, CreationDate, Title, LastActivityDate, ViewCount, AnswerCount, Score FROM stackoverflow WHERE (PostTypeId = 1) AND multiSearchAny(Body, ['ClickHouse']) SELECT * FROM search_clickhouse_stackoverflow LIMIT 1 FORMAT Vertical Row 1: ────── Id: 71655910 CreationDate: 2022-03-29 02:50:35.920000000 Title: How to execute "with" query locally in ClickHouse? LastActivityDate: 2022-03-29 03:08:04.863000000 ViewCount: 48 AnswerCount: 0 Score: 0 1 row in set. Elapsed: 1.445 sec. Processed 200.26 thousand rows, 276.42 MB (138.60 thousand rows/s., 191.31 MB/s.)

理想情况下,我们希望此视图比仅搜索 ClickHouse 帖子更灵活。使用参数化视图,我们现在可以概括此视图

CREATE VIEW search_stackoverflow AS SELECT Id, CreationDate, Title, LastActivityDate, ViewCount, AnswerCount, Score FROM stackoverflow WHERE (PostTypeId = 1) AND multiSearchAny(Body, splitByWhitespace({text:String})) SELECT * FROM search_stackoverflow(text = 'ClickHouse MergeTree') ORDER BY Score DESC LIMIT 1 FORMAT Vertical Row 1: ────── Id: 40592010 CreationDate: 2016-11-14 15:13:55.310000000 Title: Multiple small inserts in clickhouse LastActivityDate: 2021-01-06 09:14:48.947000000 ViewCount: 15849 AnswerCount: 5 Score: 15 1 row in set. Elapsed: 0.594 sec. Processed 5.79 million rows, 8.10 GB (9.75 million rows/s., 13.62 GB/s.)

请注意,我们还在空格上拆分查询字符串以利用 multiSearchAny 函数。我们还使用倒排索引进行了优化。这代表了一种粗略的搜索能力,但希望您能了解如何组合这些功能。

查询结果缓存 - Robert Schutze, Mikhail Stetsyuk

为了实现最佳性能,分析型数据库优化了其内部数据存储和处理管道的每一步。但是数据库执行的最好的一种工作是根本没有完成的工作!缓存是一种特别流行的技术,通过存储早期计算或远程数据的结果来避免不必要的工作,这些数据访问起来很昂贵。ClickHouse 广泛使用缓存,例如,缓存 DNS 记录、本地和远程 (S3) 数据、推断模式、编译查询和正则表达式。在 23.1 中,我们向 ClickHouse 缓存家族引入了一个新成员:查询结果缓存!

查询缓存基于这样的想法:有时在某些情况下,可以缓存昂贵的 SELECT 查询的结果,以便可以直接从缓存中为同一查询的进一步执行提供服务。根据查询的类型,这可以显着减少 ClickHouse 服务器的延迟和资源消耗。例如,考虑像 Grafana 或 Apache Superset 这样的数据可视化工具,它显示过去 24 小时的汇总销售额报告。在大多数情况下,一天内的销售数字变化相当缓慢,我们可以承受每三个小时(例如)刷新一次报告。从 ClickHouse v23.1 开始,可以为 SELECT 查询提供“生存时间”,在此期间服务器将仅计算查询的首次执行,并且后续执行将直接从缓存中回答,而无需进一步计算。

用户应注意,这不是事务一致性缓存 - 如果底层数据发生更改,则不会从缓存中删除条目。这是经过设计的,并且出于多种原因而合理。作为 OLAP 数据库,为了性能和缓存可伸缩性的好处,我们容忍稍微不准确的结果。ClickHouse 还有后台操作,例如可能更改数据的折叠合并,这将使事务一致性缓存可能无效。因此,缓存条目仅基于 TTL,在此之后它们的条目将被删除。

由于这是一个如此重要的功能,并且具有许多可调设置,因此我们很快将发布一篇专门的博客文章来介绍它。

分享这篇文章

订阅我们的新闻通讯

随时了解功能发布、产品路线图、支持和云服务信息!
正在加载表单...
关注我们
X imageSlack imageGitHub image
Telegram imageMeetup imageRss image
©2025ClickHouse, Inc. 总部位于加利福尼亚州湾区和荷兰阿姆斯特丹。