Apache SeaTunnel 4 月有何新动作?连接器增强与 Zeta 稳定性提升等亮点速览

4 月份月报来啦!
17784906553240f9ed9e6752b03a3

https://github.com/apache/SeaTunnel

点击蓝字



关注我们

4 月份月报来啦!社区梳理了 2026 年 4 月份 Apache SeaTunnel 合入 origin/dev 的 31 个带 PR 号代码提交,从功能特性、性能优化、Bug 修复、架构改进展开,对如 Doris Stream Load 增强等关键变更做源码级拆解,并附上当月 PR 贡献者名单,快来看看你在名单上吗?

统计口径:只统计 origin/dev 分支在上述时间范围内的提交;不含其他分支(例如 release 分支)独立提交。
时间范围:2026-04-01 ~ 2026-04-30(含)

本月关键词:SeaTunnel;Zeta;Connector V2;Doris;JDBC;CDC;Metadata;Checkpoint;Continuous Discovery;E2E

1. 当月功能特性梳理

1.1 Doris Sink:Stream Load 重定向增强(#10715

Doris 的 Stream Load 经常出现 FE 返回 307 重定向到 BE的行为。该 PR 的核心是让连接器在遇到重定向/重定向跟随失败时,输出更可诊断的错误信息,并在 HTTP 客户端侧做重定向跟踪。

关键实现片段:

  • 重定向异常信息构造(包含 request、Location、direct_to_be、2pc、stage 等诊断字段):



















public static String buildFollowUpFailure(        String requestUrl,        String location,        boolean directToBe,        boolean enable2PC,        String requestStage,        String causeMessage) {    return String.format(            "stream load redirect follow-up failed after HTTP/1.1 307 Temporary Redirect, "                    + "request=%s, Location=%s, direct_to_be=%s, 2pc=%s, stage=%s, cause=%s. "                    + "Please check BE reachability, FE load, and consider benodes + direct_to_be=true when FE redirect is unstable.",            requestUrl,            location == null ? "<missing>" : location,            directToBe,            enable2PC,            requestStage,            causeMessage == null ? "<missing>" : causeMessage);}
来自提交 #10715.../DorisRedirectExceptionBuilder.java
  • 执行请求时跟踪最后一次 redirectLocation,并在 IOException 时包装成更可读的异常:























public static CloseableHttpResponse executeWithRedirectTracking(        CloseableHttpClient httpClient,        HttpUriRequest request,        String requestUrl,        boolean directToBe,        boolean enable2PC,        String requestStage) throws IOException {    HttpClientContext context = HttpClientContext.create();    try {        return httpClient.execute(request, context);    } catch (IOException e) {        String redirectLocation = resolveLastRedirectLocation(context);        if (redirectLocation != null) {            throw new DorisConnectorException(                    DorisConnectorErrorCode.STREAM_LOAD_FAILED,                    DorisRedirectExceptionBuilder.buildFollowUpFailure(                            requestUrl, redirectLocation, directToBe, enable2PC, requestStage, e.getMessage()),                    e);        }        throw e;    }}

来自提交 #10715.../HttpUtil.java

影响范围

  • Doris Sink 的错误定位体验显著提升:以前“stream load 失败”可能只看到笼统 IOException;现在能直接看到 Location、是否 direct_to_be、阶段信息。
  • 对生产价值:减少“偶发重定向/网络抖动”导致的排障时间。

1.2 File Source:FTP/SFTP/Local/HDFS 连续发现(#10473

在文件同步场景中,“一次性扫描”不够用,用户往往需要:

  • 目录持续有新文件时持续消费;
  • 配合 sync_mode=update 做增量/去重/更新策略。

该 PR 引入 FileDiscoveryMode.CONTINUOUS,并实现一个“定时扫描 + 增量入队 + 有界状态”的 SplitEnumerator。

关键实现片段:

  • 新的枚举模式:





public enum FileDiscoveryMode implements Serializable {    ONCE,    CONTINUOUS}

来自提交 #10473.../FileDiscoveryMode.java

  • Continuous Enumerator 的核心机制:定时扫描、将新 split 入队、把 state 控制在 in-flight 范围(避免无限增长):















public void open() {    scheduler = Executors.newSingleThreadScheduledExecutor(...);    scheduler.scheduleWithFixedDelay(            this::safeScanOnce,            0L,            Math.max(1L, scanInterval.toMillis()),            TimeUnit.MILLISECONDS);}public FileSourceState snapshotState(long checkpointId) {    synchronized (lock) {        // Store in-flight splits only to avoid unbounded state growth.        return new FileSourceState(new HashSet<>(inFlightSplits), jobStartTimeMillis);    }}
来自提交 #10473.../ContinuousMultipleTableFileSourceSplitEnumerator.java
  • 扫描时对“版本变化/重复入队”做抑制,避免 scanInterval 很短导致重复 split 风暴:























private boolean enqueueSplitIfAbsent(FileSourceSplit split, SplitVersion splitVersion) {    String splitId = split.splitId();    synchronized (lock) {        if (splitVersion != null && splitVersion.equals(knownSplitVersions.get(splitId))) {            return false;        }        if (pendingSplitIds.contains(splitId)) {            return false;        }        for (FileSourceSplit inFlight : inFlightSplits) {            if (Objects.equals(inFlight.splitId(), splitId)) {                return false;            }        }        pendingSplits.addLast(split);        pendingSplitIds.add(splitId);        if (splitVersion != null) {            knownSplitVersions.put(splitId, splitVersion);        }        return true;    }}

来自提交 #10473:.../ContinuousMultipleTableFileSourceSplitEnumerator.java

影响范围

  • 连接器能力从“批处理导入”向“目录持续同步”扩展,且通过有界状态设计避免 enumerator 状态无限膨胀。
  • 配合 DistCp/update 类场景更稳:避免重复 split 入队导致重复写入压力。

1.3 JDBC Sink:新增 batch_interval_ms 定时 flush(#10609

JDBC Sink 以往主要依赖 batch_size 达到阈值时刷写;这会造成一个典型问题:

  • batch_size 设得大以提升吞吐时,小流量场景 迟迟不 flush,数据延迟不可控。

该 PR 在 JDBC Sink 中引入 batch_interval_ms,实现“时间到就刷”的策略,并配套 E2E 用例验证“在任务结束前已写入”。

核心 E2E 断言(证明“定时 flush 在 job 完成前生效”):












given().ignoreExceptions()    .await()    .atMost(30, TimeUnit.SECONDS)    .pollInterval(2, TimeUnit.SECONDS)    .untilAsserted(() -> {        Assertions.assertFalse(jobFinished.get(), "Job should still be running ...");        int rowCount = getSinkRowCount("sink_batch_interval_timer");        Assertions.assertTrue(rowCount > 0,            "Timer flush should have written rows to the database BEFORE job completion "            + "(batch_size=100000 is never reached)");    });

来自提交 #10609JdbcSinkBatchIntervalIT.java

影响范围

  • 对“低吞吐但要求低延迟写入”的场景(例如准实时维表落库、审计日志落库)非常关键:把延迟上限从“等 batch_size”变为“等 batch_interval_ms”。

1.4 CDC:暴露 binlog/GTID/SourceTimestamp 元数据(#10667

在 CDC 同步中,很多用户需要拿到“事件来自哪里、位点是多少、源端时间戳”等信息,用于:

  • 延迟/堆积诊断(sourceTimestamp vs sinkTimestamp)
  • 数据血缘与审计
  • 与外部系统对齐 offset/GTID

该 PR 在 MetadataUtil 中增加对 BINLOG_FILE/BINLOG_POS/BINLOG_ROW/GTID/SOURCE_TIMESTAMP 的设置入口,并通过 CommonOptions 标记可透传元数据集合。

示例:










public static void setBinlogFile(SeaTunnelRow row, String file) {    row.getOptions().put(BINLOG_FILE.getName(), file);}public static void setGtid(SeaTunnelRow row, String gtid) {    row.getOptions().put(GTID.getName(), gtid);}public static void setSourceTimestamp(SeaTunnelRow row, Long sourceTimestamp) {    row.getOptions().put(SOURCE_TIMESTAMP.getName(), sourceTimestamp);}

来自提交 #10667seatunnel-api/.../MetadataUtil.java

影响范围

  • CDC 链路的可观测能力增强:用户可以在 Transform / Sink 侧读取这些 metadata 做日志、分流、告警等。

2. 当月 Bug 修复梳理

2.1 Zeta Checkpoint:notifyCompleted 失败处理收敛(#10705

问题类型:Checkpoint completed 通知链路(notifyCheckpointCompleted / notifyCheckpointEnd)存在异常时,如果处理分散,容易形成“部分状态推进、部分失败”的不一致。

该 PR 的核心是把 notifyCompleted 相关异常统一收敛到 coordinator 的错误处理路径:













try {    InvocationFuture<?>[] invocationFutures = notifyCheckpointCompleted(completedCheckpoint);    CompletableFuture.allOf(invocationFutures).join();    InvocationFuture<?>[] invocationFuturesForEnd = notifyCheckpointEnd(completedCheckpoint);    CompletableFuture.allOf(invocationFuturesForEnd).join();} catch (Throwable e) {    handleCoordinatorError(        "notify checkpoint completed failed",        e,        CheckpointCloseReason.CHECKPOINT_NOTIFY_COMPLETE_FAILED);    return false;}

来自提交 #10705CheckpointCoordinator.java

影响范围

  • Zeta 引擎 Exactly-once/Checkpoint 稳定性增强:失败更快、更一致地进入“可恢复/可终止”的状态机分支。

2.2 Zeta:防止“终态僵尸 job”在 master 切换后被恢复(#10692

这类问题的典型危害是:

  • job 实际已终止,但 HA 切换后被错误恢复 -> 重复写入/资源泄漏/状态污染。

该修复落在 CoordinatorService 与测试中(见提交清单)。

2.3 Zeta:避免 NPE(overviewMap 延迟初始化)(#10610

属于典型的“监控/overview 结构在特定初始化顺序下为空”问题,修复点在 CheckpointMonitorService

2.4 其他 Fix

  • #10729:取消任务卡住、临时清理失败的防护(涉及引擎 + 文件 sink committer)
  • #10674:Kingbase JDBC 容器测试偶发失败修复(E2E/CI 稳定性)
  • #10745:Hazelcast 序列化相关测试稳定性增强
  • #10754:CI 构建状态同步逻辑修复

3. 工程与架构改进

3.1 资源申请失败可观测增强(#10304

资源不足时,传统错误往往只有“no enough resource”,无法指导运维定位是:

  • 需要多少 slot
  • 实际拿到多少
  • 哪个 resourceProfile 首个失败

该 PR 在 ResourceRequestHandler 中构造更具体的 failureMessage(required/obtained/index/profile),并把异常更好地外显给上层(JobMaster 等)。

示例(截取关键构造逻辑):












String failureMessage =    String.format(        "Apply resource not success for job: %d, required: %d slots, obtained: %d slots, "        + "first unassigned resource at index %d: %s",        jobId,        resourceProfile.size(),        resultSlotProfiles.size(),        failedIndex,        resourceProfile.get(failedIndex));LOGGER.warning(failureMessage);completeRequestWithException(toExternalException(failureMessage, requestSlotWithRetryError));

来自提交 #10304ResourceRequestHandler.java

影响范围

  • 对“资源不足/worker 不可用/标签调度失败”的排障效率提升明显:错误信息从“抽象”变成“可执行”。

3.2 Zeta:本地 IDE 启动体验改善(#10742

修改点在 seatunnel-engine-server/pom.xml,属于开发者体验优化:降低本地调试/启动摩擦。

3.3 Zeta:REST 提交任务异常日志增强(#10696

提升异常输出质量,避免 REST 层吞掉关键堆栈或上下文。

3.4 文档体系化

4 月文档提交不只是“修错别字”,而是有明显的“体系化重构”趋势:

影响范围

  • 对“新用户快速上手”和“贡献者理解架构”是直接收益:文档从散点变为结构化入口。

4. 本月PR贡献者榜

177849065650328dbc8221110e393

5. 版本演进趋势与技术发展方向

  • Connector 方向:更贴近生产复杂性


    Doris 重定向链路增强、文件源连续发现、JDBC 定时 flush、RocketMQ OptionRule 补全,都是“线上更容易踩坑的边界条件”被产品化。
  • Zeta 方向:稳定性与可观测优先


    Checkpoint 通知失败收敛、HA 场景的僵尸 job 恢复防护、REST 异常日志增强、资源申请失败信息增强,体现了“让问题更可见、更可恢复”的路线。
  • CDC 方向:把元数据作为一等公民


    binlog/GTID/source timestamp 的透出,意味着后续更容易做端到端延迟治理、审计与血缘能力。
  • Docs 方向:从“零散说明”走向“体系化架构入口”


    #10785 的大规模文档重组 + 多个 Javadoc PR,明显在为更大规模贡献者/用户群做准备。

附录:2026 年 4 月全部提交清单

  1. 2026-04-21 / #10729 / 2c81f7f / [Fix][Zeta] prevent cancel stuck and downgrade tmp cleanup failure
  2. 2026-04-21 / #10715 / 6af9ed0 / [Feature][Connectors-v2] Add Doris sink redirect enhancement
  3. 2026-04-21 / #10759 / 5111281 / [Improve][Connectors-v2][ORC] parse config on file level rather than field level
  4. 2026-04-20 / #10304 / 1d37f8c / [Improve][Engine] Enhance logging and exception handling for resource allocation failures
  5. 2026-04-19 / #10778 / 6d2a104 / Test/rocketmq restore e2e
  6. 2026-04-19 / #10743 / b9cdfeb / [Feature][E2E] Add MySQL CDC multi-database multi-table E2E test
  7. 2026-04-19 / #10705 / b70e84f / [Fix][Zeta] Converge notifyCompleted failure handling in CheckpointCoordinator
  8. 2026-04-19 / #10742 / b9b30b5 / [Improve][Zeta] Improve engine-server local IDE startup experience
  9. 2026-04-19 / #10785 / bf3eefe / [Docs] Reorganize SeaTunnel onboarding and architecture docs
  10. 2026-04-18 / #10577 / ac71b05 / [Docs][API] Add Javadoc to MultiTableSinkWriter
  11. 2026-04-16 / #10769 / ae8b96c / [Improve][Docs] Fix hive document error
  12. 2026-04-15 / #10764 / 39a25bd / [Chore][Tools] Add project PR submission skill
  13. 2026-04-14 / #10692 / 2ab8824 / [Fix][Zeta] Prevent terminal-state zombie jobs from being restored after master switch
  14. 2026-04-13 / #10754 / f3e5051 / [Fix][CI] Sync build status for recent PRs regardless of mergeable state
  15. 2026-04-12 / #10737 / 4752cee / [Docs][Connector-V2][Jdbc] Clarify save mode limitation in query mode
  16. 2026-04-12 / #10751 / 18c03db / Disable ASF Dependabot update PRs
  17. 2026-04-10 / #10741 / 8f03dfd / [Docs][Zeta] Clarify OSS checkpoint bucket URI format
  18. 2026-04-10 / #10745 / 26b30cf / [Fix][CI] Stabilize pipeline cleanup Hazelcast serialization test
  19. 2026-04-10 / #10609 / 4a8298d / [Feature][JDBC] Add batch_interval_ms option for JDBC Sink time-based flushing
  20. 2026-04-10 / #10689 / fc2d209 / [Improve][CI] Optimize update build status workflow
  21. 2026-04-09 / #10707 / df6ca72 / [Docs][Core] Add Javadoc to SupportResourceShare and MultiTableResourceManager
  22. 2026-04-09 / #10728 / 45127cd / [Docs] Fix 404 broken links in docs
  23. 2026-04-08 / #10704 / 93bba1a / [Improve][Docs] Iceberg connector adds parameter documentation related to Kerberos authentication
  24. 2026-04-08 / #10719 / 815cfc0 / [Docs][Core] Add Javadoc to CoordinatorService scheduling and HA flow
  25. 2026-04-06 / #10667 / 6dee790 / [Feature][CDC] Expose binlog file/pos/row, GTID, and SourceTimestamp …
  26. 2026-04-06 / #10713 / 9e7a0f6 / [Docs] Correct the key features in the zh documentation
  27. 2026-04-03 / #10610 / 1f81a8e / [Fix][Zeta] Prevent NPE by lazy initializing overviewMap
  28. 2026-04-03 / #10473 / 01cd08a / [Feature][Connector-V2] Add continuous discovery for FTP/SFTP/Local/HDFS file sources
  29. 2026-04-03 / #10696 / 9ad1832 / [Improve][Zeta] Enhance exception logging for task submission via RESTful API
  30. 2026-04-03 / #10701 / 7becf69 / [Improve][Connector-V2] Complete OptionRule declarations for RocketMQ source and sink
  31. 2026-04-02 / #10674 / b7a0fc5 / [Fix][E2E] Fix flaky CI failure in KingbaseDialectContainerTest

Apache SeaTunnel

Apache SeaTunnel是一个云原生的多模态、高性能海量数据集成工具。北京时间 2023 年 6 月1 日,全球最大的开源软件基金会ApacheSoftware Foundation正式宣布SeaTunnel毕业成为Apache顶级项目。目前,SeaTunnel在GitHub上Star数量已达9k+,社区达到7000+人规模。SeaTunnel支持在云数据库、本地数据源、SaaS、大模型等170多种数据源之间进行数据实时和批量同步,支持CDC、DDL变更、整库同步等功能,更是可以和大模型打通,让大模型链接企业内部的数据。




同步Demo

MySQL→Doris | MySQLCDC | MySQL→Hive | HTTP → Doris | HTTP → MySQL | MySQL→StarRocks|MySQL→Elasticsearch |Kafka→ClickHouse

新手入门

SeaTunnel 让数据集成变得 So easy!/ 3 分钟入门指南
0 到 1 快速入门 /初探/深入理解
分布式集群部署 | CDC数据同步管道 | Oracle-CDC
图片

最佳实践

中控技术天翼云多点OPPO | 清风马蜂窝孩子王哔哩哔哩唯品会众安保险兆原数通 | 亚信科技|映客|翼康济世|信也科技|华润置地|Shopee|京东科技|58同城|互联网银行|JPMorgan
图片

测试报告

SeaTunnel VS GLUE | VS Airbyte | VS DataX|SeaTunnel 与 DataX 、Sqoop、Flume、Flink CDC 对比
图片

源码解析

Zeta引擎源码解析(一) |(二) |(三)| API 源码解析 |2.1.1源码解析|封装 Flink 连接数据库解析





仓库地址:
https://github.com/apache/seatunnel
网址:
https://seatunnel.apache.org/
Apache SeaTunnel 下载地址:
https://seatunnel.apache.org/download
衷心欢迎更多人加入!
我们相信,在Community Over Code(社区大于代码)、「Open and Cooperation」(开放协作)、「Meritocracy」(精英管理)、以及「多样性与共识决策」The Apache Way 的指引下,我们将迎来更加多元化和包容的社区生态,共建开源精神带来的技术进步!
我们诚邀各位有志于让本土开源立足全球的伙伴加入 SeaTunnel 贡献者大家庭,一起共建开源!
提交问题和建议:
https://github.com/apache/seatunnel/issues
贡献代码:
https://github.com/apache/seatunnel/pulls
订阅社区开发邮件列表 :
dev-subscribe@seatunnel.apache.org
开发邮件列表:
dev@seatunnel.apache.org
加入 Slack:
https://join.slack.com/t/apacheseatunnel/shared_invite/zt-3uouszk3m-PtLLNyZsJVqE5Gb6gn24mA
关注 X.com:
https://x.com/ASFSeaTunnel


1778490659571eaca9d9dfb380e33
177849066043807a26525f5d4ce52
1778490662206e5050dd435c27685