第 26 关 · ★★★★

湖仓一体

Multi-Catalog、Hive / Iceberg / Paimon / Hudi / JDBC 与数据回写。

已点亮 · 最佳 分
湖仓一体 第 1 页

Day 26|Apache Doris 湖仓一体:Multi-Catalog、Hive、Iceberg、Hudi、Paimon 与 JDBC Catalog

课程阶段:第六阶段——湖仓与 AI
建议学习时长:4~6 小时
实验基线:Apache Doris 4.0.8 Stable / 4.1.3 Latest
本文核验日期:2026-08-18

前二十五天,我们已经完成 Doris 从基础认知、表设计、数据导入、查询加速,到执行内核、存储引擎、生产运维和安全治理的完整学习。企业数据平台继续向前演进时,数据通常已经分布在多个系统中:历史明细位于 Hive,开放表格式使用 Iceberg,CDC 结果沉淀在 Hudi,实时湖仓使用 Paimon,客户和组织信息仍保存在 MySQL、Oracle 或 PostgreSQL,面向高并发分析的结果则进入 Doris 内部表。

这类架构的难点集中在五个方面:

  1. 同一条分析链路需要访问多个元数据系统和存储系统;
  2. 数据搬运会引入延迟、重复存储、调度依赖和一致性成本;
  3. 远端文件数量、分区布局、对象存储延迟会直接影响查询稳定性;
  4. 元数据缓存带来性能收益,也会影响 Schema、分区和文件变化的可见时间;
  5. 不同表格式的查询语义、增量能力、历史版本和写回能力存在明显差异。

Apache Doris 的 Multi-Catalog 提供统一的三层命名空间和外部数据连接能力。学习者可以通过一套 SQL 访问 Doris 内部表、Hive、Iceberg、Hudi、Paimon 和关系数据库,并在联邦查询、数据入仓、外部写回三条路径之间做出工程选择。

Day 26 湖仓一体总览
Day 26 湖仓一体总览


一、今天要掌握什么

完成本篇后,学习者应具备以下能力:

  • 能够解释 Lakehouse、Multi-Catalog、External Catalog 与 Internal Catalog 的职责;
  • 能够说明 FE 元数据控制面和 BE 数据读取面的协同过程;
  • 能够根据 Hive、Iceberg、Hudi、Paimon 和 JDBC 的特点选择 Catalog;
  • 能够使用 catalog.database.table 编写跨 Catalog 查询;
  • 能够判断一条需求适合联邦查询、入仓加速或外部写回;
  • 能够设计 Metadata Cache 的 TTL、容量、刷新和观测方案;
  • 能够启用 Data Cache,验证冷查询、热查询和 Warm Up 的效果;
  • 能够通过分区、文件、Row Group、列裁剪和谓词下推减少远端扫描;
  • 能够为外部表收集统计信息,帮助 CBO 选择 Join 顺序和分布策略;
  • 能够使用 Compute Node 隔离湖仓重查询;
  • 能够评估 Kerberos、IAM Role、JDBC Driver、网络连通和权限治理;
  • 能够完成一份具有正确性、性能、稳定性和回滚条件的湖仓 POC 报告。

截至核验日,Apache Doris 官网将 4.1.3 标记为 Latest,将 4.0.8 标记为 Stable。本文以 4.x 通用能力为主体,对 include_table_list、统一 meta.cache.*、Paimon JDBC Catalog、Iceberg V3 Row Lineage 和 Data Cache 查询级限制等版本敏感能力单独标注。


二、湖仓一体解决的核心问题

传统数仓和数据湖常常形成两套独立体系。数据湖保留成本较低、格式开放、历史跨度大的原始数据;数仓提供稳定 Schema、查询性能、并发和数据服务。两套体系之间通过 Spark、Flink、Airflow 或自研调度不断搬运数据。

数据搬运具有明确价值。高频数据进入 Doris 内部表后,可以使用数据模型、索引、物化视图、Row Store、Workload Group 和高并发点查能力。问题在于,所有数据都提前搬运会产生新的成本:

  • 数百 TB 历史数据需要重复存储;
  • 新增一个分析问题可能先等待同步链路上线;
  • 同一份数据在湖、仓和下游应用之间形成多个版本;
  • 回补、重跑和 Schema 演进会扩大调度复杂度;
  • 低频数据长期占用高性能存储。

Doris Lakehouse 提供四类能力:

  1. 灵活访问:通过 Catalog 连接多种元数据服务和数据源;
  2. 高性能处理:使用 MPP、向量化、Pipeline、裁剪、缓存和统计信息执行外表查询;
  3. 多源联邦:在同一条 SQL 中 Join 内部表、湖表和 JDBC 小表;
  4. 数据处理闭环:把外部数据写入 Doris,或把处理结果写回 Hive、Iceberg、JDBC 等支持的外部系统。

