diff --git a/lib/taskana-core-test/src/test/java/acceptance/jobs/AbstractTaskanaJobAccTest.java b/lib/taskana-core-test/src/test/java/acceptance/jobs/AbstractTaskanaJobAccTest.java index d4536b2b68..6733f41f07 100644 --- a/lib/taskana-core-test/src/test/java/acceptance/jobs/AbstractTaskanaJobAccTest.java +++ b/lib/taskana-core-test/src/test/java/acceptance/jobs/AbstractTaskanaJobAccTest.java @@ -31,6 +31,7 @@ import pro.taskana.testapi.TaskanaInject; import pro.taskana.testapi.TaskanaIntegrationTest; import pro.taskana.testapi.security.WithAccessId; +import pro.taskana.workbasket.internal.jobs.WorkbasketCleanupJob; @TaskanaIntegrationTest class AbstractTaskanaJobAccTest { @@ -105,30 +106,34 @@ void should_DeleteOldTaskCleanupJobs_When_InitializingSchedule() { assertThat(jobsToRun).doesNotContainAnyElementsOf(taskCleanupJobs); } - @Nested - @TestInstance(Lifecycle.PER_CLASS) - class CleanCompletedTasks implements TaskanaConfigurationModifier { - @TaskanaInject TaskanaEngine taskanaEngine; - - @TaskanaInject JobMapper jobMapper; + @WithAccessId(user = "admin") + @Test + void should_DeleteOldWorkbasketCleanupJobs_When_InitializingSchedule() throws Exception { - @Override - public Builder modify(Builder builder) { - return builder - .taskCleanupJobEnabled(true) - .jobRunEvery(Duration.ofMillis(1)) - .jobFirstRun(Instant.now().plus(5, ChronoUnit.MINUTES)); + for (int i = 0; i < 10; i++) { + ScheduledJob job = new ScheduledJob(); + job.setType(WorkbasketCleanupJob.class.getName()); + taskanaEngine.getJobService().createJob(job); + job.setType(TaskRefreshJob.class.getName()); + taskanaEngine.getJobService().createJob(job); + job.setType(ClassificationChangedJob.class.getName()); + taskanaEngine.getJobService().createJob(job); } + List jobsToRun = jobMapper.findJobsToRun(Instant.now()); - @WithAccessId(user = "admin") - @Test - void should_FindNoJobsToRunUntilFirstRunIsReached_When_CleanupScheduleIsInitialized() - throws Exception { - AbstractTaskanaJob.initializeSchedule(taskanaEngine, TaskCleanupJob.class); + assertThat(jobsToRun).hasSize(30); - List nextJobs = jobMapper.findJobsToRun(Instant.now()); - assertThat(nextJobs).isEmpty(); - } + List workbasketCleanupJobs = + jobsToRun.stream() + .filter( + scheduledJob -> scheduledJob.getType().equals(WorkbasketCleanupJob.class.getName())) + .toList(); + + AbstractTaskanaJob.initializeSchedule(taskanaEngine, WorkbasketCleanupJob.class); + + jobsToRun = jobMapper.findJobsToRun(Instant.now()); + + assertThat(jobsToRun).doesNotContainAnyElementsOf(workbasketCleanupJobs); } @Test @@ -172,4 +177,30 @@ protected String getType() { @Override protected void execute() throws TaskanaException {} } + + @Nested + @TestInstance(Lifecycle.PER_CLASS) + class CleanCompletedTasks implements TaskanaConfigurationModifier { + @TaskanaInject TaskanaEngine taskanaEngine; + + @TaskanaInject JobMapper jobMapper; + + @Override + public Builder modify(Builder builder) { + return builder + .taskCleanupJobEnabled(true) + .jobRunEvery(Duration.ofMillis(1)) + .jobFirstRun(Instant.now().plus(5, ChronoUnit.MINUTES)); + } + + @WithAccessId(user = "admin") + @Test + void should_FindNoJobsToRunUntilFirstRunIsReached_When_CleanupScheduleIsInitialized() + throws Exception { + AbstractTaskanaJob.initializeSchedule(taskanaEngine, TaskCleanupJob.class); + + List nextJobs = jobMapper.findJobsToRun(Instant.now()); + assertThat(nextJobs).isEmpty(); + } + } } diff --git a/lib/taskana-core-test/src/test/java/acceptance/jobs/WorkbasketCleanupJobAccTest.java b/lib/taskana-core-test/src/test/java/acceptance/jobs/WorkbasketCleanupJobAccTest.java new file mode 100644 index 0000000000..d92aa5e9f1 --- /dev/null +++ b/lib/taskana-core-test/src/test/java/acceptance/jobs/WorkbasketCleanupJobAccTest.java @@ -0,0 +1,79 @@ +package acceptance.jobs; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.util.List; +import org.junit.jupiter.api.BeforeAll; +import org.junit.jupiter.api.Test; +import pro.taskana.classification.api.ClassificationService; +import pro.taskana.classification.api.models.ClassificationSummary; +import pro.taskana.common.api.TaskanaEngine; +import pro.taskana.task.api.TaskService; +import pro.taskana.task.api.TaskState; +import pro.taskana.task.api.models.ObjectReference; +import pro.taskana.testapi.DefaultTestEntities; +import pro.taskana.testapi.TaskanaInject; +import pro.taskana.testapi.TaskanaIntegrationTest; +import pro.taskana.testapi.builder.TaskBuilder; +import pro.taskana.testapi.security.WithAccessId; +import pro.taskana.workbasket.api.WorkbasketService; +import pro.taskana.workbasket.api.models.Workbasket; +import pro.taskana.workbasket.api.models.WorkbasketSummary; +import pro.taskana.workbasket.internal.jobs.WorkbasketCleanupJob; + +// All tests are executed as admin, because the jobrunner needs admin rights. +@TaskanaIntegrationTest +class WorkbasketCleanupJobAccTest { + @TaskanaInject TaskService taskService; + @TaskanaInject WorkbasketService workbasketService; + @TaskanaInject ClassificationService classificationService; + @TaskanaInject TaskanaEngine taskanaEngine; + + ClassificationSummary classification; + ObjectReference primaryObjRef; + + @WithAccessId(user = "businessadmin") + @BeforeAll + void setup() throws Exception { + classification = + DefaultTestEntities.defaultTestClassification() + .buildAndStoreAsSummary(classificationService); + primaryObjRef = DefaultTestEntities.defaultTestObjectReference().build(); + } + + @WithAccessId(user = "admin") + @Test + void should_CleanWorkbasketMarkedForDeletion_When_WorkbasketHasNoTasks() throws Exception { + DefaultTestEntities.defaultTestWorkbasket() + .markedForDeletion(true) + .buildAndStore(workbasketService); + List wbSummariesOld = workbasketService.createWorkbasketQuery().list(); + assertThat(wbSummariesOld).hasSize(1); + + WorkbasketCleanupJob job = new WorkbasketCleanupJob(taskanaEngine, null, null); + job.run(); + + List wbSummaries = workbasketService.createWorkbasketQuery().list(); + assertThat(wbSummaries).isEmpty(); + } + + @WithAccessId(user = "admin") + @Test + void should_NotCleanWorkbasketMarkedForDeletion_When_WorkbasketHasTasks() throws Exception { + Workbasket wb = DefaultTestEntities.defaultTestWorkbasket().buildAndStore(workbasketService); + TaskBuilder.newTask() + .workbasketSummary(wb.asSummary()) + .classificationSummary(classification) + .primaryObjRef(primaryObjRef) + .state(TaskState.COMPLETED) + .buildAndStore(taskService); + + // Workbasket with completed task will be marked for deletion. + workbasketService.deleteWorkbasket(wb.getId()); + WorkbasketCleanupJob job = new WorkbasketCleanupJob(taskanaEngine, null, null); + job.run(); + + List wbSummaries = workbasketService.createWorkbasketQuery().list(); + assertThat(wbSummaries).hasSize(1); + } +} diff --git a/lib/taskana-core/src/test/java/acceptance/jobs/WorkbasketCleanupJobAccTest.java b/lib/taskana-core/src/test/java/acceptance/jobs/WorkbasketCleanupJobAccTest.java deleted file mode 100644 index 6db05b39f4..0000000000 --- a/lib/taskana-core/src/test/java/acceptance/jobs/WorkbasketCleanupJobAccTest.java +++ /dev/null @@ -1,137 +0,0 @@ -package acceptance.jobs; - -import static org.assertj.core.api.Assertions.assertThat; - -import acceptance.AbstractAccTest; -import java.time.Instant; -import java.util.List; -import java.util.stream.Collectors; -import org.junit.jupiter.api.AfterEach; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.api.extension.ExtendWith; -import pro.taskana.classification.internal.jobs.ClassificationChangedJob; -import pro.taskana.common.api.BaseQuery; -import pro.taskana.common.api.ScheduledJob; -import pro.taskana.common.internal.jobs.AbstractTaskanaJob; -import pro.taskana.common.test.security.JaasExtension; -import pro.taskana.common.test.security.WithAccessId; -import pro.taskana.task.api.TaskState; -import pro.taskana.task.internal.jobs.TaskCleanupJob; -import pro.taskana.task.internal.jobs.TaskRefreshJob; -import pro.taskana.workbasket.api.WorkbasketService; -import pro.taskana.workbasket.api.models.WorkbasketSummary; -import pro.taskana.workbasket.internal.jobs.WorkbasketCleanupJob; - -/** Acceptance test for all "jobs workbasket runner" scenarios. */ -@ExtendWith(JaasExtension.class) -class WorkbasketCleanupJobAccTest extends AbstractAccTest { - - WorkbasketService workbasketService = taskanaEngine.getWorkbasketService(); - - @AfterEach - void after() throws Exception { - resetDb(true); - } - - @WithAccessId(user = "admin") - @Test - void shouldCleanWorkbasketMarkedForDeletionWithoutTasks() throws Exception { - long totalWorkbasketCount = workbasketService.createWorkbasketQuery().count(); - assertThat(totalWorkbasketCount).isEqualTo(26); - List workbaskets = - workbasketService - .createWorkbasketQuery() - .keyIn("TEAMLEAD-1") - .orderByKey(BaseQuery.SortDirection.ASCENDING) - .list(); - - assertThat(getNumberTaskNotCompleted(workbaskets.get(0).getId())).isZero(); - assertThat(getNumberTaskCompleted(workbaskets.get(0).getId())).isOne(); - - // Workbasket with completed task will be marked for deletion. - workbasketService.deleteWorkbasket(workbaskets.get(0).getId()); - - // Run taskCleanupJob for deleting completing tasks before running workbasketCleanupJob - TaskCleanupJob taskCleanupJob = new TaskCleanupJob(taskanaEngine, null, null); - taskCleanupJob.run(); - - assertThat(getNumberTaskCompleted(workbaskets.get(0).getId())).isZero(); - - WorkbasketCleanupJob workbasketCleanupJob = new WorkbasketCleanupJob(taskanaEngine, null, null); - workbasketCleanupJob.run(); - - totalWorkbasketCount = workbasketService.createWorkbasketQuery().count(); - assertThat(totalWorkbasketCount).isEqualTo(25); - } - - @WithAccessId(user = "admin") - @Test - void shouldNotCleanWorkbasketMarkedForDeletionIfWorkbasketHasTasks() throws Exception { - long totalWorkbasketCount = workbasketService.createWorkbasketQuery().count(); - assertThat(totalWorkbasketCount).isEqualTo(26); - List workbaskets = - workbasketService - .createWorkbasketQuery() - .keyIn("TEAMLEAD-1") - .orderByKey(BaseQuery.SortDirection.ASCENDING) - .list(); - - assertThat(getNumberTaskCompleted(workbaskets.get(0).getId())).isPositive(); - - // Workbasket with completed task will be marked for deletion. - workbasketService.deleteWorkbasket(workbaskets.get(0).getId()); - - WorkbasketCleanupJob job = new WorkbasketCleanupJob(taskanaEngine, null, null); - job.run(); - - totalWorkbasketCount = workbasketService.createWorkbasketQuery().count(); - assertThat(totalWorkbasketCount).isEqualTo(26); - } - - @WithAccessId(user = "admin") - @Test - void should_DeleteOldWorkbasketCleanupJobs_When_InitializingSchedule() throws Exception { - - for (int i = 0; i < 10; i++) { - ScheduledJob job = new ScheduledJob(); - job.setType(WorkbasketCleanupJob.class.getName()); - taskanaEngine.getJobService().createJob(job); - job.setType(TaskRefreshJob.class.getName()); - taskanaEngine.getJobService().createJob(job); - job.setType(ClassificationChangedJob.class.getName()); - taskanaEngine.getJobService().createJob(job); - } - - List jobsToRun = getJobMapper(taskanaEngine).findJobsToRun(Instant.now()); - - assertThat(jobsToRun).hasSize(30); - - List workbasketCleanupJobs = - jobsToRun.stream() - .filter( - scheduledJob -> scheduledJob.getType().equals(WorkbasketCleanupJob.class.getName())) - .collect(Collectors.toList()); - - AbstractTaskanaJob.initializeSchedule(taskanaEngine, WorkbasketCleanupJob.class); - - jobsToRun = getJobMapper(taskanaEngine).findJobsToRun(Instant.now()); - - assertThat(jobsToRun).doesNotContainAnyElementsOf(workbasketCleanupJobs); - } - - private long getNumberTaskNotCompleted(String workbasketId) { - return taskService - .createTaskQuery() - .workbasketIdIn(workbasketId) - .stateNotIn(TaskState.COMPLETED) - .count(); - } - - private long getNumberTaskCompleted(String workbasketId) { - return taskService - .createTaskQuery() - .workbasketIdIn(workbasketId) - .stateIn(TaskState.COMPLETED) - .count(); - } -}