首页 > 解决方案 > 循环 SQL 语句

问题描述

我的代码获得 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 语句本身附近

编辑:我想避免重组工作或非常重的代码解决方案。我相信这可以通过我的 SQL 附近的一个简单循环来完成,但无法弄清楚逻辑

标签: javasql

解决方案


Spring Batch 提供了您正在寻找的面向块的处理模型。您可以编写一个 Spring Batch 作业,其面向块的步骤具有 5000 的块大小。

您可以在spring-batch-samples模块中找到许多如何编写此类作业的示例。


推荐阅读