|
16 | 16 | package org.springframework.batch.core.job.builder;
|
17 | 17 |
|
18 | 18 | import java.util.Arrays;
|
| 19 | +import java.util.concurrent.CountDownLatch; |
| 20 | +import java.util.concurrent.TimeUnit; |
19 | 21 |
|
20 | 22 | import javax.sql.DataSource;
|
21 | 23 |
|
22 | 24 | import static org.junit.jupiter.api.Assertions.assertEquals;
|
23 | 25 |
|
| 26 | +import org.junit.jupiter.api.Assertions; |
24 | 27 | import org.junit.jupiter.api.BeforeEach;
|
25 | 28 | import org.junit.jupiter.api.Test;
|
26 | 29 | import org.springframework.batch.core.BatchStatus;
|
|
45 | 48 | import org.springframework.batch.core.step.StepSupport;
|
46 | 49 | import org.springframework.batch.core.step.builder.StepBuilder;
|
47 | 50 | import org.springframework.batch.item.support.ListItemReader;
|
| 51 | +import org.springframework.batch.repeat.RepeatStatus; |
| 52 | +import org.springframework.batch.support.transaction.ResourcelessTransactionManager; |
48 | 53 | import org.springframework.beans.factory.annotation.Value;
|
49 | 54 | import org.springframework.context.ApplicationContext;
|
50 | 55 | import org.springframework.context.annotation.AnnotationConfigApplicationContext;
|
@@ -419,4 +424,38 @@ public JdbcTransactionManager transactionManager(DataSource dataSource) {
|
419 | 424 |
|
420 | 425 | }
|
421 | 426 |
|
| 427 | + @Test |
| 428 | + public void testBuildSplitWithParallelFlow() throws InterruptedException { |
| 429 | + CountDownLatch countDownLatch = new CountDownLatch(1); |
| 430 | + Step longExecutingStep = new StepBuilder("longExecutingStep", jobRepository).tasklet((stepContribution, b) -> { |
| 431 | + Thread.sleep(500L); |
| 432 | + return RepeatStatus.FINISHED; |
| 433 | + }, new ResourcelessTransactionManager()).build(); |
| 434 | + |
| 435 | + Step interruptedStep = new StepBuilder("interruptedStep", jobRepository).tasklet((stepContribution, b) -> { |
| 436 | + stepContribution.getStepExecution().setTerminateOnly(); |
| 437 | + return RepeatStatus.FINISHED; |
| 438 | + }, new ResourcelessTransactionManager()).build(); |
| 439 | + |
| 440 | + Step nonExecutableStep = new StepBuilder("nonExecutableStep", jobRepository).tasklet((stepContribution, b) -> { |
| 441 | + countDownLatch.countDown(); |
| 442 | + return RepeatStatus.FINISHED; |
| 443 | + }, new ResourcelessTransactionManager()).build(); |
| 444 | + |
| 445 | + Flow twoStepFlow = new FlowBuilder<SimpleFlow>("twoStepFlow").start(longExecutingStep) |
| 446 | + .next(nonExecutableStep) |
| 447 | + .build(); |
| 448 | + Flow interruptedFlow = new FlowBuilder<SimpleFlow>("interruptedFlow").start(interruptedStep).build(); |
| 449 | + |
| 450 | + Flow splitFlow = new FlowBuilder<Flow>("splitFlow").split(new SimpleAsyncTaskExecutor()) |
| 451 | + .add(interruptedFlow, twoStepFlow) |
| 452 | + .build(); |
| 453 | + FlowJobBuilder jobBuilder = new JobBuilder("job", jobRepository).start(splitFlow).build(); |
| 454 | + jobBuilder.preventRestart().build().execute(execution); |
| 455 | + |
| 456 | + boolean isExecutedNonExecutableStep = countDownLatch.await(1, TimeUnit.SECONDS); |
| 457 | + assertEquals(BatchStatus.STOPPED, execution.getStatus()); |
| 458 | + Assertions.assertFalse(isExecutedNonExecutableStep); |
| 459 | + } |
| 460 | + |
422 | 461 | }
|
0 commit comments