From fc4a66516ac7048e610065628793c62dcc646db5 Mon Sep 17 00:00:00 2001 From: Mahmoud Ben Hassine Date: Wed, 7 May 2025 22:03:03 +0200 Subject: [PATCH] Make JobOperator extend JobLauncher Related to #4832 --- .../annotation/BatchRegistrar.java | 23 -------- .../support/DefaultBatchConfiguration.java | 29 +--------- .../batch/core/launch/JobOperator.java | 4 +- .../support/JobOperatorFactoryBean.java | 56 +++++++++++++------ .../launch/support/SimpleJobOperator.java | 29 ++-------- .../support/TaskExecutorJobLauncher.java | 10 ++-- .../annotation/BatchRegistrarTests.java | 3 +- .../support/JobOperatorFactoryBeanTests.java | 10 +--- .../support/SimpleJobOperatorTests.java | 14 +++-- .../resources/applicationContext-test2.xml | 5 -- .../OptimisticLockingFailureTests-context.xml | 11 +--- .../resources/simple-job-launcher-context.xml | 7 +-- .../xml/JobLaunchingGatewayParserTests.java | 4 +- .../misc/jmx/adhoc-job-launcher-context.xml | 13 +---- .../restart/stop/stopRestartSample.xml | 29 ++++++++-- .../job/skipSample-job-launcher-context.xml | 6 +- .../resources/simple-job-launcher-context.xml | 11 +--- .../stop/GracefulShutdownFunctionalTests.java | 5 +- .../stop/JobOperatorFunctionalTests.java | 15 +---- 19 files changed, 105 insertions(+), 179 deletions(-) diff --git a/spring-batch-core/src/main/java/org/springframework/batch/core/configuration/annotation/BatchRegistrar.java b/spring-batch-core/src/main/java/org/springframework/batch/core/configuration/annotation/BatchRegistrar.java index 2970db506..1c3164da6 100644 --- a/spring-batch-core/src/main/java/org/springframework/batch/core/configuration/annotation/BatchRegistrar.java +++ b/spring-batch-core/src/main/java/org/springframework/batch/core/configuration/annotation/BatchRegistrar.java @@ -52,8 +52,6 @@ class BatchRegistrar implements ImportBeanDefinitionRegistrar { private static final String JOB_REPOSITORY = "jobRepository"; - private static final String JOB_LAUNCHER = "jobLauncher"; - private static final String JOB_REGISTRY = "jobRegistry"; private static final String JOB_LOADER = "jobLoader"; @@ -67,7 +65,6 @@ class BatchRegistrar implements ImportBeanDefinitionRegistrar { .get(EnableBatchProcessing.class) .synthesize(); registerJobRepository(registry, batchAnnotation); - registerJobLauncher(registry, batchAnnotation); registerJobRegistry(registry); registerJobRegistrySmartInitializingSingleton(registry); registerJobOperator(registry, batchAnnotation); @@ -147,25 +144,6 @@ class BatchRegistrar implements ImportBeanDefinitionRegistrar { registry.registerBeanDefinition(JOB_REPOSITORY, beanDefinitionBuilder.getBeanDefinition()); } - private void registerJobLauncher(BeanDefinitionRegistry registry, EnableBatchProcessing batchAnnotation) { - if (registry.containsBeanDefinition(JOB_LAUNCHER)) { - LOGGER.info("Bean jobLauncher already defined in the application context, skipping" - + " the registration of a jobLauncher"); - return; - } - BeanDefinitionBuilder beanDefinitionBuilder = BeanDefinitionBuilder - .genericBeanDefinition(TaskExecutorJobLauncher.class); - // set mandatory properties - beanDefinitionBuilder.addPropertyReference(JOB_REPOSITORY, JOB_REPOSITORY); - - // set optional properties - String taskExecutorRef = batchAnnotation.taskExecutorRef(); - if (registry.containsBeanDefinition(taskExecutorRef)) { - beanDefinitionBuilder.addPropertyReference("taskExecutor", taskExecutorRef); - } - registry.registerBeanDefinition(JOB_LAUNCHER, beanDefinitionBuilder.getBeanDefinition()); - } - private void registerJobRegistry(BeanDefinitionRegistry registry) { if (registry.containsBeanDefinition(JOB_REGISTRY)) { LOGGER.info("Bean jobRegistry already defined in the application context, skipping" @@ -205,7 +183,6 @@ class BatchRegistrar implements ImportBeanDefinitionRegistrar { beanDefinitionBuilder.addPropertyReference("transactionManager", transactionManagerRef); beanDefinitionBuilder.addPropertyReference(JOB_REPOSITORY, JOB_REPOSITORY); - beanDefinitionBuilder.addPropertyReference(JOB_LAUNCHER, JOB_LAUNCHER); beanDefinitionBuilder.addPropertyReference(JOB_REGISTRY, JOB_REGISTRY); // set optional properties diff --git a/spring-batch-core/src/main/java/org/springframework/batch/core/configuration/support/DefaultBatchConfiguration.java b/spring-batch-core/src/main/java/org/springframework/batch/core/configuration/support/DefaultBatchConfiguration.java index 8f7c0ee36..00cbbd305 100644 --- a/spring-batch-core/src/main/java/org/springframework/batch/core/configuration/support/DefaultBatchConfiguration.java +++ b/spring-batch-core/src/main/java/org/springframework/batch/core/configuration/support/DefaultBatchConfiguration.java @@ -39,7 +39,6 @@ import org.springframework.batch.core.converter.StringToLocalTimeConverter; import org.springframework.batch.core.launch.JobLauncher; import org.springframework.batch.core.launch.JobOperator; import org.springframework.batch.core.launch.support.JobOperatorFactoryBean; -import org.springframework.batch.core.launch.support.TaskExecutorJobLauncher; import org.springframework.batch.core.repository.ExecutionContextSerializer; import org.springframework.batch.core.repository.JobRepository; import org.springframework.batch.core.repository.dao.AbstractJdbcBatchMetadataDao; @@ -145,27 +144,6 @@ public class DefaultBatchConfiguration implements ApplicationContextAware { } } - /** - * Define a job launcher bean. - * @param jobRepository the job repository - * @return a job launcher - * @throws BatchConfigurationException if unable to configure the default job launcher - * @since 5.2 - */ - @Bean - public JobLauncher jobLauncher(JobRepository jobRepository) throws BatchConfigurationException { - TaskExecutorJobLauncher taskExecutorJobLauncher = new TaskExecutorJobLauncher(); - taskExecutorJobLauncher.setJobRepository(jobRepository); - taskExecutorJobLauncher.setTaskExecutor(getTaskExecutor()); - try { - taskExecutorJobLauncher.afterPropertiesSet(); - return taskExecutorJobLauncher; - } - catch (Exception e) { - throw new BatchConfigurationException("Unable to configure the default job launcher", e); - } - } - @Bean public JobRegistry jobRegistry() throws BatchConfigurationException { return new MapJobRegistry(); @@ -175,20 +153,19 @@ public class DefaultBatchConfiguration implements ApplicationContextAware { * Define a job operator bean. * @param jobRepository a job repository * @param jobRegistry a job registry - * @param jobLauncher a job launcher * @return a job operator * @throws BatchConfigurationException if unable to configure the default job operator * @since 5.2 */ @Bean - public JobOperator jobOperator(JobRepository jobRepository, JobRegistry jobRegistry, JobLauncher jobLauncher) + public JobOperator jobOperator(JobRepository jobRepository, JobRegistry jobRegistry) throws BatchConfigurationException { JobOperatorFactoryBean jobOperatorFactoryBean = new JobOperatorFactoryBean(); - jobOperatorFactoryBean.setTransactionManager(getTransactionManager()); jobOperatorFactoryBean.setJobRepository(jobRepository); jobOperatorFactoryBean.setJobRegistry(jobRegistry); - jobOperatorFactoryBean.setJobLauncher(jobLauncher); + jobOperatorFactoryBean.setTransactionManager(getTransactionManager()); jobOperatorFactoryBean.setJobParametersConverter(getJobParametersConverter()); + jobOperatorFactoryBean.setTaskExecutor(getTaskExecutor()); try { jobOperatorFactoryBean.afterPropertiesSet(); return jobOperatorFactoryBean.getObject(); diff --git a/spring-batch-core/src/main/java/org/springframework/batch/core/launch/JobOperator.java b/spring-batch-core/src/main/java/org/springframework/batch/core/launch/JobOperator.java index a56947412..ac36f6b42 100644 --- a/spring-batch-core/src/main/java/org/springframework/batch/core/launch/JobOperator.java +++ b/spring-batch-core/src/main/java/org/springframework/batch/core/launch/JobOperator.java @@ -1,5 +1,5 @@ /* - * Copyright 2006-2024 the original author or authors. + * Copyright 2006-2025 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -42,7 +42,7 @@ import org.springframework.lang.Nullable; * @author Mahmoud Ben Hassine * @since 2.0 */ -public interface JobOperator { +public interface JobOperator extends JobLauncher { /** * List the {@link JobExecution JobExecutions} associated with a particular diff --git a/spring-batch-core/src/main/java/org/springframework/batch/core/launch/support/JobOperatorFactoryBean.java b/spring-batch-core/src/main/java/org/springframework/batch/core/launch/support/JobOperatorFactoryBean.java index 3a8983862..ed8425827 100644 --- a/spring-batch-core/src/main/java/org/springframework/batch/core/launch/support/JobOperatorFactoryBean.java +++ b/spring-batch-core/src/main/java/org/springframework/batch/core/launch/support/JobOperatorFactoryBean.java @@ -1,5 +1,5 @@ /* - * Copyright 2022-2024 the original author or authors. + * Copyright 2022-2025 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -17,15 +17,20 @@ package org.springframework.batch.core.launch.support; import java.util.Properties; +import io.micrometer.core.instrument.MeterRegistry; +import io.micrometer.core.instrument.Metrics; +import org.apache.commons.logging.Log; +import org.apache.commons.logging.LogFactory; import org.springframework.aop.framework.ProxyFactory; import org.springframework.batch.core.configuration.JobRegistry; import org.springframework.batch.core.converter.DefaultJobParametersConverter; import org.springframework.batch.core.converter.JobParametersConverter; -import org.springframework.batch.core.launch.JobLauncher; import org.springframework.batch.core.launch.JobOperator; import org.springframework.batch.core.repository.JobRepository; import org.springframework.beans.factory.FactoryBean; import org.springframework.beans.factory.InitializingBean; +import org.springframework.core.task.SyncTaskExecutor; +import org.springframework.core.task.TaskExecutor; import org.springframework.transaction.PlatformTransactionManager; import org.springframework.transaction.TransactionManager; import org.springframework.transaction.annotation.Isolation; @@ -46,6 +51,8 @@ import org.springframework.util.Assert; */ public class JobOperatorFactoryBean implements FactoryBean, InitializingBean { + protected static final Log logger = LogFactory.getLog(JobOperatorFactoryBean.class); + private static final String TRANSACTION_ISOLATION_LEVEL_PREFIX = "ISOLATION_"; private static final String TRANSACTION_PROPAGATION_PREFIX = "PROPAGATION_"; @@ -56,20 +63,25 @@ public class JobOperatorFactoryBean implements FactoryBean, Initial private JobRegistry jobRegistry; - private JobLauncher jobLauncher; - private JobRepository jobRepository; private JobParametersConverter jobParametersConverter = new DefaultJobParametersConverter(); + private TaskExecutor taskExecutor; + + private MeterRegistry meterRegistry = Metrics.globalRegistry; + private final ProxyFactory proxyFactory = new ProxyFactory(); @Override public void afterPropertiesSet() throws Exception { - Assert.notNull(this.transactionManager, "TransactionManager must not be null"); - Assert.notNull(this.jobLauncher, "JobLauncher must not be null"); - Assert.notNull(this.jobRegistry, "JobRegistry must not be null"); Assert.notNull(this.jobRepository, "JobRepository must not be null"); + Assert.notNull(this.jobRegistry, "JobRegistry must not be null"); + Assert.notNull(this.transactionManager, "TransactionManager must not be null"); + if (this.taskExecutor == null) { + logger.info("No TaskExecutor has been set, defaulting to synchronous executor."); + this.taskExecutor = new SyncTaskExecutor(); + } if (this.transactionAttributeSource == null) { Properties transactionAttributes = new Properties(); String transactionProperties = String.join(",", TRANSACTION_PROPAGATION_PREFIX + Propagation.REQUIRED, @@ -88,14 +100,6 @@ public class JobOperatorFactoryBean implements FactoryBean, Initial this.jobRegistry = jobRegistry; } - /** - * Setter for the job launcher. - * @param jobLauncher the job launcher to set - */ - public void setJobLauncher(JobLauncher jobLauncher) { - this.jobLauncher = jobLauncher; - } - /** * Setter for the job repository. * @param jobRepository the job repository to set @@ -112,6 +116,25 @@ public class JobOperatorFactoryBean implements FactoryBean, Initial this.jobParametersConverter = jobParametersConverter; } + /** + * Set the TaskExecutor. (Optional) + * @param taskExecutor instance of {@link TaskExecutor}. + * @since 6.0 + */ + public void setTaskExecutor(TaskExecutor taskExecutor) { + this.taskExecutor = taskExecutor; + } + + /** + * Set the meter registry to use for metrics. Defaults to + * {@link Metrics#globalRegistry}. + * @param meterRegistry the meter registry + * @since 6.0 + */ + public void setMeterRegistry(MeterRegistry meterRegistry) { + this.meterRegistry = meterRegistry; + } + /** * Setter for the transaction manager. * @param transactionManager the transaction manager to set @@ -155,7 +178,8 @@ public class JobOperatorFactoryBean implements FactoryBean, Initial SimpleJobOperator simpleJobOperator = new SimpleJobOperator(); simpleJobOperator.setJobRegistry(this.jobRegistry); simpleJobOperator.setJobRepository(this.jobRepository); - simpleJobOperator.setJobLauncher(this.jobLauncher); + simpleJobOperator.setTaskExecutor(this.taskExecutor); + simpleJobOperator.setMeterRegistry(this.meterRegistry); simpleJobOperator.setJobParametersConverter(this.jobParametersConverter); simpleJobOperator.afterPropertiesSet(); return simpleJobOperator; diff --git a/spring-batch-core/src/main/java/org/springframework/batch/core/launch/support/SimpleJobOperator.java b/spring-batch-core/src/main/java/org/springframework/batch/core/launch/support/SimpleJobOperator.java index 0932de9ba..bd8a46c7d 100644 --- a/spring-batch-core/src/main/java/org/springframework/batch/core/launch/support/SimpleJobOperator.java +++ b/spring-batch-core/src/main/java/org/springframework/batch/core/launch/support/SimpleJobOperator.java @@ -1,5 +1,5 @@ /* - * Copyright 2006-2024 the original author or authors. + * Copyright 2006-2025 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -86,17 +86,13 @@ import org.springframework.util.Assert; * @author Mahmoud Ben Hassine * @since 2.0 */ -public class SimpleJobOperator implements JobOperator, InitializingBean { +public class SimpleJobOperator extends TaskExecutorJobLauncher implements JobOperator, InitializingBean { private static final String ILLEGAL_STATE_MSG = "Illegal state (only happens on a race condition): " + "%s with name=%s and parameters=%s"; private ListableJobLocator jobRegistry; - private JobLauncher jobLauncher; - - private JobRepository jobRepository; - private JobParametersConverter jobParametersConverter = new DefaultJobParametersConverter(); private final Log logger = LogFactory.getLog(getClass()); @@ -108,9 +104,8 @@ public class SimpleJobOperator implements JobOperator, InitializingBean { */ @Override public void afterPropertiesSet() throws Exception { - Assert.state(jobLauncher != null, "JobLauncher must be provided"); + super.afterPropertiesSet(); Assert.state(jobRegistry != null, "JobLocator must be provided"); - Assert.state(jobRepository != null, "JobRepository must be provided"); } /** @@ -129,18 +124,6 @@ public class SimpleJobOperator implements JobOperator, InitializingBean { this.jobRegistry = jobRegistry; } - public void setJobRepository(JobRepository jobRepository) { - this.jobRepository = jobRepository; - } - - /** - * Public setter for the {@link JobLauncher}. - * @param jobLauncher the {@link JobLauncher} to set - */ - public void setJobLauncher(JobLauncher jobLauncher) { - this.jobLauncher = jobLauncher; - } - @Override public List getExecutions(long instanceId) throws NoSuchJobInstanceException { JobInstance jobInstance = jobRepository.getJobInstance(instanceId); @@ -233,7 +216,7 @@ public class SimpleJobOperator implements JobOperator, InitializingBean { logger.info(String.format("Attempting to resume job with name=%s and parameters=%s", jobName, parameters)); } try { - return jobLauncher.run(job, parameters).getId(); + return run(job, parameters).getId(); } catch (JobExecutionAlreadyRunningException e) { throw new UnexpectedJobExecutionException( @@ -263,7 +246,7 @@ public class SimpleJobOperator implements JobOperator, InitializingBean { .info(String.format("Attempting to launch job with name=%s and parameters={%s}", jobName, parameters)); } try { - return jobLauncher.run(job, jobParameters).getId(); + return run(job, jobParameters).getId(); } catch (JobExecutionAlreadyRunningException e) { throw new UnexpectedJobExecutionException( @@ -293,7 +276,7 @@ public class SimpleJobOperator implements JobOperator, InitializingBean { logger.info(String.format("Attempting to launch job with name=%s and parameters=%s", jobName, parameters)); } try { - return jobLauncher.run(job, parameters).getId(); + return run(job, parameters).getId(); } catch (JobExecutionAlreadyRunningException e) { throw new UnexpectedJobExecutionException( diff --git a/spring-batch-core/src/main/java/org/springframework/batch/core/launch/support/TaskExecutorJobLauncher.java b/spring-batch-core/src/main/java/org/springframework/batch/core/launch/support/TaskExecutorJobLauncher.java index aab3443cd..1576c57c4 100644 --- a/spring-batch-core/src/main/java/org/springframework/batch/core/launch/support/TaskExecutorJobLauncher.java +++ b/spring-batch-core/src/main/java/org/springframework/batch/core/launch/support/TaskExecutorJobLauncher.java @@ -1,5 +1,5 @@ /* - * Copyright 2022-2024 the original author or authors. + * Copyright 2022-2025 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -70,13 +70,13 @@ public class TaskExecutorJobLauncher implements JobLauncher, InitializingBean { protected static final Log logger = LogFactory.getLog(TaskExecutorJobLauncher.class); - private JobRepository jobRepository; + protected JobRepository jobRepository; - private TaskExecutor taskExecutor; + protected TaskExecutor taskExecutor; - private MeterRegistry meterRegistry = Metrics.globalRegistry; + protected MeterRegistry meterRegistry = Metrics.globalRegistry; - private Counter jobLaunchCount; // NoopCounter is still incubating + protected Counter jobLaunchCount; // NoopCounter is still incubating /** * Run the provided job with the given {@link JobParameters}. The diff --git a/spring-batch-core/src/test/java/org/springframework/batch/core/configuration/annotation/BatchRegistrarTests.java b/spring-batch-core/src/test/java/org/springframework/batch/core/configuration/annotation/BatchRegistrarTests.java index 6bb03fa4a..2aee2be07 100644 --- a/spring-batch-core/src/test/java/org/springframework/batch/core/configuration/annotation/BatchRegistrarTests.java +++ b/spring-batch-core/src/test/java/org/springframework/batch/core/configuration/annotation/BatchRegistrarTests.java @@ -1,5 +1,5 @@ /* - * Copyright 2022-2024 the original author or authors. + * Copyright 2022-2025 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -77,7 +77,6 @@ class BatchRegistrarTests { var context = new AnnotationConfigApplicationContext(JobConfigurationWithUserDefinedInfrastructureBeans.class); Assertions.assertTrue(Mockito.mockingDetails(context.getBean(JobRepository.class)).isMock()); - Assertions.assertTrue(Mockito.mockingDetails(context.getBean(JobLauncher.class)).isMock()); Assertions.assertTrue(Mockito.mockingDetails(context.getBean(JobRegistry.class)).isMock()); Assertions.assertTrue(Mockito.mockingDetails(context.getBean(JobOperator.class)).isMock()); Assertions diff --git a/spring-batch-core/src/test/java/org/springframework/batch/core/launch/support/JobOperatorFactoryBeanTests.java b/spring-batch-core/src/test/java/org/springframework/batch/core/launch/support/JobOperatorFactoryBeanTests.java index 923edf303..0b1241c01 100644 --- a/spring-batch-core/src/test/java/org/springframework/batch/core/launch/support/JobOperatorFactoryBeanTests.java +++ b/spring-batch-core/src/test/java/org/springframework/batch/core/launch/support/JobOperatorFactoryBeanTests.java @@ -1,5 +1,5 @@ /* - * Copyright 2022-2023 the original author or authors. + * Copyright 2022-2025 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -23,8 +23,6 @@ import org.springframework.aop.Advisor; import org.springframework.aop.framework.Advised; import org.springframework.batch.core.configuration.JobRegistry; import org.springframework.batch.core.converter.JobParametersConverter; -import org.springframework.batch.core.repository.explore.JobExplorer; -import org.springframework.batch.core.launch.JobLauncher; import org.springframework.batch.core.launch.JobOperator; import org.springframework.batch.core.repository.JobRepository; import org.springframework.test.util.AopTestUtils; @@ -43,12 +41,8 @@ class JobOperatorFactoryBeanTests { private final JobRepository jobRepository = Mockito.mock(); - private final JobLauncher jobLauncher = Mockito.mock(); - private final JobRegistry jobRegistry = Mockito.mock(); - private final JobExplorer jobExplorer = Mockito.mock(); - private final JobParametersConverter jobParametersConverter = Mockito.mock(); @Test @@ -56,7 +50,6 @@ class JobOperatorFactoryBeanTests { // given JobOperatorFactoryBean jobOperatorFactoryBean = new JobOperatorFactoryBean(); jobOperatorFactoryBean.setTransactionManager(this.transactionManager); - jobOperatorFactoryBean.setJobLauncher(this.jobLauncher); jobOperatorFactoryBean.setJobRegistry(this.jobRegistry); jobOperatorFactoryBean.setJobRepository(this.jobRepository); jobOperatorFactoryBean.setJobParametersConverter(this.jobParametersConverter); @@ -78,7 +71,6 @@ class JobOperatorFactoryBeanTests { TransactionAttributeSource transactionAttributeSource = Mockito.mock(); JobOperatorFactoryBean jobOperatorFactoryBean = new JobOperatorFactoryBean(); jobOperatorFactoryBean.setTransactionManager(this.transactionManager); - jobOperatorFactoryBean.setJobLauncher(this.jobLauncher); jobOperatorFactoryBean.setJobRegistry(this.jobRegistry); jobOperatorFactoryBean.setJobRepository(this.jobRepository); jobOperatorFactoryBean.setJobParametersConverter(this.jobParametersConverter); diff --git a/spring-batch-core/src/test/java/org/springframework/batch/core/launch/support/SimpleJobOperatorTests.java b/spring-batch-core/src/test/java/org/springframework/batch/core/launch/support/SimpleJobOperatorTests.java index 22320c473..30e2ccd4b 100644 --- a/spring-batch-core/src/test/java/org/springframework/batch/core/launch/support/SimpleJobOperatorTests.java +++ b/spring-batch-core/src/test/java/org/springframework/batch/core/launch/support/SimpleJobOperatorTests.java @@ -1,5 +1,5 @@ /* - * Copyright 2006-2023 the original author or authors. + * Copyright 2006-2025 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -47,7 +47,9 @@ import org.springframework.batch.core.launch.NoSuchJobException; import org.springframework.batch.core.launch.NoSuchJobExecutionException; import org.springframework.batch.core.launch.NoSuchJobInstanceException; import org.springframework.batch.core.repository.JobExecutionAlreadyRunningException; +import org.springframework.batch.core.repository.JobInstanceAlreadyCompleteException; import org.springframework.batch.core.repository.JobRepository; +import org.springframework.batch.core.repository.JobRestartException; import org.springframework.batch.core.scope.context.ChunkContext; import org.springframework.batch.core.step.tasklet.StoppableTasklet; import org.springframework.batch.core.step.tasklet.TaskletStep; @@ -97,7 +99,12 @@ class SimpleJobOperatorTests { } }; - jobOperator = new SimpleJobOperator(); + jobOperator = new SimpleJobOperator() { + @Override + public JobExecution run(Job job, JobParameters jobParameters) { + return new JobExecution(new JobInstance(123L, job.getName()), 999L, jobParameters); + } + }; jobOperator.setJobRegistry(new MapJobRegistry() { @Override @@ -114,9 +121,6 @@ class SimpleJobOperatorTests { } }); - jobOperator.setJobLauncher( - (job, jobParameters) -> new JobExecution(new JobInstance(123L, job.getName()), 999L, jobParameters)); - jobRepository = mock(); jobOperator.setJobRepository(jobRepository); diff --git a/spring-batch-core/src/test/resources/applicationContext-test2.xml b/spring-batch-core/src/test/resources/applicationContext-test2.xml index fe27a3211..00d678726 100644 --- a/spring-batch-core/src/test/resources/applicationContext-test2.xml +++ b/spring-batch-core/src/test/resources/applicationContext-test2.xml @@ -48,11 +48,6 @@ - - - - - diff --git a/spring-batch-core/src/test/resources/org/springframework/batch/core/repository/dao/OptimisticLockingFailureTests-context.xml b/spring-batch-core/src/test/resources/org/springframework/batch/core/repository/dao/OptimisticLockingFailureTests-context.xml index b30871a8e..b62728286 100644 --- a/spring-batch-core/src/test/resources/org/springframework/batch/core/repository/dao/OptimisticLockingFailureTests-context.xml +++ b/spring-batch-core/src/test/resources/org/springframework/batch/core/repository/dao/OptimisticLockingFailureTests-context.xml @@ -37,13 +37,6 @@ - - - - - - - @@ -56,9 +49,11 @@ - + + + diff --git a/spring-batch-core/src/test/resources/simple-job-launcher-context.xml b/spring-batch-core/src/test/resources/simple-job-launcher-context.xml index 600ccf4a2..2b0a31aa8 100644 --- a/spring-batch-core/src/test/resources/simple-job-launcher-context.xml +++ b/spring-batch-core/src/test/resources/simple-job-launcher-context.xml @@ -6,11 +6,6 @@ - - - - @@ -21,7 +16,7 @@ + p:jobRepository-ref="jobRepository" p:jobRegistry-ref="jobRegistry" /> - - - - @@ -51,12 +46,8 @@ - - - - - - + + diff --git a/spring-batch-samples/src/main/resources/org/springframework/batch/samples/restart/stop/stopRestartSample.xml b/spring-batch-samples/src/main/resources/org/springframework/batch/samples/restart/stop/stopRestartSample.xml index 715a773e6..5b4e1aeae 100644 --- a/spring-batch-samples/src/main/resources/org/springframework/batch/samples/restart/stop/stopRestartSample.xml +++ b/spring-batch-samples/src/main/resources/org/springframework/batch/samples/restart/stop/stopRestartSample.xml @@ -1,18 +1,35 @@ + xmlns:p="http://www.springframework.org/schema/p" + xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd"> - + - - + + + + + + + + + + + + + + diff --git a/spring-batch-samples/src/main/resources/org/springframework/batch/samples/skip/job/skipSample-job-launcher-context.xml b/spring-batch-samples/src/main/resources/org/springframework/batch/samples/skip/job/skipSample-job-launcher-context.xml index b67fb6da9..89e43c035 100644 --- a/spring-batch-samples/src/main/resources/org/springframework/batch/samples/skip/job/skipSample-job-launcher-context.xml +++ b/spring-batch-samples/src/main/resources/org/springframework/batch/samples/skip/job/skipSample-job-launcher-context.xml @@ -6,14 +6,10 @@ - - - - - - - - - @@ -21,11 +16,7 @@ - - + p:jobRepository-ref="jobRepository" p:jobRegistry-ref="jobRegistry" /> diff --git a/spring-batch-samples/src/test/java/org/springframework/batch/samples/restart/stop/GracefulShutdownFunctionalTests.java b/spring-batch-samples/src/test/java/org/springframework/batch/samples/restart/stop/GracefulShutdownFunctionalTests.java index 20c8a11e0..69a21c8d6 100644 --- a/spring-batch-samples/src/test/java/org/springframework/batch/samples/restart/stop/GracefulShutdownFunctionalTests.java +++ b/spring-batch-samples/src/test/java/org/springframework/batch/samples/restart/stop/GracefulShutdownFunctionalTests.java @@ -1,5 +1,5 @@ /* - * Copyright 2006-2022 the original author or authors. + * Copyright 2006-2025 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -43,8 +43,7 @@ import static org.junit.jupiter.api.Assertions.assertTrue; * @author Mahmoud Ben Hassine * */ -@SpringJUnitConfig(locations = { "/simple-job-launcher-context.xml", - "/org/springframework/batch/samples/restart/stop/stopRestartSample.xml" }) +@SpringJUnitConfig(locations = { "/org/springframework/batch/samples/restart/stop/stopRestartSample.xml" }) class GracefulShutdownFunctionalTests { /** Logger */ diff --git a/spring-batch-samples/src/test/java/org/springframework/batch/samples/restart/stop/JobOperatorFunctionalTests.java b/spring-batch-samples/src/test/java/org/springframework/batch/samples/restart/stop/JobOperatorFunctionalTests.java index 88c5b0e94..6369b038c 100644 --- a/spring-batch-samples/src/test/java/org/springframework/batch/samples/restart/stop/JobOperatorFunctionalTests.java +++ b/spring-batch-samples/src/test/java/org/springframework/batch/samples/restart/stop/JobOperatorFunctionalTests.java @@ -1,5 +1,5 @@ /* - * Copyright 2008-2023 the original author or authors. + * Copyright 2008-2025 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -38,8 +38,7 @@ import static org.junit.jupiter.api.Assertions.assertFalse; import static org.junit.jupiter.api.Assertions.assertNotEquals; import static org.junit.jupiter.api.Assertions.assertTrue; -@SpringJUnitConfig(locations = { "/simple-job-launcher-context.xml", - "/org/springframework/batch/samples/restart/stop/stopRestartSample.xml" }) +@SpringJUnitConfig(locations = { "/org/springframework/batch/samples/restart/stop/stopRestartSample.xml" }) class JobOperatorFunctionalTests { private static final Log LOG = LogFactory.getLog(JobOperatorFunctionalTests.class); @@ -50,16 +49,6 @@ class JobOperatorFunctionalTests { @Autowired private Job job; - @Autowired - private JobRegistry jobRegistry; - - @BeforeEach - void setUp() throws Exception { - if (!jobRegistry.getJobNames().contains(job.getName())) { - jobRegistry.register(new ReferenceJobFactory(job)); - } - } - @Test void testStartStopResumeJob() throws Exception { String params = "jobOperatorTestParam=7,java.lang.Long,true";