pg_clickhouse 参考文档
描述
pg_clickhouse 是一个 PostgreSQL 扩展,用于在 ClickHouse 数据库上远程执行查询, 并提供一个 foreign data wrapper。它支持 PostgreSQL 13 及更高版本,以及 ClickHouse 23 及更高版本。
入门
尝试 pg_clickhouse 的最简单方式是使用 [Docker 镜像],该镜像基于标准 PostgreSQL Docker 镜像,并已预装 pg_clickhouse 和 [re2][re2 扩展] 扩展:
请参阅教程,以开始导入 ClickHouse 表并实现查询下推。
使用方法
版本策略
pg_clickhouse 的正式发布遵循 [Semantic Versioning] 语义化版本规范。
- 在 API 发生变更时递增主版本号
- 在保持向后兼容的 SQL 变更时递增次版本号
- 在仅有二进制级变更时递增补丁版本号
安装后,PostgreSQL 会跟踪两种版本号:
- 库版本 (在 PostgreSQL 18 及更高版本中由
PG_MODULE_MAGIC定义) 包含完整的语义化版本,可在pgch_version()函数或 Postgrespg_get_loaded_modules()函数的输出中看到。 - 扩展版本 (在控制文件中定义) 只包含主版本号和次版本号,可在
pg_catalog.pg_extension表、pg_available_extension_versions()函数的输出以及\dx pg_clickhouse中看到。
在实践中,这意味着一个只提升补丁版本的发布,例如从 v0.1.0 到 v0.1.1,会惠及所有已加载 v0.1 的数据库,而无需执行 ALTER EXTENSION 即可获得升级收益。
另一方面,一个提升次版本号或主版本号的发布会附带 SQL 升级脚本,所有包含该扩展的现有数据库都必须运行 ALTER EXTENSION pg_clickhouse UPDATE 才能获得升级收益。
DDL SQL 参考
以下 SQL DDL 语句使用 pg_clickhouse。
CREATE EXTENSION
使用 CREATE EXTENSION 将 pg_clickhouse 扩展添加到数据库中:
使用 WITH SCHEMA 将其安装到特定的 schema 中(推荐做法):
ALTER EXTENSION
使用 ALTER EXTENSION 来修改 pg_clickhouse。示例:
-
在安装 pg_clickhouse 的新版本后,使用
UPDATE子句: -
使用
SET SCHEMA将该扩展迁移到新的 schema:
DROP EXTENSION
使用 DROP EXTENSION 从数据库中删除 pg_clickhouse:
如果存在任何依赖 pg_clickhouse 的对象,此命令将失败。使用
CASCADE 子句可以一并删除这些对象:
CREATE SERVER
使用 CREATE SERVER 创建一个外部服务器,以连接到 ClickHouse 服务器。示例:
支持的选项有:
driver: 要使用的 ClickHouse 连接驱动,可以是 "binary" 或 "http"。必需。dbname: 连接时要使用的 ClickHouse 数据库。默认为 "default"。fetch_size: HTTP 流式传输的近似批次大小 (以字节为单位) 。批次 按行边界拆分。默认为50000000(50 MB) 。0会禁用 流式传输,并缓冲整个响应。外部表可以覆盖此 值。host: ClickHouse 服务器的主机名。默认为 "localhost"。port: 要连接到 ClickHouse 服务器的端口。默认值如下:- 当
driver为 "binary" 且host为 ClickHouse Cloud 主机时为 9440 - 当
driver为 "binary" 且host不是 ClickHouse Cloud 主机时为 9004 - 当
driver为 "http" 且host为 ClickHouse Cloud 主机时为 8443 - 当
driver为 "http" 且host不是 ClickHouse Cloud 主机时为 8123
- 当
ALTER SERVER
使用 ALTER SERVER 来修改外部服务器。例如:
可用选项与 CREATE SERVER 中的相同。
DROP SERVER
使用 DROP SERVER 来删除外部服务器:
如果有其他对象依赖于该服务器对象,则此命令将失败。使用 CASCADE 以同时删除这些依赖对象:
CREATE USER MAPPING
使用 CREATE USER MAPPING 将 PostgreSQL 用户映射到 ClickHouse 用户。例如,在通过外部服务器 taxi_srv 连接时,将当前 PostgreSQL 用户映射到远程 ClickHouse 用户:
支持的选项包括:
user: ClickHouse 用户名。默认为 "default"。password: ClickHouse 用户的密码。
ALTER USER MAPPING
使用 ALTER USER MAPPING 命令修改用户映射的定义:
这些选项与 CREATE USER MAPPING 中的相同。
DROP USER MAPPING
使用 DROP USER MAPPING 删除用户映射:
IMPORT FOREIGN SCHEMA
使用 IMPORT FOREIGN SCHEMA 将 ClickHouse 数据库中定义的所有表作为外部表导入到 PostgreSQL 架构中:
使用 LIMIT TO 将导入限制为特定的表:
使用 EXCEPT 排除表:
pg_clickhouse 将获取指定 ClickHouse 数据库(在上述示例中为 "demo")中的所有表清单,为每个表获取列定义,并执行 CREATE FOREIGN TABLE 命令来创建外部表。列将使用 支持的数据类型 进行定义,并在能够检测到的情况下,使用 CREATE FOREIGN TABLE 所支持的选项。
IMPORT FOREIGN SCHEMA 会对其导入的表名和列名运行 quote_identifier(),该函数会为包含大写字符或空格的标识符加上双引号。因此,这类表名和列名在 PostgreSQL 查询中必须使用双引号。全部为小写且不包含空格字符的名称则无需加引号。
例如,给定如下 ClickHouse 表:
IMPORT FOREIGN SCHEMA 会创建以下外部表:
因此,查询语句中必须正确加上引号,例如:
要创建名称不同或全部小写(因此不区分大小写)的对象,请使用 CREATE FOREIGN TABLE。
CREATE FOREIGN TABLE
使用 CREATE FOREIGN TABLE 创建可查询 ClickHouse 数据库中数据的外部表:
支持的表选项如下:
database:远程数据库的名称。默认为为外部服务器定义的数据库。fetch_size:HTTP 流式传输的近似批大小 (以字节为单位) 。会覆盖服务器级别的fetch_size。默认为50000000(50 MB) 。0会禁用流式传输并缓冲整个响应。table_name:远程表的名称。默认为为外部表指定的名称。engine:ClickHouse 表使用的[表引擎]。对于CollapsingMergeTree()和AggregatingMergeTree(),pg_clickhouse 会自动将这些参数应用于在该表上执行的函数表达式。
对每一列,请使用与远程 ClickHouse 数据类型相匹配的数据类型。 支持的列选项如下:
-
column_name:ClickHouse 侧的列名,在反向解析查询和 插入语句时,会优先使用它而不是 PostgreSQL 属性名。它可用于将未加引号的小写 PostgreSQL 列名映射到区分大小写的 ClickHouse 列,例如: -
AggregateFunction:应用于 [AggregateFunction 类型] 列的聚合函数名称。 将数据类型映射为传递给该函数的 ClickHouse 类型,并通过相应的列选项指定 聚合函数名称,pg_clickhouse 会自动为计算该列的聚合函数追加Merge。 -
SimpleAggregateFunction:应用于 [SimpleAggregateFunction 类型] 列的聚合函数名称。将数据类型映射为 传递给该函数的 ClickHouse 类型,并通过相应的列选项指定聚合函数名称。
ALTER FOREIGN TABLE
使用 ALTER FOREIGN TABLE 来更改外部表的定义:
受支持的表和列选项与 CREATE FOREIGN TABLE 相同。
DROP FOREIGN TABLE
使用 DROP FOREIGN TABLE 来删除外部表:
如果存在任何依赖该外部表的对象,此命令会失败。
使用 CASCADE 子句可以将它们一并删除:
DML SQL 参考
下面的 SQL DML 表达式可能会使用 pg_clickhouse。示例基于这些 ClickHouse 表:
EXPLAIN
EXPLAIN 命令按预期工作,但使用 VERBOSE 选项会触发
ClickHouse 发出 “Remote SQL” 查询:
此查询通过一个名为“Foreign Scan”的计划节点将远程 SQL 下推到 ClickHouse。
SELECT
使用 SELECT 语句在 pg_clickhouse 表上执行查询,如同对其他表一样:
pg_clickhouse 会尽可能将查询执行下推到 ClickHouse,包括聚合函数。使用 EXPLAIN 来确定下推的程度。以上述查询为例,整个执行过程都会下推到 ClickHouse。
pg_clickhouse 还会把对同一远程服务器上表的 JOIN 下推到 ClickHouse 执行:
如果不进行仔细调优,将本地表参与 JOIN 会导致查询效率较低。在本例中,我们创建一份 nodes 表的本地副本,并连接该本地表,而不是远程表:
在这种情况下,我们可以通过对 node_id 而不是对本地列进行分组,把更多聚合下推到 ClickHouse,并在之后再与查找表进行关联:
现在,“Foreign Scan” 节点会按 node_id 下推聚合,将必须回传到 Postgres 的行数从 1000 行(全部)减少到仅 8 行,每个节点一行。
PREPARE、EXECUTE、DEALLOCATE
自 v0.1.2 起,pg_clickhouse 支持参数化查询,主要通过 PREPARE 命令来创建:
像往常一样使用 EXECUTE 执行预备语句:
在 25.8 之前的 ClickHouse 版本中,参数化执行会导致 http driver
无法正确转换 DateTime 的时区;该底层缺陷 已在 25.8 中修复。
请注意,有时即使不使用 PREPARE,PostgreSQL 也会使用参数化查询计划。
对于任何需要精确时区转换但又无法升级到 25.8 或更高版本的查询,请改用
binary driver。
pg_clickhouse 像往常一样执行聚合下推,如在 EXPLAIN 的详细输出中所示:
请注意,这里发送的是完整的日期值,而不是参数占位符。
对于前五个请求都是如此,如 PostgreSQL 的
PREPARE notes 中所述。在第六次执行时,它会向 ClickHouse 发送
{param:type} 形式的[查询参数]:
参数:
使用 DEALLOCATE 释放预处理语句:
INSERT
使用 INSERT 命令将数据插入到远程 ClickHouse 表中:
COPY
使用 COPY 命令将一批行插入到远程 ClickHouse 表中:
⚠️ 批量 API 限制
pg_clickhouse 目前尚未实现对 PostgreSQL FDW 批量插入 API 的支持。因此,COPY 当前使用 INSERT 语句来插入记录。此行为将在未来版本中予以改进。
LOAD
使用 LOAD 语句加载 pg_clickhouse 共享库:
通常无需使用 LOAD,因为在首次使用其任一功能(函数、外部表等)时,Postgres 会自动加载 pg_clickhouse。
有一种情况使用 LOAD pg_clickhouse 会很有用:在执行依赖这些参数的查询之前,先通过 SET 设置 pg_clickhouse 参数。
SET
使用 SET 设置 pg_clickhouse 的自定义配置参数。
pg_clickhouse.session_settings
该参数用于配置后续查询中要应用的 ClickHouse settings。示例:
默认值为 join_use_nulls 1, group_by_use_nulls 1, final 1。将其设为空字符串以回退到 ClickHouse 服务器的设置。
语法为由逗号分隔的键值对列表,各键值对之间以一个或多个空格分隔。键必须对应 ClickHouse settings。值中的空格、逗号和反斜杠需要使用反斜杠进行转义:
或者使用单引号包裹的值以避免对空格和逗号进行转义;也可以考虑使用 dollar quoting,从而无需使用双引号:
如果你重视可读性,并且需要设置很多参数,可以使用多行,例如:
在某些情况下,如果某些设置会干扰 pg_clickhouse 本身的运行,这些设置将被忽略。这些设置包括:
date_time_output_format:http 驱动程序要求其为 "iso"format_tsv_null_representation:http 驱动程序要求使用默认值output_format_tsv_crlf_end_of_line:http 驱动程序要求使用默认值
除此之外,pg_clickhouse 不会验证这些设置,而是在每次查询时将它们传递给 ClickHouse。因此,它支持该 ClickHouse 版本的所有设置。
请注意,必须先加载 pg_clickhouse,然后才能设置
pg_clickhouse.session_settings;可以使用 shared library preloading,或者
直接使用扩展中的任一对象以确保其被加载。
pg_clickhouse.pushdown_regex
pg_clickhouse.pushdown_regex 参数用于控制 pg_clickhouse
是否将正则表达式函数和运算符下推。默认情况下会下推;
将此参数设为 false 可阻止下推:
详见正则表达式。
ALTER ROLE
使用 ALTER ROLE 的 SET 命令为特定角色预加载 pg_clickhouse,
并和/或为其SET参数:
使用 ALTER ROLE 的 RESET 命令来重置 pg_clickhouse 预加载设置和/或参数:
预加载
如果所有或几乎所有的 Postgres 连接都需要使用 pg_clickhouse, 可以考虑使用[共享库预加载]功能来自动加载它:
session_preload_libraries
对每个新的 PostgreSQL 连接都会加载共享库:
这样可以在无需重启服务器的情况下应用更新:只需重新连接即可。也可以通过 ALTER ROLE 为特定用户或角色单独设置。
shared_preload_libraries
在 PostgreSQL 父进程启动时将共享库加载到其中:
对于每个会话而言,这有助于节省内存并降低加载开销,但在更新该库时需要重启集群。
数据类型
pg_clickhouse 将以下 ClickHouse 数据类型映射到 PostgreSQL 数据类型。IMPORT FOREIGN SCHEMA 在导入列时使用 PostgreSQL 列中的第一个数据类型;其他类型可以在 CREATE FOREIGN TABLE 语句中使用:
| ClickHouse | PostgreSQL | 说明 |
|---|---|---|
| Bool | boolean | |
| Date | date | |
| Date32 | date | |
| DateTime | timestamptz | |
| Decimal | numeric | |
| Float32 | real | |
| Float64 | double precision | |
| IPv4 | inet | |
| IPv6 | inet | |
| Int16 | smallint | |
| Int32 | integer | |
| Int64 | bigint | |
| Int8 | smallint | |
| JSON | jsonb, json | |
| String | text, bytea | |
| UInt16 | integer | |
| UInt32 | bigint | |
| UInt64 | bigint | 当值大于 BIGINT 最大值时会报错 |
| UInt8 | smallint | |
| UUID | uuid |
后续部分将提供更多说明和详细信息。
BYTEA
ClickHouse 不提供与 PostgreSQL BYTEA 类型等效的类型,但允许将任意字节存储在 String 类型中。通常,ClickHouse 字符串应映射到 PostgreSQL 的 TEXT 类型,但在处理二进制数据时,应将其映射到 BYTEA。示例:
最终的 SELECT 查询将输出:
请注意,如果 ClickHouse 列中存在任何空字节(nul bytes),使用 TEXT 列的外部表将无法输出正确的值:
将输出:
请注意,第二行和第三行包含截断的值。这是因为 PostgreSQL 依赖以 nul 结尾的字符串,且不支持在字符串中包含 nul 字符。
尝试将二进制值插入 TEXT 列将会成功并按预期工作:
文本列将正确显示:
但是如果将它们读取为 BYTEA,则不会:
函数与运算符参考
函数
这些函数为对 ClickHouse 数据库进行查询提供接口。
clickhouse_raw_query
通过 ClickHouse 服务的 HTTP 接口连接、执行单个
查询,然后断开连接。可选的第二个参数指定连接字符串,
默认值为 host=localhost port=8123。支持的连接参数包括:
host:要连接的主机;必填。port:要连接的 HTTP 端口;默认是8123,除非host是 ClickHouse Cloud 主机,在这种情况下默认是8443。dbname:要连接的数据库名称。username:用于连接的用户名;默认是default。password:用于认证的密码;默认为无密码。
默认情况下,没有任何角色拥有执行此函数的 EXECUTE 权限;请考虑仅向
确实需要执行临时 ClickHouse 查询的角色GRANT访问权限,
例如专用的 ClickHouse 管理员角色:
适用于不返回记录的查询;对于有返回值的查询, 结果将作为单个文本值返回:
下推函数
pg_clickhouse 会下推条件 (HAVING 和 WHERE 子句) 中使用的部分 PostgreSQL 内置函数。该子集与 ClickHouse 中的等价函数的对应关系如下:
abs: absfactorial: factorialmod(int2/int4/int8/numeric): modulopow&power(float8/numeric): powround: roundsin,cos,tan,atan,atan2,sinh,cosh,tanh,asinh,degrees,radians,pi:对应同名的 ClickHouse 数学函数。asin、acos、atanh、acosh不会被下推:对于超出范围的输入,PG 会报错,而 CH 会返回NaN。date_part:date_part('day'): toDayOfMonthdate_part('doy'): toDayOfYeardate_part('dow'): toDayOfWeekdate_part('year'): toYeardate_part('month'): toMonthdate_part('hour'): toHourdate_part('minute'): toMinutedate_part('second'): toSeconddate_part('quarter'): toQuarterdate_part('isoyear'): toISOYeardate_part('week'): toISOYeardate_part('epoch'): toISOYear
date_trunc:date_trunc('week'): toMondaydate_trunc('second'): toStartOfSeconddate_trunc('minute'): toStartOfMinutedate_trunc('hour'): toStartOfHourdate_trunc('day'): toStartOfDaydate_trunc('month'): toStartOfMonthdate_trunc('quarter'): toStartOfQuarterdate_trunc('year'): toStartOfYear
extract(field FROM source):映射关系与date_part相同date(timestamp)&date(timestamptz): toDate (反向解析为 CH 别名date)array_position: indexOfarray_cat: arrayConcatarray_append: arrayPushBackarray_prepend: arrayPushFrontarray_remove: arrayRemovearray_length&cardinality: lengtharray_to_string: arrayStringConcatstring_to_array: splitByStringsplit_part: splitByString + 数组下标trim_array: arrayResizearray_fill: arrayWithConstantarray_reverse: arrayReversearray_shuffle: arrayShufflearray_sample: arrayRandomSamplearray_sort: arraySort / arrayReverseSortbtrim: trimBothltrim: ltrimrtrim: rtrimconcat_ws: concatWithSeparatorlower(text): lowerUTF8upper(text): upperUTF8substring(text, ...)&substr(text, ...): substringUTF8substring(bytea, ...)&substr(bytea, ...): substringlength(text): lengthUTF8length(bytea)&octet_length: lengthreverse(text): reverseUTF8reverse(bytea): reversestrpos: positionUTF8regexp_like: matchregexp_replace: replaceRegexpOne 或在带有g标志时使用 replaceRegexpOneregexp_split_to_array: splitByRegexpmd5: MD5json_extract_path_text: 子列表示法json_extract_path: toJSONString + 子列语法jsonb_extract_path_text: 子列语法jsonb_extract_path: toJSONString + 子列语法bit_count(bytea): bitCountto_timestamp(float8): fromUnixTimestampto_char(timestamp[tz], fmt): formatDateTime 当fmt是字符串常量,且其中每个关键字在 ClickHouse 中都有准确对应的等价项时。有关受支持的关键字,请参见“兼容性 说明”下的 to_char()。否则,该函数会在 PostgreSQL 本地求值。statement_timestamp、transaction_timestamp和clock_timestamp: nowInBlock64 (nowInBlock64(9, $session_timezone))CURRENT_DATE: now 和 toDate (toDate(now($session_timezone)))now、CURRENT_TIMESTAMP和LOCALTIMESTAMP: now64 (now64(9, $session_timezone))CURRENT_TIMESTAMP(n)&LOCALTIMESTAMP(n): now64 (now64(n, $session_timezone))CURRENT_DATABASE:作为值由 PostgreSQL 函数传入。CURRENT_SCHEMA:作为 PostgreSQL 函数返回的值传递。CURRENT_CATALOG:作为 PostgreSQL 函数返回的值传递。CURRENT_USER:作为 PostgreSQL 函数返回的值传递。USER:作为值由 PostgreSQL 函数传递。CURRENT_ROLE:作为值从 PostgreSQL 函数传递而来。SESSION_USER:作为值从 PostgreSQL 函数传递。
下推运算符
- 数组切片 (
arr[L:U]): arraySlice @>(数组包含) : hasAll<@(数组被包含) : hasAll&&(数组重叠) : hasAny~(正则匹配) : match!~(正则不匹配) : match~*(大小写不敏感的正则不匹配) : match!~*(大小写不敏感的正则不匹配) : match->>(将 JSON/JSONB 元素提取为文本) : sub-column syntax->(提取 JSON/JSONB 元素) : toJSONString + sub-column syntax
自定义函数
由 pg_clickhouse 创建的这些自定义函数,为部分在 PostgreSQL 中没有等价实现的 ClickHouse 函数提供外部查询下推功能。如果这些函数中的任意一个无法下推,则会抛出异常。
扩展下推
pg_clickhouse 可识别部分核心扩展和第三方扩展中的函数,并将其下推为 ClickHouse 中对应的等效函数。
re2
所有 [re2 扩展] 函数都会以 1:1 映射下推到 ClickHouse:
re2match→ matchre2extract→ extractre2extractall→ extractAllre2regexpextract→ regexpExtractre2extractgroups→ extractGroupsre2replaceregexpone→ replaceRegexpOnere2replaceregexpall→ replaceRegexpAllre2countmatches→ countMatchesre2countmatchescaseinsensitive→ countMatchesCaseInsensitivere2multimatchany→ multiMatchAnyre2multimatchanyindex→ multiMatchAnyIndexre2multimatchallindices→ multiMatchAllIndices
intarray
有一个 intarray 函数可下推到 ClickHouse:
idx→ indexOf
fuzzystrmatch
以下两个 fuzzystrmatch 函数会下推到 ClickHouse:
soundex: soundexlevenshtein(2 个参数) : editDistanceUTF8
下推类型转换
pg_clickhouse 会对兼容的数据类型下推诸如 CAST(x AS bigint) 形式的类型转换。
对于不兼容的类型,下推会失败;如果此示例中的 x 是 ClickHouse 的 UInt64,
ClickHouse 将拒绝执行该类型转换。
为了在不兼容的数据类型上也能进行下推类型转换,pg_clickhouse 提供了以下函数。 如果这些函数未被下推,就会在 PostgreSQL 中抛出异常。
可下推的聚合函数
这些 PostgreSQL 聚合函数可以下推到 ClickHouse 执行。
自定义聚合
这些由 pg_clickhouse 创建的自定义聚合函数,为部分在 PostgreSQL 中没有等价实现的 ClickHouse 聚合函数提供外部查询下推 (foreign query pushdown) 能力。如果其中任意函数无法下推,将抛出异常。
下推有序集合聚合函数
这些[有序集合聚合函数]会通过将其 直接参数 作为参数、将其 ORDER BY 表达式作为函数实参传入,从而映射到 ClickHouse 的[参数化聚合函数]。例如,下面这个 PostgreSQL 查询:
对应如下 ClickHouse 查询:
请注意,非默认的 ORDER BY 后缀 DESC 和 NULLS FIRST
不被支持,并会导致报错。
percentile_cont(double): quantilequantile(double): quantilequantileExact(double): quantileExact
下推窗口函数
这些 PostgreSQL [窗口函数] 可下推到 ClickHouse,并使用 OVER (PARTITION BY ... ORDER BY ...) 子句,在适用时也包含帧规范。
- row_number
- rank
- dense_rank
- ntile
- cume_dist
- percent_rank
- lead
- lag
- first_value
- last_value
- nth_value
min/max(带OVER子句)
排名函数 (row_number、rank、dense_rank、ntile、cume_dist、
percent_rank) 在下推时会省略其帧子句,因为 ClickHouse
不支持为这些函数指定帧规范。
兼容性说明
正则表达式
当 pg_clickhouse.pushdown_regex 为 true (默认值) 时,pg_clickhouse 会将正则表达式下推为 ClickHouse 中的等价形式,并尽力保证基本兼容性;但请注意两者之间的差异,以及 pg_clickhouse 对这些差异的处理方式。
-
PostgreSQL 支持 POSIX Regular Expressions,而 ClickHouse 支持 RE2 Regular Expressions。请注意两者在行为上的差异:当正则表达式由 ClickHouse 求值时 (例如在
WHERE子句中) ,请编写 RE2;当其由 Postgres 求值时 (例如在SELECT子句中) ,请编写 POSIX。 -
pg_clickhouse 会将 Postgres 的 [Regex flags] 追加到 ClickHouse 正则表达式前面,并放入
(?)中,以此下推这些标志。例如:会变成
注意这里包含了
-s;这是为了禁用 ClickHouse 默认启用的s,从而使其行为与 Postgres 正则表达式保持一致。 如果 Postgres 函数调用中的标志包含s,pg_clickhouse 就不会添加-s。遗憾的是,这种行为会破坏 Postgres 24 及更早版本中某些正则表达式的兼容性。 -
两者都支持、因此在由 ClickHouse 求值时可用的标志只有:
i:不区分大小写m:多行模式:s:让.匹配\np:部分换行敏感匹配 (处理方式与s相同)t:严格语法 (默认值,会被 pg_clickhouse 移除)
RE2 只支持这些标志;不要使用其他任何 Postgres flags
-
传递给正则表达式函数的任何其他标志,都会导致该函数无法下推。
-
例外情况是
regexp_replace(),它还支持g标志。当 设置了g时,pg_clickhouse 会使用replaceRegexpAll()而不是replaceRegexpOne(),并在添加其他标志前先移除该标志。 -
Postgres
regexp_replace()的替换参数支持使用\&引用整个匹配结果,而 ClickHouse 则使用\0表示整个匹配结果。请确保当该函数下推到 ClickHouse 时使用\0。
为避免任何歧义,建议设置 pg_clickhouse.pushdown_regex 以阻止 Postgres 正则表达式下推到 ClickHouse,并使用 [re2 扩展];对于该扩展,pg_clickhouse 支持将与 ClickHouse 兼容的 RE2 正则表达式直接下推。
to_char()
对于 timestamp 和 timestamp with time zone 类型,PostgreSQL 的 to_char() 仅在格式参数为非 NULL 的字符串常量,且其中每个 PostgreSQL 关键字在 ClickHouse 中都存在逐字节完全一致的对应项时,才会下推到 ClickHouse formatDateTime。如果格式是动态的 (不是 Const) ,或者包含任何不受支持的关键字或 modifier,则该调用会回退为在 PostgreSQL 本地求值——绝不会在部分翻译的情况下尝试下推,因此输出会保持与 PG 兼容。
用于 numeric、interval 及其他非时间戳类型的双参数 to_char() 形式永远不会下推;ClickHouse formatDateTime 只能格式化日期时间值。
已转换的关键字
| PostgreSQL | ClickHouse | 含义 |
|---|---|---|
YYYY, yyyy | %Y | 4 位年份 |
YY, yy | %y | 2 位年份 |
MM, mm | %m | 补零的月份 (01–12) |
DD, dd | %d | 补零的日期 (01–31) |
DDD, ddd | %j | 补零的一年中的第几天 (001–366) |
HH24, hh24 | %H | 补零的 24 小时制小时 (00–23) |
HH, hh, HH12, hh12 | %I | 补零的 12 小时制小时 (01–12) |
MI, mi | %i | 补零的分钟 (00–59) |
SS, ss | %S | 补零的秒 (00–59) |
Q, q | %Q | 季度 (1–4) |
Mon | %b | 月份简称,例如 Oct |
Dy | %a | 星期简称,例如 Mon |
AM, PM | %p | 上下午指示符,始终为大写 |
带引号的文本和字面量
用 "..." 包裹的文本会按原样传递,其中任何字面量 %
都会加倍为 %%,以转义 ClickHouse 的说明符前缀。在引号外的 \"
也会按字面量 " 原样传递。在 "..." 内,反斜杠
只会转义 ";其他反斜杠序列都会被视为字面文本。
作者
版权声明
Copyright (c) 2025-2026, ClickHouse