Spring批处理和Spring任务调度器

Spring批处理和Spring任务调度器,spring,jakarta-ee,scheduled-tasks,spring-batch,Spring,Jakarta Ee,Scheduled Tasks,Spring Batch,所以我有两份工作,每个工作都有单独的微线程 JobA可以: sysout("JobA executed at "+new Date()); sysout("JobB executed at "+new Date()); JobB可以: sysout("JobA executed at "+new Date()); sysout("JobB executed at "+new Date()); 两者都可以在单独的xml中,也可以在一个xml中。但我目前对两者都有单独的xml。我用同样的方式

所以我有两份工作,每个工作都有单独的微线程

JobA可以:

sysout("JobA executed at "+new Date());
sysout("JobB executed at "+new Date());
JobB可以:

sysout("JobA executed at "+new Date());
sysout("JobB executed at "+new Date());
两者都可以在单独的xml中,也可以在一个xml中。但我目前对两者都有单独的xml。我用同样的方式定义了这两种工作:

<batch:job id="task_scheduler" restartable="false">
    <batch:step id="test_task_scheduler"
        allow-start-if-complete="true">
        <batch:tasklet ref="job1" />
    </batch:step>
</batch:job>

<bean id="job1" class="com.irsis.batch.tasklet.TestOut" />
<bean id="runScheduler" class="com.irsis.batch.taskscheduler.RunScheduler1" />
运行时,我有此异常

Could not autowire field: org.springframework.batch.core.Job com.irsis.batch.taskscheduler.RunScheduler1.job; nested exception is org.springframework.beans.factory.NoUniqueBeanDefinitionException: No qualifying bean of type [org.springframework.batch.core.Job] is defined: expected single matching bean but found 2: task_scheduler,task_scheduler2
顺便说一句,这是我的RunScheduler1.java文件

@Autowired 
JobLauncher jobLauncher;

@Autowired 
Job job;

public void run() {


    try {

        String dateParam = new Date().toString();
        JobParameters param = new JobParametersBuilder().addString("date",
                dateParam).toJobParameters();

        JobExecution execution = jobLauncher.run(job, param);
        System.out.println("Exit Status : " + execution.getStatus());

    } catch (Exception e) {
        e.printStackTrace();
    }

    System.out.println("Done");

}
现在我的问题是,SpringBatch是否可能有多个作业?因为从我的特例中我看到的是,它只期待一份工作

尽管我尝试了另一种方法。我在application-context.xml中做了类似的事情

<batch:job id="job" restartable="false">
    <batch:step id="test_task_scheduler"
        allow-start-if-complete="true">
        <batch:tasklet ref="job1" />
    </batch:step>
</batch:job>

<bean id="job1" class="com.irsis.batch.tasklet.TestOut" />
<bean id="runScheduler1" class="com.irsis.batch.taskscheduler.RunScheduler1" />


    <batch:job id="job2" restartable="false">
    <batch:step id="test_task2_scheduler"
        allow-start-if-complete="true">
        <batch:tasklet ref="job2" />
    </batch:step>
</batch:job>

<bean id="job2" class="com.irsis.batch.tasklet.TestOut2" />
<bean id="runScheduler2" class="com.irsis.batch.taskscheduler.RunScheduler2" />


<task:scheduled-tasks>
    <task:scheduled ref="runScheduler1" method="run"
        cron="*0 0/1 * 1/1 * ? " />

</task:scheduled-tasks>

<task:scheduled-tasks>
    <task:scheduled ref="runScheduler2" method="run"
        cron="0 0/2 * 1/1 * ? " />
</task:scheduled-tasks>

它运行第一个作业,然后无论何时尝试运行第二个作业,都会出现以下异常:

