查找X天以前的spring批处理实例

时间:2015-03-30 13:59:05

标签: java spring spring-batch

目前,我已经重新启动了spring-batch每小时运行的作业,并通过JobExplorer检查数据库是否失败的作业实例,它为失败的作业选取最新作业实例并重新启动最新执行。这工作正常但我们现在有新的请求不仅要重新启动最新的实例,而且还要重新启动X天窗口中的所有实例,我们应该从最旧的实例重新启动一个实例,直到它超出此窗口。

示例:

  • 作业A的实例jobInstance1在晚上8点失败
  • 作业A的实例jobInstance2在晚上9点失败
  • 第一次在晚上10点重新开始,并首先重新启动jobInstance1
  • jobInstance1现已成功
  • 在晚上11点重新开始第二次踢,然后重新开始jobInstance2

我在考虑两个选择:

  1. 使用JobExplorer以及List<JobInstance> getJobInstances(String jobName, int start, int count);int getJobInstanceCount(String jobName) throws NoSuchJobException;的组合,并通过查看开始时间来查看我要查找的内容
  2. 扩展JdbcJobInstanceDao并针对与JOB_INSTANCE加入的JOB_EXECUTION表格撰写我自己的查询并使用
  3. 是否有更好的方法来获取最多3天的某个作业的所有失败作业实例并将它们排在最前面?

    如果没有更好的方法,你对选项1和2有什么看法?

1 个答案:

答案 0 :(得分:0)

我最后编写了自己的JobInstanceDao作为Michael Minella建议。我只在重启工作中需要它,所以我没有延长弹簧批次,但我用弹簧批次作为例子。如果有人需要,这是实施:

package com.custom.package;

import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.List;

import org.joda.time.DateTime;
import org.springframework.batch.core.JobInstance;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.jdbc.core.simple.ParameterizedRowMapper;
import org.springframework.stereotype.Component;
import org.springframework.util.StringUtils;

@Component
public class CustomJobInstanceDao {

    public static final String BATCH_TABLE_PREFIX = "BATCH";

    private static final String GET_JOBS_WITH_STATUS_AFTER_DATE = "SELECT ji.JOB_INSTANCE_ID, ji.JOB_NAME FROM %PREFIX%_JOB_EXECUTION je LEFT JOIN %PREFIX%_JOB_INSTANCE ji "
            + " ON je.JOB_INSTANCE_ID = ji.JOB_INSTANCE_ID WHERE ji.JOB_NAME = ? AND je.STATUS = ? AND je.START_TIME > ? GROUP BY  je.JOB_INSTANCE_ID";

    private static final String GET_RUNNING_JOBS_AFTER_DATE = "SELECT ji.JOB_INSTANCE_ID, ji.JOB_NAME FROM %PREFIX%_JOB_EXECUTION je LEFT JOIN %PREFIX%_JOB_INSTANCE ji "
            + " ON je.JOB_INSTANCE_ID = ji.JOB_INSTANCE_ID WHERE ji.JOB_NAME = ? AND je.END_TIME is NULL AND je.START_TIME > ? GROUP BY  je.JOB_INSTANCE_ID";

    @Autowired
    private JdbcTemplate jdbcTemplate;

    public List<JobInstance> getJobInstancesWithStatusAfterStartDate(final String jobName, final String status,
            final DateTime afterStartTime) {

        return jdbcTemplate.query(getQuery(GET_JOBS_WITH_STATUS_AFTER_DATE), new Object[] {jobName, status,
                afterStartTime.toDate()}, new JobInstanceRowMapper());
    }

    public List<JobInstance> getRunningJobInstancesAfterStartDate(final String jobName, final DateTime afterStartTime) {

        return jdbcTemplate.query(getQuery(GET_RUNNING_JOBS_AFTER_DATE),
                new Object[] {jobName, afterStartTime.toDate()}, new JobInstanceRowMapper());
    }

    private String getQuery(final String base) {
        return StringUtils.replace(base, "%PREFIX%", BATCH_TABLE_PREFIX);
    }

    private final class JobInstanceRowMapper implements ParameterizedRowMapper<JobInstance> {

        public JobInstanceRowMapper() {
        }

        @Override
        public JobInstance mapRow(final ResultSet rs, final int rowNum) throws SQLException {
            final JobInstance jobInstance = new JobInstance(rs.getLong(1), rs.getString(2));
            // should always be at version=0 because they never get updated
            jobInstance.incrementVersion();
            return jobInstance;
        }
    }

}