湖仓一体总架构
湖仓一体总架构

Lakehouse 架构的价值来自数据路径选择。高频、稳定、需要低尾延迟的数据适合进入 Doris 内部表;低频历史数据可以保留在 HDFS 或对象存储;探索和核验需求可以先使用联邦查询;确认长期价值后,再通过 INSERT INTO SELECT、CTAS、异步物化视图或周期任务完成物化。


三、Multi-Catalog 的基本模型

3.1 两类 Catalog

Doris 中存在两类 Catalog:

类型 说明
Internal Catalog 固定名称为 internal,管理 Doris 内部表,不能创建、改名或删除
External Catalog 连接外部数据源,可以创建、修改、刷新和删除

External Catalog 保存连接属性、认证信息、名称映射和缓存配置。远端 Schema 仍由 HMS、Iceberg REST、Paimon Catalog 或关系数据库管理,数据文件仍位于 HDFS、S3、OSS、COS、OBS、GCS、Azure Blob 等存储系统。

删除 External Catalog 只会移除 Doris 中的映射。远端 Metastore、表和文件不会随之删除。这个边界对生产变更非常重要,Catalog 删除后的恢复重点是重建配置、凭据、权限和缓存策略。

3.2 三层命名空间

所有数据对象统一使用:

catalog.database.table

例如:

SELECT *
FROM hive_prod.sales_dw.fact_sales;

Doris 提供三种常见会话方式:

-- 方式一:完整限定名
SELECT * FROM iceberg_prod.sales.product_dim;

-- 方式二:切换 Catalog 和 Database
SWITCH iceberg_prod;
USE sales;
SELECT * FROM product_dim;

-- 方式三:直接切换到 catalog.database
USE iceberg_prod.sales;
SELECT * FROM product_dim;

用户属性 default_init_catalog 可以设置默认 Catalog。MySQL 命令行或 JDBC URL 显式指定 catalog.database 时,连接参数具有更高优先级。

三层命名空间
三层命名空间

3.3 Catalog 级过滤和大小写

大型 HMS 可能包含数千个数据库和数十万张表。每次完整枚举会增加 Metastore 压力,也可能导致客户端执行 SHOW TABLES 超时。Catalog 通用属性可以收敛同步范围:

CREATE CATALOG hive_prod PROPERTIES (
    "type" = "hms",
    "hive.metastore.uris" = "thrift://hms-host:9083",
    "include_database_list" = "sales_dw,ods",
    "include_table_list" = "sales_dw.fact_sales,ods.raw_events"
);

include_table_list 从 4.1.0 起支持。Catalog 级 lower_case_table_nameslower_case_database_names 同样从 4.1.0 起提供。远端存在 MyTablemytable 这类仅大小写不同的对象时,启用大小写不敏感模式会产生名称冲突,上线前需要完整扫描和验证。


四、控制面和数据面怎样协同

理解湖仓查询,需要把元数据和数据文件分开观察。

4.1 FE:元数据与计划控制面

FE 负责:

  • 解析三层对象名称;
  • 校验 Catalog、Database、Table 和 Column 权限;
  • 从本地缓存或远端 Metastore 获取 Schema、分区和文件信息;
  • 进行分区裁剪、谓词下推、列裁剪、Join Reorder 和分布策略选择;
  • 生成外表 Scan 的 Split 和 PlanFragment;
  • 调度 BE 执行,并汇总 Profile 和结果。

4.2 BE:远端数据读取与计算面

BE 负责:

  • 访问 HDFS、对象存储或关系数据库;
  • 读取 Parquet、ORC、Hudi、Paimon、Iceberg 文件和删除文件;
  • 执行解压、解码、谓词过滤、Runtime Filter、Join、聚合和排序;
  • 把热点远端文件写入 Data Cache;
  • 通过 Exchange 传输跨节点中间结果。

因此,Catalog 创建成功只证明 FE 可以保存配置和访问部分元数据。生产验收还要确认所有参与执行的 BE 能访问远端存储、DNS、证书、Kerberos Keytab、对象存储 Endpoint 和 JDBC 数据库。

控制面与数据面
控制面与数据面


五、五类 Catalog 的选择方法

Catalog 选型矩阵
Catalog 选型矩阵

5.1 Hive Catalog:既有离线数仓的入口

