Lorsque vous utilisez deux ou plusieurs sources de données avec spring-batch, spécifiez le gestionnaire de transactions avec StepBuilderHelper # transactionManager` lors de la création de la définition d'étape.
Voici un exemple de réglage.
import java.util.stream.Collectors;
import java.util.stream.IntStream;
import javax.sql.DataSource;
import org.springframework.batch.core.Job;
import org.springframework.batch.core.Step;
import org.springframework.batch.core.configuration.annotation.EnableBatchProcessing;
import org.springframework.batch.core.configuration.annotation.JobBuilderFactory;
import org.springframework.batch.core.configuration.annotation.StepBuilderFactory;
import org.springframework.batch.core.launch.support.RunIdIncrementer;
import org.springframework.batch.core.step.tasklet.TaskletStep;
import org.springframework.batch.item.ItemReader;
import org.springframework.batch.item.support.ListItemReader;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.boot.WebApplicationType;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.autoconfigure.batch.BatchDataSource;
import org.springframework.boot.builder.SpringApplicationBuilder;
import org.springframework.boot.jdbc.DataSourceBuilder;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Primary;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.jdbc.datasource.DataSourceTransactionManager;
import org.springframework.transaction.PlatformTransactionManager;
@SpringBootApplication
@EnableBatchProcessing
public class Application {
	@Bean
	@BatchDataSource
	public DataSource springBatchDs() {
		// 1
		return DataSourceBuilder
				.create()
				.url("jdbc:h2:mem:testdb;DB_CLOSE_DELAY=-1;DB_CLOSE_ON_EXIT=FALSE")
				.username("sa")
				.password("")
				.build();
	}
	
	@Bean
	@Primary
	public DataSource primaryDs() {
		// 2
		return DataSourceBuilder
				.create()
				.url("jdbc:oracle:thin:system/oracle@localhost:11521/XEPDB1")
				.username("system")
				.password("oracle")
				.build();
	}
	
	
	@Bean
	public Job job(JobBuilderFactory jobs, Step s1) {
		return jobs.get("myJob")
				.incrementer(new RunIdIncrementer())
				.start(s1)
				.build();
	}
	
	@Bean("stepTransactionManager")
	public PlatformTransactionManager stepTransactionManager(DataSource primaryDs) {
		// 3
		return new DataSourceTransactionManager(primaryDs);
	}
	
	@Bean
	public Step step1(StepBuilderFactory steps
			,DataSource dataSource
			// 4
			,@Qualifier("stepTransactionManager") PlatformTransactionManager transactionManager) {
		ItemReader<Integer> reader = new ListItemReader<Integer>(
				IntStream.range(1, 1001).boxed().collect(Collectors.toList()));
		JdbcTemplate jdbc = new JdbcTemplate(dataSource);
		
		TaskletStep build = steps.get("step1")
				// 5
				.transactionManager(transactionManager)
				.<Integer, Integer>chunk(10)
				.reader(reader)
				.writer(list -> {
					list.forEach(s -> {
						jdbc.update("update aaa set user_id = user_id + 1");
					});
				})
				.build();
		return build;
	}
	
	public static void main(String[] args) {
		new SpringApplicationBuilder(Application.class).web(WebApplicationType.NONE).run(args);
	}
}
@ Qualifier ''. Sans @ Qualifier '', transactionManager '' créé en interne par SimpleBatchConfiguration '' de spring-batch sera inclus.Recommended Posts