PreparedStatementCallback; SQL[插入批处理作业实例(作业实例ID、作业名称、作业密钥、版本)
数值(?,?,?)];错误:重复的键值违反了唯一性 约束“作业安装”详细信息:键(作业名称,作业键)=(作业, 8a87688793625c6f3b8f982dbe6689d2)已存在。;嵌套异常是 org.postgresql.util.PSQLException:错误:重复的键值 唯一约束“作业安装”详细信息:键(作业名称, 作业(U键)=(作业,8a87688793625c6f3b8f982dbe6689d2)已存在

更新:我想我要改变我的方法。另一个问题链接

谢谢,

Jet

这不是弹簧批次异常,更像是正常的弹簧接线异常。原因是您的
RunScheduler1
中可能有
@Autowired
作业属性的注释。现在,在您的上下文中,您将得到两个作业,一个id为
task\u scheduler
,另一个id为
task\u scheduler2
,Spring不知道您要连接到哪个特定的作业

一个简单的修复方法是简单地删除
@Autowired
,并通过以下方式通过xml插入引用:

<bean id="runScheduler" class="com.irsis.batch.taskscheduler.RunScheduler1" >
    <property name="job" ref="task_scheduler"/>
</bean>

更新:
您的唯一约束相关异常实际上是可能的-如果两个作业的参数完全匹配,则两个作业被认为是相同的,在您的情况下,对于两个不同的作业实例,日期在某种程度上是冲突的(我觉得Spring batch有一个小错误,因为toString方法的日期精度),因此出现了问题。我可以建议您再添加一个参数(比如您使用
UUID.randomUUID().toString()
)的自定义UUID),这将确保这两个作业参数是绝对唯一的,并且应被视为两个完全不同的作业实例。

这不是Spring批处理异常,而是正常的Spring连接异常。原因是您的
RunScheduler1
中可能有
@Autowired
作业属性的注释。现在,在您的上下文中,您将得到两个作业,一个id为
task\u scheduler
,另一个id为
task\u scheduler2
,Spring不知道您要连接到哪个特定的作业

一个简单的修复方法是简单地删除
@Autowired
,并通过以下方式通过xml插入引用:

<bean id="runScheduler" class="com.irsis.batch.taskscheduler.RunScheduler1" >
    <property name="job" ref="task_scheduler"/>
</bean>

更新:
您的唯一约束相关异常实际上是可能的-如果两个作业的参数完全匹配,则两个作业被认为是相同的,在您的情况下,对于两个不同的作业实例,日期在某种程度上是冲突的(我觉得Spring batch有一个小错误,因为toString方法的日期精度),因此出现了问题。我可以建议您再添加一个参数(使用
UUID.randomUUID().toString()
表示您的自定义UUID),这将确保两个作业参数是绝对唯一的,并且应被视为两个完全不同的作业实例。

这是spring注入问题。它们在名称引用中可能存在冲突。您可能需要使用@Qualifier来解决此问题。请检查此链接。

这是spring注入问题。它们的名称引用中可能存在冲突。您可能需要使用@Qualifier来解决此问题。请检查此链接。

我认为您正在一次又一次地传递相同的作业参数。。。为了运行作业。 尝试更改每次运行的作业参数

像--


我认为您正在一次又一次地传递相同的作业参数。。。为了运行作业。 尝试更改每次运行的作业参数

像--


嗨@BijuKunjummen我编辑了我的问题。我添加了RunScheduler1.java文件以供参考。能够运行项目,但无论何时开始执行作业,都会捕获异常。“作业不得为空。”我建议您只需关闭当前问题,然后重新打开特定问题-现在您已经提到了3个不同的问题,我已经为其中2个问题提供了答案。请按照您的建议进行操作。谢谢你的回答。在顶部提供了新的问题链接。hi@BijuKunjummen我编辑了我的问题。我添加了RunScheduler1.java文件以供参考。能够运行项目,但无论何时开始执行作业,都会捕获异常。“作业不得为空。”我建议您只需关闭当前问题,然后重新打开特定问题-现在您已经提到了3个不同的问题,我已经为其中2个问题提供了答案。请按照您的建议进行操作。谢谢你的回答。在顶部提供了新的问题链接。