我的代码获取5,000行并进行了一些处理,然后停止。我想循环代码,以便在处理5,000行之后将获得另外5,000并再次处理。我希望它这样做直到没有更多的行了。
如果有人可以给我一个很棒的示例或伪代码,我将无法解决这个逻辑。
@Component("Inv226")
@Scope("prototype")
public class Inv226 extends BatchProgram {
@Override
public void process() {
// Make it so the printing goes to the result page.
this.webOn();
print(" ", false);
print("*****************************************", false);
print("** B.INV226 Begins: " + getTime() + " " + date(YearFormat.YYYY), false);
print("*****************************************", false);
// Find the first 5,000 records to remove.
//TODO find a way to keep looping
// and obtaining another set of 5,000 records
// when we're done processing each result set
Calendar limitDate = Calendar.getInstance();
limitDate.add(Calendar.DAY_OF_YEAR, -1095);
MList<Inv> delList = new MList<>(Inv.class, //
"CREATE_DATE < ? " //
+ "order by CREATE_DATE " //
+ "offset 0 rows " //
+ "fetch next 5000 rows ONLY", //
limitDate);
// Set the commit limit.
int commitLimit = 50;
int i = 0;
int delCount = 0;
// Loop through them...
for (Inv inv : delList) {
// Remove each.
inv.delete();
if (++i >= commitLimit) {
try {
this.commit();
print("Succesfully deleted " + i + " records");
delCount += i;
i = 0;
// Do we want a delay here?
} catch (MccMidusException mme) {
// Is this a timestamp mismatch?
if ("0080".equals(mme.getErrorCode())) {
// Poke the record so the next invocation of Eddbl will process it correctly,
// along with the other 49 records in this block.
// Assuming the poke is successful, processing on the remaining Edb003 records in the
// block of 5000 will continue.
this.getIoHarness().pokeUow(mme.getUow());
// Call commit to get a new transaction started.
this.commit();
// Reset the counter.
i = 0;
} else {
throw mme;
}
}
}
}
delCount += i;
// Ensure anything else gets committed.
this.commit();
print("*****************************************", false);
print("** B.INV226 TOTAL DELETES OF GBL RECORDS OLDER THAN " + Calendar.DAY_OF_YEAR, -1095, false);
print("** TOTAL RECORDS DELETED = " + delCount, false);
print("** EDD003 Cleanup Ends : " + date(YearFormat.YYYY) + " " + getTime(), false);
print("*****************************************", false);
print(" ", false);
this.webDone();
}
}
编辑:我知道我可能需要在SQL语句本身附近的某个地方添加另一个循环
edit:我想避免重组工作或代码繁重的解决方案。我相信可以通过在我的SQL附近进行一个简单的循环来完成此操作,但无法弄清楚逻辑
答案 0 :(得分:1)
Spring Batch提供了您正在寻找的chunk-oriented processing model。您可以使用面向块的步骤(块大小为5000)编写Spring Batch作业。
您可以在spring-batch-samples模块中找到许多有关如何编写此类作业的示例。
答案 1 :(得分:0)
好吧
从代码中快速判断,循环是删除行的地方,这意味着您一次加载5000行,并且可能需要重新运行脚本,直到没有剩余内容为止。
为什么不使用简单的SQL来检查数据库中剩余多少行,并有一个while语句来检查呢?
while(SELECT COUNT(*) FROM *tablename* > 0 ) {
*your code*
}
即使您在while循环中删除了行,当再次进行检查时,数据库也会为COUNT()
函数提供一个新值,这意味着它将进行检查,直到没有剩余的行为止。
答案 2 :(得分:0)
嗯,我最终解决了自己的问题。
这是代码段
while (true) {
MList<Fax> delList = new MList<>(Fax.class, //
"CREATE_DATE < ? " //
+ "order by CREATE_DATE " //
+ "offset 0 rows " //
+ "fetch next 5000 rows ONLY", //
limitDate);
if (delList.size() == 0) {
break;
}
这将连续执行代码,直到列表返回空白。感谢您的所有答复和想法。