ClickHouse v24.9 版本深度解读:JSON 类型、轻量删除与并行副本性能优化实战指南
ClickHouse v24.9 版本深度解读JSON 类型、轻量删除与并行副本性能优化实战指南【免费下载链接】ClickHouseClickHouse® is a real-time analytics database management system项目地址: https://gitcode.com/GitHub_Trending/cli/ClickHouse本文基于 ClickHouse 官方变更日志 v24.9.1.3278-stable该版本为 v24.9.1.1-new 的修复发布对应提交 6d058d82a8e完整梳理 24.9 稳定版的五大类变化向后不兼容变更、新特性、性能优化、改进与缺陷修复并结合当前仓库源码如 toStartOfInterval 实现、FormatFactorySettings 等验证关键特性的实际落地方式帮助你在升级或评估该版本时快速掌握其能力边界与注意事项。版本背景与阅读对象ClickHouse 的版本号采用 CalVer 格式YY.M.patch.构建号v24.9.1.3278-stable即 2024 年 9 月发布线的第一次稳定版。该变更日志覆盖的 PR 区间大致从 #60197 到 #70034横跨查询解析、数据类型、存储引擎、分布式读写、鉴权与 CI 等多个子系统。建议的读者画像正在从 24.6/24.8 LTS 或 24.9 早期版本升级到 24.9 稳定版的运维与开发需要评估 JSON 类型、轻量删除Lightweight Delete、并行副本Parallel Replicas等新特性的应用开发者关心版本间兼容性尤其是 Replicated 数据库、Dynamic 类型、SETTINGS 子句解析的团队。以下各节按官方日志的原始分类展开条目均保留 PR 编号以便追溯涉及仓库实现的给出当前源码路径佐证。向后不兼容变更Backward Incompatible Change这一节是升级评估的重中之重24.9 共有 5 项明确的不兼容变更。1. UNION 中 SETTINGS 子句可位于 FORMAT 之前当带括号的子查询组成UNION链时允许在SETTINGS之后跟随FORMAT此前顺序受限对应 issue #39712PR #60197。同时当一条查询出现两个 SETTINGS 子句时行为发生变化现在离对应子查询最近的 SETTINGS 优先生效旧版本中外层 SETTINGS 可能覆盖内层。如果你的 SQL 里嵌套使用了双重 SETTINGS升级后各子查询取到的参数可能不同。2. Replicated 数据库中禁止显式指定 UUID 与副本参数在 Replicated 数据库中创建表时不再允许显式指定表 UUID不再允许为 *MergeTree 表显式指定 ZooKeeper 路径zookeeper_path和副本名replica_name。从源码结构看这一约束是为了让 Replicated 数据库在副本间保持元数据一致性。副作用是之前显式指定了这些参数、后来又DETACH TABLE PERMANENTLY的表重新ATTACH时会因显式参数而失败日志中对应 PR #69539 专门修复了这一路径的兼容处理。3. Dynamic 类型重新实现PR #68132这是 24.9 最重要的类型系统变更。重新实现后的 Dynamic 类型行为当动态数据类型数量达到上限时新类型不再被强制转成 String而是以“二进制编码的数据类型 二进制编码的数据”存入特殊数据结构曾经插入过 Dynamic 列的任何类型都可以作为子列subcolumn被读回。如果你的业务依赖“超出类型数量后自动降级为 String”的旧语义升级前必须回归测试相关列。4. 命名元组下标表达式a[b].c的解析语义变化PR #68435现在支持对命名元组使用a[b].c形式的访问以及“任意表达式结果按名称取下标”的写法例如expr().name这对处理 JSON 尤其有用对应 issue #54965。不兼容点旧版本中expr().name被解析为tupleElement(expr(), name)——分析器会去查找一个名为name的列新版本改为tupleElement(expr(), name)——按字符串名取元组元素。绝大多数旧场景本来就无法工作但存在一个极小众的坏用例把元组元素名存放在某个列或别名中且该列名与元组元素名不同例如SELECT b AS a, CAST([tuple(123)] AS Array(Tuple(b UInt8))) AS t, t[1].a;此类查询在新版下行为会变化官方因此将其标记为潜在不兼容。5.print_pretty_type_names作用范围扩大PR #68492此前该设置只影响DESCRIBE查询与toTypeName现在在SHOW CREATE TABLE、formatQuery以及clickhouse-client/clickhouse-local交互模式下Tuple类型也会以“美观形式”带元素名打印。如果你的工具链依赖元组的纯位置式文本表示例如做表结构 diff需要留意输出变化。新特性New Feature24.9 共引入 20 项新特性下面逐项说明并结合仓库源码佐证。1.toStartOfInterval()支持任意基准点origin重载新增三参重载语义对齐 TimescaleDB 的time_bucket()与 PostgreSQL 的date_bin()对应 issue #55619PR #56738将时间值对齐到从任意 origin 起算的区间倍数而不是固定的 0000-01-01 零点SELECT toStartOfInterval(toDateTime(2023-01-01 14:45:00), INTERVAL 1 MINUTE, toDateTime(2023-01-01 14:35:30)); -- 返回 2023-01-01 14:44:30origin 14:35:30 起算的整分钟仓库源码 src/Functions/toStartOfInterval.cpp 中可以看到ToStartOfIntervalOverload枚举区分Default与Origin两个重载Origin重载额外校验origin time的逐行约束并且因为 LowCardinality 字典恒含默认值 0 而不支持canBeExecutedOnDefaultArguments。实现上通过 libdivide 加速整型除法Date/Date32/DateTime/DateTime64四种返回类型分别分派处理。2.ATTACH PARTITION ALL FROM支持一次性挂载某表的所有分区PR #61987简化跨集群/跨库批量恢复分区数据的运维操作。3.input_format_try_infer_variants设置文本格式做 schema 推断时如果某列或数组元素存在多种可能的类型可以推断为 Variant 类型PR #63798。仓库中该设置定义在 src/Core/FormatFactorySettings.h 第 574 行附近默认值为falseDECLARE(Bool, input_format_try_infer_variants, false, ...)即默认关闭需显式开启。4.JSONCompactWithProgress输出格式每行输出为一个换行分隔的 JSON 对象包含metadata、data、progress、totals、statistics五段PR #66205适合需要边读结果边拿到进度与汇总的流式消费场景SELECT * FROM table FORMAT JSONCompactWithProgress;5. 全新 JSON 数据类型PR #6644424.9 引入了原生 JSON 数据类型当时实现为DataTypeJSON后续版本中与 Dynamic 进一步统一为别名体系。它按 JSON 路径物化子列存储支持子列查询与聚合下推。围绕该类型的配套能力同版本陆续补齐聚合函数distinctDynamicTypes/distinctJSONPaths/distinctJSONPathsAndTypes用于内省 JSON 列实际出现的类型与路径分布PR #68463JSON 列写入采用自适应写缓冲区以降低宽 part 下的小文件内存开销PR #69272。6.input_format_json_empty_as_default设置JSON 输入中的空字段empty field可被视为默认值而非 NULLPR #66782对应 issue #59339。同样定义于 src/Core/FormatFactorySettings.h 第 600 行附近默认false。7.overlay/overlayUTF8字符串函数按字节/UTF-8 位置替换字符串片段PR #66933SELECT overlay(Hello New York, Jersey, 11); -- 返回 Hello New Jersey8. 分区级轻量删除Lightweight Delete In Partition新增命令形式PR #67805DELETE FROM [db.]table [ON CLUSTER cluster] [IN PARTITION partition_expr] WHERE expr;相比整表轻量删除限定分区可缩小标记失效的数据范围。另注意配套改进PR #66169表上存在 projection 时除“抛异常默认”和“先删 projection”外新增了第三种选项——轻量删除后自动重建 projection。9.Interval类型值可比较PR #68057Interval 值参与比较时会自动转换到最小公共父类型least supertype此前此类比较不可用。10.create_if_not_exists设置PR #68164开启后CREATE语句默认按IF NOT EXISTS语义执行等价于“创建语句幂等化”。仓库中该设置定义于 src/Core/Settings.cpp 第 8534 行附近默认false。11. 读取 Azure 与本地的 Iceberg 表PR #68210此前 Iceberg 读取主要面向 S3此版本补齐 Azure 和本地文件系统路径配合 hive 分区的按需读取优化PR #68963见性能节使用。12. 查询缓存按标签删除PR #68477SELECT 1 SETTINGS use_query_cache true, query_cache_tag abc; -- 之后可精确清理该标签的缓存 SYSTEM DROP QUERY CACHE TAG abc; -- 或清空整个缓存 SYSTEM DROP QUERY CACHE;另有一个配套安全修复max_result_rows溢出模式不为throw的查询不再允许使用查询缓存PR #69549防止被截断的错误结果被缓存污染。13. Named Collections 存储加密PR #68615命名集合named collections落盘时支持加密敏感连接信息不再明文可见。14.ripeMD160哈希函数PR #68639SELECT hex(ripeMD160(The quick brown fox jumps over the lazy dog)); -- 返回 37F332F68DB77BD9D7EDD4969571AD671CF9DD3B需要特别说明该功能在本 stable 日志末尾的“NOT FOR CHANGELOG”区中出现了回退记录“Revert Add RIPEMD160 function”PR #70005对应后续问题 #70034即最终随 24.9 稳定版流出的构建中该函数可能已被撤下——升级后请以实际构建的system.functions为准。15. URL 表引擎新增_headers虚拟列PR #68867url()表引擎现在暴露响应头虚拟列_headers便于把网关返回的头信息一并入库对应 issue #65026。16.system.projections系统表PR #68901新增系统表跟踪所有可用 projection。仓库中对应实现为 src/Storages/System/StorageSystemProjections.h可用于查询投影定义与状态。17.arrayZipUnalignedPR #69030为 Spark 兼容对应 Spark 的arrays_zip提供“按最短长度截断对齐”的数组 zipSELECT arrayZipUnaligned([1], [1, 2, 3]); -- 结果长度取最短数组即 1 个元素后续 PR #69576 进一步允许空参数与concat行为对齐。18. HTTP 头X-ClickHouse-Summary增加RealTimeMicrosecondsPR #69032无需查询system.query_log即可在 HTTP 响应头中直接拿到请求 CPU 时间。同样注意该 PR 在日志末尾出现回退记录“Revert include_real_time_execution_in_http_header”PR #69885最终形态以构建实际输出为准。19. Keeper 客户端新增cp/mv原子命令PR #69034clickhouse-keeper-client支持原子拷贝/移动节点底层依赖本版本新增的RemoveRecursiveKeeper 请求见性能节。20.arrayAUC新增scale参数PR #69717scale默认true可设为false以跳过归一化步骤对应 issue #69609。性能改进Performance Improvement24.9 在性能侧的投入集中在 Join、Merge、并行副本与对象存储访问共 15 项Hash Join 右表按键重排当右表键在 left/inner hash join 中“密集”时重排右表提升 join 性能PR #60341Join 惰性输出buildOutput阶段通过RowRefList/RowRef追加列实现懒输出并移除buildOutput循环中的is_join_get判断PR #63677文件系统缓存元数据异步加载缓存元数据加载移出启动关键路径加快服务重启PR #65736array/map构造函数优化常见输入形态有显著加速PR #67707ORC 字符串读取优化列中无 NULL 的常见情形走快速路径PR #67794Merge 调度开销降低减少 merge 各调度步骤的开销整体 merge 提速PR #68016S3 无凭据场景提速未设置 profile、未设置凭据且 IMDS 不可用如在云外机器上读公开桶时不再为 IMDS 探测付出时间代价PR #68082对应 issue #52771并行副本 mark 分配新算法基于一致性哈希决定各副本读取的 mark 数量针对不同读模式选择不同粒度PR #68424格式读取器去虚化尝试RowInputFormatWithNamesAndTypes中尝试 devirtualize 格式读取器PR #68437带键并行 Merge引入parallel merge with key最大化 CPU 利用率PR #68441ORC 输出字典编码阈值新设置output_format_orc_dictionary_key_size_threshold允许对字符串列启用字典编码显著减小 ORC 输出体积并提升读取性能PR #68591Hive 分区按需读文件hive 分区的元数据解析只读取所需文件PR #68963KeeperRemoveRecursive请求一次性删除节点及其整棵子树替代多次单节点删除PR #69332向量相似度索引并行写入向量化索引并行灌入数据加快插入PR #69493并行副本去重复杂度优化并行副本声明处理中 part 去重逻辑从 O(n²) 降到 O(n·log n)大 part 数/大分区数的表收益明显PR #69596。重要改进Improvement日志中 Improvements 一节多达 40 余条此处按主题归组覆盖全部条目。解析与类型推断小实体解析代码加固顺带修复DeltaLake 按 Bool 分区时分区值恒被解释为 falseExternalDistributed只用单个分片地址max_threads等设置打印为auto(N)带引号而非auto(N)PR #52503文本格式中 Date/DateTime 推断更严格仅当带小数部分才推断为DateTime64其余用DateTimedate_time_input_formatbest_effort时避免边角字符串被误推断PR #68382从 Variant/Dynamic 列做castOrDefault的改进内部类型完全不可转换时也能正常工作PR #67150移除 DeltaLake 中字典旧版 named collections 代码允许字典直接使用 DDL 创建的命名集合PR #68412关闭 issue #60936、#36890。可刷新物化视图Refreshable Materialized ViewPR #58934 带来一组重要增强追加模式... REFRESH EVERY 1 MINUTE APPEND ...只追加行而不整表覆盖失败重试默认关闭通过查询 SETTINGS 段配置新增SYSTEM WAIT VIEW name等待当前正在执行的刷新结束。认证与安全单用户支持多种认证方式并存认证方式可重置为最近添加的一种。官方特别提醒若同一集群要混跑 24.8 与 24.9过渡期建议设置max_authentication_methods_per_user 1以避免互操作报错PR #65277新增dns_allow_resolve_names_to_ipv4/dns_allow_resolve_names_to_ipv6两个选项可按地址族阻断连接PR #66895x509SubjectAltName用户标识支持通配符PR #68236外部 HTTP 认证默认使用 HTTP/1.1 而非 HTTP/1.0PR #68456gcs()表函数参数中的敏感信息脱敏PR #69611修复了CLICKHOUSE_PASSWORD在官方镜像 entrypoint 中的 XML 转义问题PR #69301。函数与文本处理upperUTF8/lowerUTF8不再只支持西里尔字母大小写转换任意语言均可如SELECT upperUTF8(Süden)返回SÜDENPR #65761 / #68523JSON 输出格式的 Unicode 编码修复保证特殊字节序列下仍生成合法 JSONPR #67938内嵌字典embedded dictionaries支持西班牙语PR #69035ODBC 从服务端配置读取http_max_triesPR #68128。观测性与诊断Merge 与 Mutation 增加 profile events便于内省PR #68015线程池Thread Pool新增一组观测指标PR #68674system.processors_profile_log新增plan_step_name与plan_step_description列PR #68954崩溃简短信息中加入 CPU 架构PR #69037restore_replace_external_engines_to_null/restore_replace_external_table_functions_to_null恢复模式修复表定义带 SETTINGS 时不再失败PR #69253大表/多 part 表上的索引分析阶段现在支持被 KILL 中断PR #69606。写入与存储新增用户级设置min_free_disk_bytes_to_perform_insert/min_free_disk_ratio_to_perform_insert防止往接近写满的磁盘执行插入PR #69376INSERT INTO ... SELECT支持 Values 格式异步插入async inserts携带查询参数PR #68741dateTrunc/toStartOfInterval支持Date32PR #68874CREATE TABLE AS支持复制PRIMARY KEY、ORDER BY等子句目前仅限 MergeTree 家族引擎PR #69076新增min_max实验性列统计支持数值列范围谓词如x 100估计PR #67013CPU 用量核算改用 cgroup 专属指标替代整机指标PR #62003clickhouse-client中 Ctrl-Z 挂起行为可配置ignore_shell_suspendPR #67134SHOW CREATE TABLE输出标识符引用策略新增output_format_always_quote_identifiers与output_format_identifier_quoting_style取值None/Backticks默认/DoubleQuotes/BackticksMySQLPR #68896DatabaseFactory支持自定义数据库引擎携带参数、设置与表覆盖类似StorageFactoryPR #69201MaterializedPostgreSQL 支持只同步部分列PR #69092关闭 issue #33748Keeper 内部通信支持更完整的 SSL 选项如带口令的私钥PR #69582建立 Keeper 新连接时不再阻塞重试PR #69148databasereplicatedddlworker::enqueuequeryimpl抢锁失败时先睡 10ms 再重试缓解忙等PR #69588PocoAbstractConfiguration新增getHost方法对配置值做 IP/域名合法性校验PR #69130。缺陷修复Bug Fix摘要本版本 Bug Fix 条目多达 79 项按主题分组概述均附 PR 编号以便溯源JSON/Dynamic 类型簇修复 joined block 流结构不匹配#68686、动态子列枚举#68582、动态子列序列化竞争#68953、JSON 解析默认值插 NULL 的解析错误#68955、Variant 排列permutation越界错误#68681、JSON/Dynamic 的uniq与GROUP BY结果错误#69203、子查询中解析动态子列#68824、以及将 Dynamic 标记为不安全主键类型#69311并行副本IN子句含 Decimal 转换时结果错误新分析器引入#67234、子查询 UNION 处理错误导致 “Duplicate announcement received for replica”#69146、Not-ready Set 问题#69264Replicated/DDL非正常重启后 “covered-by-broken” part 处理导致 ReplicatedMergeTree 启动失败#68584、metadata_version为 0 与元数据版本不一致导致 alter 失败#69274、restore replica后零拷贝无限循环#69293、SYSTEM SYNC REPLICA缺少 sync 副本模式#68326、创建 Replicated 数据库中途失败后无法重建#69102、TTL 带 WHERE 时 DatabaseReplicated 新建副本 METADATA_MISMATCH#69736、丢弃带 SETTINGS 表在零拷贝加密盘上的 UNFREEZE bug#68821属于改进节列出的修复、StorageS3Queue的tracked_file_ttl_sec拼写错误写成tracked_files_ttl_sec读取#69742轻量删除/Projection行数减少的 merge 现在会重建 projection#62364窗口与聚合lag/lead崩溃修复#68262回补 #67091 引入的回归、grouping sets 聚合数据 merge 修复#68744、anyHeavy状态合并可能出错#68950外部数据与格式Parquet 过滤下推在文件类型与声明类型严重不符时崩溃#68131临时规避input_format_parquet_filter_push_down 0#68494 为小补丁、getHyperrectangleForRowGroup在 Decimal64 文件对 DateTime 列不抛异常#69745、DeltaLake 复杂类型元数据解析#68836、Parquet/Arrow 的schema_inference_make_columns_nullable0行为恢复并引入auto新取值#68298分布式/虚拟列Distributed 表找回_table/_database虚拟列24.3 后丢失#68672、s3Cluster传递 structure 参数时列 DEFAULT 丢失#69147客户端只读用户--queries-file报 “Cannot modify log_comment” 修复#69175、管道到提前退出的进程时的数据竞争#69186、查询取消时进度显示竞争#69081、--multiquery下 explain AST insert 解析错误#69123访问控制LDAP 外部目录中删除/重命名角色导致崩溃#68355、RoleCache过期修复#67748、访问实体依赖恢复改进#69346物化视图/存储optimize_functions_to_subcolumns开启时写 MV 失败#68951、窗口视图因 flush 慢丢块#67983、system.view_refreshes的 Progress 大于 1#68378、Storage Join 左表可空列支持#66926哈希函数sipHash64Keyed/sipHash128Keyed/sipHash128ReferenceKeyed对空数组/空元组的 LOGICAL_ERROR#68630、map 键含数组时 materialized constant 问题#68731全文索引多列全文索引未在不同列间重置row_id导致错误过滤复现用例见 tests/queries/0_stateless/03228_full_text_with_multi_col.sql#68644其他值得注意的修复ALTER MODIFY ORDER BY元数据不一致#67436、fromModifiedJulianDay上界应为9999-12-31#67583、IN查询中元组索引不在首位#67626、正则标志处理#68389、PostgreSQL 风格::对 SQL 十六进制/二进制字面量如x414243::String#68482、SAMPLE n传整数的 bug#68499、mannWhitneyUTest样本量不等时出错#68556、Replicated 表 replica_name 含\t/\n导致 LogEntry 解析错误#68645、ALTER/MODIFY列后再MODIFY STATISTICS的 LOGICAL_ERROR#68820、异步插入期间表结构变更#68837、Content-Encoding缺失#68975、路径拼接出现//#69066、空异步插入 LOGICAL_ERROR#69080、向量相似度索引配合余弦距离未被使用#69090、INSERT INTO ... SELECT挤压squashing导致内存过高#69469、表名含点号时SHOW COLUMNS/SHOW INDEX失效#69514、sqidDecodeLOGICAL_ERROR#69451、24.6 S3Queue 或 Replicated 库建表失败#69454、materialize()对稀疏列应返回完整列#69429、gcs/azure连接串脱敏#69611/#69570、Keeper 多请求在 ZNOAUTH 后的预处理#69627、unique/GROUP BY语义修复#69203 已列、UNION提升后 plan 表达式描述错误#69124、Values 格式转换尊重格式设置#69149、异步插入 INFILE 格式按扩展名探测#69237、Prewhere 条件下移保持顺序#69560、SQL 安全对参数化视图生效#69984、CREATE OR REPLACE VIEW在存在依赖表时 DROP 旧视图失败#69907等。构建/测试/打包改进测试框架支持在 tags 之后以setting(min, max)形式指定随机设置的上下界例如index_granularity最小值不能太低否则超时PR #67875集成测试 flaky 检查按模块文件分组执行可为每个模块单独设超时避免慢测试吃光整体预算PR #68380dbms程序与clickhouse_functions库解耦PR #69914。此外日志中的 “NO CL ENTRY” 与 “NOT FOR CHANGELOG / INSIGNIFICANT” 两节是内部提交多为 CI 修复、测试去 flaky、依赖升级如 OpenSSL 3.2.3、curl 8.9.1、libpq 16.4以及若干 revert不面向用户承诺但其中“Revert RealTimeMicroseconds 头字段”“Revert RIPEMD160”两条对行为可见已在正文中标注。升级建议与总结结合本版本内容给出可操作的升级检查清单审计双重 SETTINGS 用法嵌套子查询中两处 SETTINGS 的取值优先级已改变就近原则回归相关 SQLReplicated 数据库建表规范移除显式 UUID、zookeeper_path、replica_name并对“曾显式指定参数 PERMANENTLY DETACH”的表制定 ATTACH 预案Dynamic 列语义回归类型数超上限不再降级 String且有多个 Dynamic 相关 bug 在本版集中修复建议对 JSON/Dynamic 密集型业务做专项测试混合集群认证24.8 与 24.9 混跑期间显式设置max_authentication_methods_per_user 1关注 JSON 类型与并行副本原生 JSON 类型、distinctJSONPaths内省函数、并行副本 O(n·log n) 去重与 mark 分配新算法是本次升级的主要收益点以实际构建为准ripeMD160与X-ClickHouse-Summary的RealTimeMicroseconds在日志中存在回退记录功能可用性以所部署构建的system.functions/ 实际响应头为准。总体上v24.9 是一个“类型系统 查询解析 并行读路径”三条主线并进的大版本JSON/Dynamic 类型能力定型、轻量删除细化到分区、并行副本在算法与协议层面持续优化。升级前通读本文所列不兼容变更升级后利用system.projections、查询缓存标签管理与新增 profile events 做效果验证即可平稳落地该版本。【免费下载链接】ClickHouseClickHouse® is a real-time analytics database management system项目地址: https://gitcode.com/GitHub_Trending/cli/ClickHouse创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考