Skip to main content

描述

Protobuf 格式即 Protocol Buffers 格式。 此格式需要外部 format schema,并且会在查询之间缓存。 ClickHouse 支持:
  • proto2proto3 语法。
  • Repeated/optional/required 字段。
为了确定表列与 Protocol Buffers’ 消息类型中各字段之间的对应关系,ClickHouse 会比较它们的名称。 这种比较不区分大小写,并且字符 _ (下划线) 和 . (点) 被视为等同。 如果某一列与 Protocol Buffers’ 消息中对应字段的类型不同,则会进行必要的转换。 支持嵌套消息。例如,对于以下消息类型中的字段 z
ClickHouse 会尝试查找名为 x.y.z 的列 (也可能是 x_y_zX.y_Z 等) 。 嵌套消息适合作为嵌套数据结构的输入或输出。 像下面这样在 protobuf schema 中定义的默认值不会生效,而是改用表默认值
如果消息包含 oneof,并且设置了 input_format_protobuf_oneof_presence,ClickHouse 会填充一个列,用于指示检测到的是 oneof 中的哪个字段。
表示存在性的列名必须与 oneof 的名称相同。 支持嵌套消息 (参见 basic-examples) 。也支持空消息。 允许的类型包括 Int8、UInt8、Int16、UInt16、Int32、UInt32、Int64、UInt64、Enum、Enum8 和 Enum16。 Enum (以及 Enum8 和 Enum16) 必须包含 oneof’ 的所有可能标签,另外还必须包含 0 以表示不存在,字符串表示形式并不重要。 设置 input_format_protobuf_oneof_presence 默认处于禁用状态。 ClickHouse 以 带长度分隔的 格式输入和输出 protobuf 消息。 这意味着每条消息前都应先写入其长度,编码为可变长度整数 (varint)

使用示例

读写数据

示例文件本示例中使用的文件可在 示例仓库 中找到
在本示例中,我们将把 protobuf_message.bin 文件中的一些数据读入 ClickHouse 表中,然后再使用 Protobuf 格式将其写回名为 protobuf_message_from_clickhouse.bin 的文件。 给定文件 schemafile.proto
如果你已经知道如何使用 Protobuf 格式序列化和反序列化数据,则可以跳过此步骤。我们将使用 Python 将一些数据序列化到 protobuf_message.bin 中,并将其读入 ClickHouse。 如果你想使用其他语言,请参见:“如何在常见语言中读取/写入带长度分隔的 Protobuf 消息”运行以下命令,在 与 schemafile.proto 相同的目录中生成一个名为 schemafile_pb2.py 的 Python 文件。该文件包含 表示你的 UserData Protobuf 消息的 Python 类:
现在,在与 schemafile_pb2.py 相同的 目录中创建一个名为 generate_protobuf_data.py 的新 Python 文件。将以下代码粘贴进去:
现在从命令行运行该脚本。建议你在 Python 虚拟环境中运行它,例如使用 uv
你需要安装以下 Python 库:
运行脚本以生成二进制文件:
创建一个与 schema 匹配的 ClickHouse 表:
通过命令行将数据插入表中:
您还可以使用 Protobuf 格式将数据重新写入二进制文件:
借助你的 Protobuf schema,你现在可以对 ClickHouse 写入文件 protobuf_message_from_clickhouse.bin 的数据进行反序列化。

使用 ClickHouse Cloud 读写数据

在 ClickHouse Cloud 中,你无法上传 Protobuf schema 文件。不过,可以使用 format_protobuf_schema 设置在查询中直接指定 schema。本示例将说明如何从本地 机器读取序列化数据,并将其插入 ClickHouse Cloud 中的表。 与前一个示例一样,请根据 Protobuf schema 在 ClickHouse Cloud 中创建表:
设置 format_schema_source 用于指定设置 format_schema 的来源 可能的取值:
  • ‘file’ (默认) :Cloud 中不支持
  • ‘string’:format_schema 是 schema 的字面内容。
  • ‘query’:format_schema 是用于获取 schema 的查询。

format_schema_source='string'

将数据插入 ClickHouse Cloud,并以字符串形式指定 schema,运行:
查询已插入表中的数据:

format_schema_source='query'

你也可以将 Protobuf schema 存储在表中。 在 ClickHouse Cloud 中创建一个用于插入数据的表:
将数据插入 ClickHouse Cloud,并将 schema 指定为要执行的查询:
查询已插入到表中的数据:

使用自动生成的 schema

如果你的数据没有外部 Protobuf schema,仍然仍可借助自动生成的 schema 以 Protobuf 格式导出/导入数据。 为此,请使用 format_protobuf_use_autogenerated_schema 设置。 例如:
在这种情况下,ClickHouse 将使用函数 structureToProtobufSchema根据表结构自动生成 Protobuf schema。随后,它会使用该 schema 以 Protobuf 格式序列化数据。 你也可以使用自动生成的 schema 读取 Protobuf 文件。在这种情况下,该文件必须使用相同的 schema 创建:
设置 format_protobuf_use_autogenerated_schema 默认启用,并在未设置 format_schema 时生效。 你也可以在输入/输出过程中,使用设置 output_format_schema 将自动生成的 schema 保存到文件中。例如:
在这种情况下,自动生成的 Protobuf schema 会保存到文件 path/to/schema/schema.capnp 中。

清除 Protobuf 缓存

要重新加载通过 format_schema_path 加载的 Protobuf schema,请使用 SYSTEM DROP ... FORMAT CACHE 语句。
最后修改于 2026年7月23日