Spring Bach 处理器更改块选择中使用的状态会影响已处理项目的数量

问题描述 投票:0回答:1

我遇到这样的情况:ItemReader 按状态选择表中的项目,而处理器更改状态(从 READY 到 PROCESSED)。 这些已处理的项目(当然)不会被覆盖在下一个块的选择中,导致某些项目根本没有被处理。

第一个块选择并处理 ID 为 1-10 的项目,正确地将状态设置为“已处理”

SELECT t.* FROM the_table t WHERE t.status = READY OFFSET 0 FETCH NEXT 10 ROWS ONLY;

下一个块尝试选择 ids 11-20 by

SELECT t.* FROM the_table t WHERE t.status = READY OFFSET 10 FETCH NEXT 10 ROWS ONLY;

但是由于 1-10 不再被覆盖到 select 中(被第一个块更改),所以 ids 21-30 被选择。项目 11-20 从未被处理

事实也证明,将块大小设置得足够大以覆盖所有潜在的 READY 项目可以提供所需的结果(编写器一次保存所有项目)。但这不是生产的解决方案,因为预计会有大量物品等。

这会导致某些项目根本不会被处理,具体取决于我设置了多少个并行块。

处理这种情况的标准解决方案是什么?

  • 预先选择要在下一步中处理的 ID?是否可以对上一步的结果进行 chunk 处理?
  • 如何在整个步骤中使用固定的项目列表(仅选择一次)

注意: 上面的选择被简化,因为 ItemReader 中使用了更复杂的选择,选择按特定列(ssn)分组的最新可处理项目,而 SUCCESS 状态下没有更新的项目

                    SELECT bi.*, ri.*
                    FROM ri_item ri
                             JOIN item bi ON ri.item_id = bi.id
                    WHERE (ri.ssn, bi.created_timestamp) IN
                          (SELECT ri2.ssn, MAX(bi2.created_timestamp)
                           FROM ri_item ri2
                                    JOIN item bi2 ON ri2.item_id = bi2.id
                           WHERE ri2.status IN
                                 ('READY', 'FAILED_RECOVERABLE')
                             AND bi2.created_timestamp > COALESCE((SELECT MAX(bi3.created_timestamp)
                                                                   FROM ri_item ri3
                                                                            JOIN item bi3 ON ri3.item_id = bi3.id
                                                                   WHERE ri3.status IN ('SUCCESS')
                                                                     AND ri3.ssn = ri2.ssn),
                                                                  TO_TIMESTAMP('1970-01-01', 'YYYY-MM-DD'))
                           GROUP BY ri2.ssn
                          )
                          )

谢谢你

编辑: 我尝试了这个建议,但结果是一样的。明显地。 谁能为我提供如何使用流程指示器模式的简单示例?是这样吗?

非常感谢!!

spring spring-batch
1个回答
0
投票

问题是块步骤中的处理器正在修改状态。然后下一个块的选择在不同的数据集上运行: 选择...偏移 10 限制 10

结果是作业运行时跳过了一半要处理的项目。

解决方案是使用“暂存模式”,它首先选择要处理到单独表中的 id,然后针对此固定暂存列表执行块选择。

可以在随后的某些清理步骤中清除暂存表

© www.soinside.com 2019 - 2024. All rights reserved.