DLF Paimon 表全文检索

更新时间:
复制 MD 格式

DLF 支持基于 Tantivy 引擎为 Paimon Append-only 表的文本列创建全文索引。您可以通过 PyPaimon、Spark SQL 或 DLF 数据探查执行全文检索。

功能说明

全文检索基于 Tantivy 搜索引擎,为 Paimon Append-only 表的 STRING 类型列提供基于倒排索引的检索能力。适用于日志搜索、文档检索、内容过滤等场景。

特性

说明

索引引擎

Tantivy(Rust 实现,通过 JNI/Python 绑定调用)

支持的列类型

STRING(VARCHAR / CHAR)

搜索类型

关键词匹配、布尔查询(AND/OR)

使用限制

限制项

说明

表类型

仅支持 Append-only 表。

列类型

仅支持 STRING(VARCHAR / CHAR)列,不支持数值、数组等类型。

索引列数量

每个表只能对一个 STRING 列建全文索引。

索引构建

索引由 DLF 异步构建,写入数据后需等待构建完成才能搜索。

搜索精度

基于倒排索引的关键词匹配,非语义搜索。如需语义搜索,请参见构建 Global Index 实现查询加速和向量搜索

NULL 值

若文本列值为 NULL,该行不参与索引构建和全文搜索。

分词器

支持 defaultsimplewhitespacerawngramjieba。DLF 自动构建默认使用 default

前提条件

根据您的使用方式,确保满足以下环境要求:

  • PyPaimonpypaimon-1.5.dev20260727 尚未发布到公开 PyPI,需下载本文附件。平台要求为 Linux x86_64(glibc >= 2.28)。

    1. 下载并安装pypaimon-1.5.dev20260727.tar.gz及全文检索依赖:

      pip install 'pypaimon-1.5.dev20260727.tar.gz[full-text]'
    2. (可选)如需 DuckDB 输出格式,还需安装:

      pip install duckdb
  • Spark SQL:使用 Paimon Ali 1-ali-29.1,准备以下 JAR 并上传到 OSS:

    spark.emr.serverless.excludedModules              paimon
    spark.emr.serverless.user.defined.jars            oss://<your-bucket>/paimon-ali-emr-spark-3.5-1-ali-29.1.jar,oss://<your-bucket>/paimon-full-text-1-ali-29.1.jar,oss://<your-bucket>/paimon-full-text-index-0.1.0.jar

创建表并开启全文检索

通过 Spark SQL 创建

CREATE TABLE articles (
    id INT,
    title STRING,
    content STRING
) TBLPROPERTIES (
    'row-tracking.enabled' = 'true',
    'data-evolution.enabled' = 'true',
    'morax.full-text-index.enabled' = 'true',
    'global-index.full-text.index-column' = 'content'
);

建表参数说明

参数

说明

row-tracking.enabled = true

行级跟踪,用于关联索引与数据行。

data-evolution.enabled = true

数据演化,支持索引的增量构建和长期维护。

morax.full-text-index.enabled = true

开启全文索引自动调度。

global-index.full-text.index-column

索引列名,必须为 STRING 类型。

写入数据并触发索引构建

以下 INSERT 语句适用于 Flink SQL 和 Spark SQL:

INSERT INTO articles VALUES
    (1, 'lake storage', 'apache paimon is a lake storage format for big data'),
    (2, 'stream engine', 'flink is a stream processing engine for real time analytics'),
    (3, 'data evolution', 'paimon supports data evolution and row tracking features'),
    (4, 'query engine', 'spark sql can query paimon tables directly with high performance'),
    (5, 'distributed', 'ray data provides distributed data processing capabilities');

写入数据后:

  • DLF 自动调度全文索引构建。

  • 索引构建为异步任务,构建完成后查询自动使用索引加速。

  • 您可在 DLF 控制台查看全局索引构建进度:进入目标 Catalog > 目标表 > 文件列表页签,索引构建完成后可看到全文索引文件(如 tantivy-global-index-<UUID>.index)。

设置全文索引检查间隔

morax.full-text-index.check-interval 用于设置 DLF 检查是否需要提交全文索引构建任务的间隔,默认值为 1h。如需提高新写入数据进入全文索引的及时性,可以缩短检查间隔,例如:

ALTER TABLE articles SET TBLPROPERTIES (
    'morax.full-text-index.check-interval' = '5min'
);
说明

该配置本身不会固定占用 CU;当 DLF 检测到需要构建的新数据并提交索引构建任务时,任务会消耗 CU。检查间隔设置得越短,索引任务可能越频繁,CU 消耗也可能增加。建议根据数据写入频率、索引时效要求和 CU 成本综合设置。设置为 5min 仅表示每 5 分钟检查一次,不代表索引一定能在 5 分钟内构建完成。

