3

Spring 文档(第 46 页,第 5.1.7 节)说:

默认情况下,无论是重试还是跳过,ItemWriter 抛出的任何异常都会导致 Step 控制的事务回滚。如果如上所述配置了跳过,则从 ItemReader 抛出的异常将不会导致回滚。

我的提交间隔设置为 10。所以我对上述段落的理解是,如果他们在读取 10 块中的第 7 条记录时出错,则该项目将被跳过,并且 itemReader 将提前发送正确的 9 条记录。

但是,如果在写入过程中第 7 条记录出错 - 这 10 条记录都不会被写入,并且会发生回滚。

但是,当我包含在我的 skipPolicy 中引发的错误时,itemWriter 正在将剩余的 9 条记录写入数据库,从而跳过错误的一条。这与上面提到的矛盾。

任何人都可以解释“在项目写作期间跳过”的概念。

此外,即使抛出单个错误,我也会得到以下信息:

在我的 shouldSkip(Object, Throwable) 方法中,SkipCount 两次为 -1,然后为 0,再次为 -1。- 我没有得到这种行为。

回滚计数也是 2 - 这是什么意思?为什么是 2 ?


@michael 您是否可以使用某些场景来解释行为!

就像“我正在从文件中读取 20 条记录并在经过一些处理后写入数据库。我为某些异常设置了跳过策略。如果异常发生在读取、处理、写入期间会发生什么——块将如何已提交,默认重试如何工作,计数将如何更新等等......”

这对我来说真的是一个很大的帮助,因为我仍然对这种行为感到困惑..

4

2 回答 2

9

从您的用例描述看来,您混合了不同的概念。

您描述了一个跳过场景,但您似乎期望跳过应该像无回滚场景一样工作。

来自春季批处理文档

跳过

处理过程中遇到的错误不应导致 Step 失败,而应跳过

无回滚

如果如上所述配置了跳过,则从 ItemReader 抛出的异常将不会导致回滚。

用我自己的话说,skip 的意思是:

如果该步骤在读取/处理/写入期间遇到错误,则当前块将被回滚,并且块中的每个项目都被单独读取/处理/写入 - 没有坏项目。基本上,Spring Batch 回退到坏块的提交率 1,并在坏块之后回到指定的提交率。

回滚计数也是 2 - 这是什么意思?为什么是 2 ?

B.5。BATCH_STEP_EXECUTION

ROLLBACK_COUNT:此执行期间的回滚次数。请注意,此计数包括每次发生回滚, 包括重试回滚和跳过恢复过程中的回滚

(强调我的)

此外,即使抛出单个错误,我也会得到以下信息:

在我的 shouldSkip(Object, Throwable) 方法中,SkipCount 两次为 -1,然后为 0,再次为 -1。- 我没有得到这种行为。

我尝试了一个具有两种配置样式的简单跳过作业,跳过策略和带有可跳过异常的跳过限制,两者在回滚和跳过计数方面的工作方式相同

(步骤元数据没问题,但 shouldSkip(...) 的调用似乎比预期的要多得多)

于 2011-07-18T09:19:19.647 回答
2

我想解释一下你提到的一个问题:

在我的 shouldSkip(Object, Throwable) 方法中,SkipCount 两次为 -1,然后为 0,再次为 -1。- 我没有得到这种行为。

我不知道shouldSkip()您指的是哪个方法的签名,但是在我的SkipPolicy界面中只有一个方法具有以下签名:

boolean shouldSkip(Throwable t, int skipCount) throws SkipLimitExceededException;

此方法决定是否应该跳过Exception e给定的。skipCount

不幸的是,Spring Batch 的程序员滥用这种方法来测试异常是否可以跳过,而不管当前的跳过计数如何skipCount这就是为什么在参数设置为的情况下多次调用此方法的原因-1

所以不要怀疑你看到的行为。

于 2013-05-15T13:05:43.320 回答