Hive Catalog 通过 Hive Metastore 或兼容服务获取数据库、表、Schema、分区和 Location。除了 Hive 表,它还可以读取使用 HMS 保存元数据的 Iceberg 或 Hudi 表。对于 Iceberg,官方更推荐使用专用 Iceberg Catalog,以获得更完整的 Snapshot、Branch、Tag、系统表和写入语义。

Hive Catalog 适合三类任务:

  • 直接查询 Hive 历史明细;
  • 将 Hive 数据写入 Doris 内部表;
  • 通过 Doris 处理后写回 Hive 表。

当前官方支持 Hive 1.x、2.x、3.x、4.x,常见文件格式包括 Parquet、ORC、Text、CSV 和 JSON。数据可以位于 HDFS,也可以位于多种对象存储。

典型创建语句:

CREATE CATALOG hive_prod PROPERTIES (
    "type" = "hms",
    "hive.metastore.uris" = "thrift://hms-host:9083",
    "fs.defaultFS" = "hdfs://nameservice1",
    "hadoop.username" = "doris"
);

fs.defaultFS 对只读查询可以省略;需要从 Doris 创建 Hive 表或写回数据时应显式配置。写回过程会使用 staging 目录,4.0.3 起可以通过 hive.staging_dir 调整临时路径,避免临时目录和目标表位于不同命名空间导致移动失败。

Hive Catalog 查询路径
Hive Catalog 查询路径

5.2 Iceberg Catalog:开放湖仓的完整表语义

Iceberg Catalog 支持多种元数据服务:

  • Hive Metastore;
  • Iceberg REST Catalog;
  • Hadoop FileSystem Catalog;
  • AWS Glue;
  • Alibaba DLF;
  • Iceberg JDBC Catalog;
  • AWS S3 Tables。

Iceberg 的核心是 Snapshot。每次 Append、Overwrite、Update、Delete 或 Merge 都会生成新的表状态。Doris 默认读取最新 Snapshot,也可以使用历史时间或 Snapshot ID:

SELECT *
FROM iceberg_prod.sales.product_dim
FOR TIME AS OF '2026-08-01 10:00:00';

SELECT *
FROM iceberg_prod.sales.product_dim
FOR VERSION AS OF 123456789;

Doris 还支持读取 Branch 和 Tag。3.1.0 起可以管理 Branch/Tag 和 Schema Change;4.1.0 起提供实验性的 Iceberg V3 Row Lineage 隐藏列 _row_id_last_updated_sequence_number,适合增量同步和审计验证。

当前 Iceberg 写入能力较完整,包括:

INSERT
INSERT OVERWRITE
UPDATE
DELETE
MERGE INTO
CTAS
Schema Change

这使 Doris 可以承担湖仓数据处理引擎角色:读取 Hive 或 JDBC 数据,完成 Join 和聚合,再把结果写入 Iceberg。写回链路需要测试并发提交、Snapshot 增长、Manifest 数量、对象存储请求和失败回滚。

Iceberg Snapshot 与写回
Iceberg Snapshot 与写回

5.3 Hudi Catalog:读取 CDC 沉淀结果

Hudi Catalog 复用 Hive Catalog,通过 HMS 获取表信息,并结合 Hudi Timeline、Meta Client 和文件系统视图完成读取。常见表类型包括:

  • Copy-on-Write:读取路径直接,写入侧承担合并成本;
  • Merge-on-Read:读取时合并 Base File 和 Log File,适合更高频更新。

Doris 支持普通快照查询、Time Travel 和 Incremental Query。Hudi Time Travel 使用 FOR TIME AS OF,不支持 FOR VERSION AS OF。增量读取可以使用 @incr 指定起止 Commit Time,并在执行计划中转化为对 _hoodie_commit_time 的过滤。

hudi.use_hive_sync_partition=true 可以直接使用 HMS 已同步的分区信息,效率更高;前提是 Hudi 写入任务持续把最新分区同步到 HMS。同步延迟会导致新分区暂时不可见。

当前 Hudi Catalog 支持查询加速和数据入仓,数据写回尚未支持。需要由 Flink 或 Spark 等 Hudi 写入引擎负责外部表更新。

5.4 Paimon Catalog:实时湖仓与变更语义

Paimon Catalog 支持 Filesystem、HMS、DLF 和 JDBC 元数据服务。Paimon JDBC Catalog 从 4.1.0 起提供,当前带有实验属性。

Paimon 查询能力包括:

  • 普通 Snapshot 查询;
  • Batch Incremental Query;
  • Time Travel;
  • Branch 和 Tag;
  • $snapshots$files$partitions$manifests 等系统表;
  • @options 选择指定 Snapshot、Tag、Watermark 或增量起点。

