我是Spring批次的新手,我有一个问题,我的写跳过计数被视为块的整个计数,而不仅仅是块中的无效记录。
例如,我正在读取500条记录,每个块的块大小为100条记录。
然后,如果第一个区块有2条无效记录,则该无效记录之后的所有记录都被称为无效,并带有“无效异常”,其中它们不是无效的。
因此,batch_step_execution中的write_skip_count为100,而不是2。
但是另一方面,具有无效记录的块得到重新处理,并且除了两个无效记录之外,所有记录都正确地到达目的地。功能已实现,但write_skip_count错误,导致我们无法显示正确的日志。请指出我在这里错过了什么。
我可以在下面看到日志,
检查重新抛出:count=1
在重试策略时再次引发:计数=1
在应用程序异常时启动事务回滚
下面是我们目前为止尝试过的代码片段,
<batch:step id="SomeStep">
<batch:tasklet>
<batch:chunk reader="SomeStepReader"
writer="SomeWriter" commit-interval="1000"
skip-limit="1000" retry-limit="1">
<batch:skippable-exception-classes>
<batch:include class="org.springframework.dao.someException" />
</batch:skippable-exception-classes>
<batch:retryable-exception-classes>
<batch:exclude class="org.springframework.dao.someException"/>
</batch:retryable-exception-classes>
</batch:chunk>
</batch:tasklet>
</batch:step>
尝试了一段时间后。我发现,当写入数据库时发生在块中并且此数据库没有事务管理器时,特别是当您的批处理作业从一个数据库数据源读取并写入另一个数据库数据源时。
在这种情况下,批处理失败整个块,跳过计数成为块大小。但是它稍后处理commit interval = 1的chuck,并且只跳过错误的记录并处理正确的记录。但是跳过写计数现在是不正确的,因为它应该只是不正确的记录计数。
为了避免这种情况,请为正在写入数据的数据库数据源创建事务管理器。
<bean id="SometransactionManager"
class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
<property name="dataSource" ref="SomedataSource" />
</bean>
然后在所有事务发生的步骤中使用事务管理器,
<batch:step id="someSlaveStep">
<batch:tasklet transaction-manager="SometransactionManager">
<batch:chunk reader="SomeJDBCReader"
writer="SomeWriterBean" commit-interval="1000"
skip-limit="1000">
<batch:skippable-exception-classes>
<batch:include class="java.lang.Exception" />
</batch:skippable-exception-classes>
<batch:listeners>
<batch:listener ref="SomeSkipHandler" />
</batch:listeners>
</batch:chunk>
</batch:tasklet>
</batch:step>
现在,写入期间的故障将在一个事务下发生,错误记录将得到妥善处理,并且只有错误记录会记录在写入跳过计数下的批处理表中。