全文搜索

方式一:通过 DLF 数据探查搜索

在 DLF 控制台的 AI 中心 > 数据探查页面,选择目标 Catalog 后,可以直接执行全文检索。例如,搜索 content 列中包含 paimon 的记录并返回 Top-10:

SELECT *
FROM full_text_search(
    'default.articles',
    'content',
    'paimon',
    10
);

在数据探查中,第三个参数直接填写需要检索的文本;表名支持 db.tablecatalog.db.table 格式。全文索引尚未构建完成时,查询可能没有结果。关于数据探查功能的更多信息,请参见数据探查

方式二:通过 PyPaimon 搜索

通过 PyPaimon 执行全文搜索,无需启动 Spark 引擎。

初始化 Catalog

执行全文搜索前需要初始化 Catalog 连接 DLF。完整参数说明请参见 PyPaimonRay Data

from pypaimon import CatalogFactory

CATALOG_OPTIONS = {
    "metastore": "rest",
    "uri": "http://<DLF-ENDPOINT>",  # VPC 环境使用 http://<REGION>-vpc.dlf.aliyuncs.com
    "warehouse": "<YOUR-CATALOG>",
    "token.provider": "dlf",
    "dlf.region": "<REGION-ID>",
    "dlf.access-key-id": "<ACCESS-KEY-ID>",
    "dlf.access-key-secret": "<ACCESS-KEY-SECRET>",
    "dlf.oss-endpoint": "<OSS-ENDPOINT>",
}

catalog = CatalogFactory.create(CATALOG_OPTIONS)

基本用法

执行全文搜索,获取匹配行 ID:

table = catalog.get_table('default.articles')

builder = table.new_full_text_search_builder()
builder.with_query(
    'content',
    '{"match":{"query":"paimon"}}'
)
builder.with_limit(3)
result = builder.execute_local()

根据搜索结果读取实际行数据:

read_builder = table.new_read_builder()
read_builder = read_builder.with_projection(['id', 'title', 'content'])
scan = read_builder.new_scan().with_global_index_result(result)
splits = scan.plan().splits()
table_read = read_builder.new_read()
df = table_read.to_pandas(splits)
print(df)

输出示例:

id

content

1

apache paimon is a lake storage format for big data

3

paimon supports data evolution and row tracking features

4

spark sql can query paimon tables directly with high performance

获取相关性分数

# 接续上方的 builder 和 result 变量
score_fn = result.score_getter()
for row_id in result.results():
    print(f"row_id={row_id}, score={score_fn(row_id)}")

输出示例:

row_id=0, score=1.0508
row_id=2, score=1.1567
row_id=3, score=1.0508

布尔查询

AND 模式(所有关键词都必须出现):

builder = table.new_full_text_search_builder()
builder.with_query(
    'content',
    '{"match":{"query":"data processing","operator":"And"}}'
)
builder.with_limit(10)
result = builder.execute_local()

输出示例:

id

content

5

ray data provides distributed data processing capabilities

OR 模式(默认,任一关键词出现即匹配):

builder = table.new_full_text_search_builder()
builder.with_query(
    'content',
    '{"match":{"query":"spark flink","operator":"Or"}}'
)
builder.with_limit(10)
result = builder.execute_local()

输出格式

PyPaimon 支持多种输出格式:

# PyArrow Table
arrow_table = table_read.to_arrow(splits)
print(arrow_table)
# DuckDB
conn = table_read.to_duckdb(splits, 'articles')
print(conn.execute('SELECT * FROM articles').fetchdf())

方式三:通过 Spark SQL 搜索

-- 搜索包含"paimon"的文章,返回 Top-3
SELECT *
FROM full_text_search(
    'articles',
    'content',
    '{"match":{"query":"paimon"}}',
    3
);

输出示例:

id

content

1

apache paimon is a lake storage format for big data

3

paimon supports data evolution and row tracking features

4

spark sql can query paimon tables directly with high performance

结合投影和过滤:

SELECT id, title
FROM full_text_search(
    'default.articles',
    'content',
    '{"match":{"query":"data"}}',
    10
)
WHERE id > 1;

full_text_search 函数参数说明:

参数

类型

说明

table_name

STRING

表名,支持 db.tablecatalog.db.table 格式。

column_name

STRING

文本列名,类型必须为 STRING。

query

STRING

JSON 格式的全文检索表达式。

limit

INT

返回结果数量。