例如:

SELECT snapshot_id, commit_time
FROM paimon_prod.realtime.events$snapshots;

SELECT *
FROM paimon_prod.realtime.events
FOR VERSION AS OF 12;

Doris 当前对 Paimon 只开放读取能力。需要写入 Paimon 时,继续使用 Flink 或其他原生写入引擎。

Hudi 与 Paimon 增量语义
Hudi 与 Paimon 增量语义

5.5 JDBC Catalog:远端小表和按需集成

JDBC Catalog 支持 MySQL、PostgreSQL、Oracle、SQL Server、IBM DB2、ClickHouse、SAP HANA 和 OceanBase。执行链路依赖 Java 和 JDBC Driver,Doris 3.0+ 的 JDK 17 环境能够提供更好的整体性能。

JDBC Catalog 的生产边界需要明确:

  • 适合读取客户、组织、配置、汇率、字典等小表;
  • 适合把少量源库数据导入 Doris;
  • 适合核验和低并发跨源 Join;
  • 大表全量扫描会占用源库 CPU、IO、连接和网络;
  • Doris 无法改变远端数据库的物理索引和执行能力;
  • 下推失败时,可能把大量数据拉到 Doris 再过滤。

生产设计应使用源库只读账号,配置连接超时和 Fetch Size,限制并发,监控源库慢 SQL,并为大表准备 CDC 或批量入仓方案。

JDBC Catalog 使用边界
JDBC Catalog 使用边界


六、跨 Catalog 查询怎样执行

以下 SQL 同时访问 Hive 事实表、Iceberg 商品维表和 MySQL 客户维表:

SELECT
    h.dt,
    h.region,
    i.category,
    j.level,
    SUM(h.amount) AS sales_amount
FROM hive_prod.sales_dw.fact_sales AS h
JOIN iceberg_prod.sales.product_dim AS i
  ON h.product_id = i.product_id
JOIN mysql_business.business.customer AS j
  ON h.customer_id = j.customer_id
WHERE h.dt >= DATE '2026-08-01'
GROUP BY h.dt, h.region, i.category, j.level;

FE 会分别读取三个 Catalog 的 Schema 和统计信息,判断过滤选择率、Join 顺序、Build/Probe 侧和 Distribution。BE 读取 Hive/Iceberg 文件,并通过 JDBC 获取小维表数据。理想执行计划通常具备以下特征:

  • Hive 日期分区完成裁剪;
  • 只读取查询涉及的列;
  • Parquet/ORC Row Group 或 Iceberg 文件统计继续过滤;
  • MySQL 查询带有必要字段和过滤条件;
  • 小型 JDBC 维表进入 Broadcast Build 侧;
  • Runtime Filter 从维表或聚合 Build 侧下推到大事实表 Scan;
  • 最终只传输经过过滤和局部聚合的数据。

跨源 Join 的性能上限由最慢数据源决定。外部存储延迟、JDBC 源库负载、文件数量和元数据请求都可能形成长尾。生产 POC 需要同时保存 Explain、Query Profile 和外部系统监控。


七、外表查询的逐级裁剪

湖仓查询的第一原则是减少远端读取。Doris 可以在多个层级收缩数据范围:

  1. Catalog/Database 过滤:减少元数据范围;
  2. Partition Pruning:根据目录或表格式分区信息跳过无关分区;
  3. Manifest/File Pruning:利用 Iceberg Manifest、文件 Min/Max 等信息过滤文件;
  4. Row Group/Stripe Pruning:利用 Parquet Row Group 或 ORC Stripe 统计;
  5. Column Pruning:只读取 SQL 使用的列;
  6. Predicate Pushdown:在 Scanner 侧执行过滤;
  7. Runtime Filter:Join 运行时把 Build 侧条件发送给 Probe 侧 Scan;
  8. Vectorized Execution:使用列式 Block 批量解码和计算。

外表逐级裁剪
外表逐级裁剪

容易破坏裁剪的写法包括:

WHERE DATE_FORMAT(event_time, '%Y-%m-%d') = '2026-08-01'

更利于下推和分区裁剪的形式是:

WHERE event_time >= '2026-08-01 00:00:00'
  AND event_time <  '2026-08-02 00:00:00'

文件布局同样重要。数十万个极小 Parquet 文件会增加远端 LIST、文件打开、Footer 读取和调度开销。Doris 查询侧能够并行读取,却无法完全消除上游小文件设计带来的成本。湖仓治理需要在写入引擎侧持续执行文件合并和分区优化。


登录后可阅读本文完整内容。