nzw921rx commented on code in PR #10306:
URL: https://github.com/apache/seatunnel/pull/10306#discussion_r3510930714


##########
docs/zh/introduction/configuration/error-handling.md:
##########
@@ -0,0 +1,318 @@
+# 错误数据处理(实验性功能)
+
+在 SeaTunnel 中,默认行为:只要某个 Connector 或 Transform 抛出异常,**整个作业就会失败**。
+
+从本实验性能力开始,用户可以改变这一行为,由引擎 **捕获异常数据,将其路由到错误 Sink,并在条件允许时继续推进作业**。
+
+> **状态:实验性(Experimental)**
+>
+> 目前该能力只接入 Zeta 引擎,且经过验证的 Sink 实现为 JDBC Sink。Flink/Spark translation 
路径暂未使用这套机制。错误处理与行级错误路由默认关闭,配置和语义在后续版本中可能有调整。
+
+## 适用场景
+
+推荐启用错误处理的典型场景包括但不限于:
+
+- 大批量离线任务中存在少量脏数据(例如非法时间、字符串超长等);
+- Sink 表偶发出现主键或唯一约束冲突;
+- 需要在存在个别异常记录的情况下保持作业整体可用性,并将错误数据单独记录以便后续排查和补数。
+
+不建议或需谨慎启用错误处理的场景包括:
+
+- 对“所有合法数据必须严格写入”具有较强 at-least-once 或 exactly-once 语义要求;
+- 使用复杂的多表 Sink 并希望在多个表之间保持严格一致性语义的场景。
+
+## 整体思路
+
+启用错误处理后,Zeta 引擎对于每条记录的处理逻辑可概括为:
+
+1. 首先按照原有逻辑,由 Transform / Sink 正常处理该记录;
+2. 在处理过程中如发生异常,引擎会尝试区分:
+   - **行级错误**:由于该条数据本身引起的异常(例如数据格式错误、约束冲突等);
+   - **系统级错误**:例如连接中断、资源不足(OOM)等基础设施问题;
+3. 对于系统级错误,行为与默认一致:直接失败作业;
+4. 对于被判定为行级错误的情况,引擎会将该记录及异常信息交给 **错误处理器(ErrorHandler)**:
+   - `mode = LOG`:仅记录日志;
+   - `mode = ROUTE`:在记录日志的基础上,将错误记录写入单独配置的 **错误 Sink**(例如 JDBC 错误表)。
+
+其余正常记录仍会沿原有链路向下游传递。
+
+错误处理行为通过 **env 配置** 控制:
+
+- **阶段级(env)**:在 `env.transform_error_handler` / `env.sink_error_handler` 
中统一配置该阶段默认行为;
+- **全局(env)**:在 `env.error_handler` 中给所有阶段提供默认值。
+
+部分 Transform(例如 JsonPath、DataValidator)仍然保留自身早期的 `row_error_handle_way` 
等行错误控制选项,这些选项与本文介绍的引擎级错误处理机制可以并行存在,但目前尚未与 `env.*_error_handler` 做自动合并。
+
+## 核心概念
+
+### 模式(mode)
+
+配置中最常见的字段为 `mode`:
+
+- `DISABLE`:关闭该阶段的错误处理(默认行为);
+- `LOG`:仅记录行级错误日志,不路由到错误 Sink;
+- `ROUTE`:记录并将行级错误路由到错误 Sink。
+
+如果完全不配置上述选项,SeaTunnel 的行为与历史版本保持一致:任意异常都会导致作业失败。
+
+### 错误 Sink
+
+**错误 Sink** 是专门用于接收错误数据的一条 Sink,需要在 `..._error_handler.sink` 下进行配置,例如:
+
+```hocon
+env {
+  sink_error_handler {
+    mode = "ROUTE"
+
+    sink {
+      plugin_name = "Jdbc"
+      error_table = "orders_sink_error_basic"
+      # 这里配置错误表对应的 Jdbc Sink 选项
+    }
+  }
+}
+```
+
+一种常见用法是:
+
+- 主 Sink 写入业务表(例如 `orders_from_sink`);
+- 错误 Sink 写入错误表(例如 `orders_sink_error_*`),用于后续排查和补数。
+
+### 行级错误 vs 系统级错误
+
+在大多数情况下,用户无需手动编写逻辑来判断“是否为行级错误”。
+
+引擎会尝试区分:
+
+- **行级错误**:通常由单条数据本身导致,引擎可在配置允许时旁路该条数据并继续作业;
+- **系统级错误**:通常是连接中断、资源不足(OOM)等基础设施问题,会直接导致作业失败。
+
+当前版本的默认分类策略:
+
+- **Sink 阶段**:若 Sink Connector 未实现 
`SupportRowLevelErrorClassifier`,其异常将被当作系统级错误处理(即使配置了 `sink_error_handler` 
也会失败作业)。
+- **Transform 阶段**:若 Transform 未实现 
`SupportRowLevelErrorClassifier`,其异常将被当作系统级错误处理(即使配置了 `transform_error_handler` 
也会失败作业)。
+
+对于部分 Connector(例如 JDBC),Connector 本身会通过接口显式声明“哪些异常属于行级错误”。引擎会优先采用这类显式声明。
+
+只有实现了 `SupportRowLevelErrorClassifier` 的 
Connector/Transform,才能触发行级错误;否则所有异常都会被当作系统级错误处理并导致作业失败。
+
+> 说明
+>
+> 本文描述的是当前版本的 Zeta 引擎处理流程。后续会逐步推动更多内置 Transform 和引擎集成实现 
`SupportRowLevelErrorClassifier`,以便更准确地区分“行级错误”与“系统级错误”。
+
+### ROUTE 模式的可靠性范围
+
+在 Zeta 中,`ROUTE` 模式会在 checkpoint ack 前等待待写入的错误记录写入完成,并 flush 已配置的错误 Sink 
writer。若错误 Sink 写入或关闭失败,任务会失败,而不是仅记录日志后表现为正常关闭。
+
+当前实验性实现仅支持不需要 writer state、committer、aggregated committer 或 commit-info 
serializer 的错误 Sink。若配置的错误 Sink 启用了这类生命周期能力,作业会在初始化阶段快速失败,而不是在 
checkpoint/commit 语义不完整的情况下继续运行。例如,JDBC 错误 Sink 在 `ROUTE` 模式下不应开启 
exactly-once/XA 相关选项。
+
+该能力仍属于实验性功能。错误记录的最终投递语义取决于所配置错误 Sink Connector 自身的事务和提交行为,因此不应将其视为通用的 
exactly-once DLQ 保证。
+
+### Transform 阶段发生行级错误时会怎样
+
+当 Transform 被判定为行级错误时,**该条记录会从主链路中被丢弃**,不会进入后续 Transform,也不会进入下游 Sink:
+
+- 对 `map(...)`:返回 `null`,等价于“过滤掉该条记录”;
+- 对 `flatMap(...)`:返回空列表,等价于“丢弃该条记录”。
+
+如果同时开启了 `mode = ROUTE` 且配置了错误 Sink,则该条原始记录及异常信息仍可被写入错误表用于排查和补数。
+
+## 配置与参数说明
+
+### 配置位置
+
+错误处理目前主要通过 **env 配置** 生效:
+
+- **阶段级(env)**:在 `env.transform_error_handler` / `env.sink_error_handler` 
中统一配置该阶段默认行为,例如:
+
+  ```hocon
+  env {
+    transform_error_handler {
+      mode = "ROUTE"
+
+      sink {
+        plugin_name = "Jdbc"
+        error_table = "orders_transform_error_from_env"
+      }
+    }
+
+    sink_error_handler {
+      mode = "ROUTE"
+      queue_capacity = 10000
+      queue_overflow_policy = "FAIL"
+
+      sink {
+        plugin_name = "Jdbc"
+        error_table = "orders_sink_error_from_env"
+      }
+    }
+  }
+  ```
+
+- **全局(env)**:在 `env.error_handler` 中为所有阶段提供默认值,例如:
+
+  ```hocon
+  env {
+    error_handler {
+      mode = "LOG"
+      include_original_data = true
+      include_stacktrace = false
+    }
+  }
+  ```
+
+同名参数的覆盖顺序(由高到低):
+
+1. 阶段级 `env.transform_error_handler` / `env.sink_error_handler`;
+2. 全局 `env.error_handler`(默认 `DISABLE`)。
+
+各个 Transform / Sink 插件自身已有的错误处理选项(例如 JsonPath / DataValidator 的 
`row_error_handle_way`)目前与上述 env 配置**相互独立**:插件内部选项仅影响该插件内部行为,而 
`env.*_error_handler` 控制的是引擎级的行级错误旁路能力。
+
+### 通用参数一览
+
+| 参数                     | 类型     | 默认值   | 说明 / 取值                            
                                                     |
+|------------------------|--------|--------|------------------------------------------------------------------------------------------|
+| `mode`                 | String    | `DISABLE` | 
行级错误处理模式:`DISABLE`(关闭)、`LOG`(只记录)、`ROUTE`(记录并路由到错误 Sink)。                       
  |
+| `max_error_ratio`      | Double     | `0.0`   | 允许的错误比例,0.0–1.0;例如 `0.01` 
表示错误记录超过 1% 时失败作业;`0.0` 表示不按比例触发失败。                          |
+| `max_error_ratio_min_records` | Integer | `100`  | `max_error_ratio` 
的预热阈值:当总处理记录数小于该值时,不进行比例触发,避免在样本很小时误触发失败。 |

Review Comment:
   I think the default value of 100 here seems a bit low
   
   For example:
   A user has 200K records, with `max_error_ratio_min_records = 100` (the 
default, user didn't change it) and `max_error_ratio = 0.01`. In this case, 
even a single record failure causes the entire task to fail. Perhaps it would 
be safer to set a higher default and let users decrease it when needed — what 
do you think?
   
   
   



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: [email protected]

For queries about this service, please contact Infrastructure at:
[email protected]

Reply via email to