Closes #2469: Refactor HistoryCleanupJobAccTest to use test-API

This commit is contained in:
jamesrdi 2024-01-04 12:29:07 +01:00 committed by Elena Mokeeva
parent dcdf92a0a9
commit b657f6d4dc
4 changed files with 508 additions and 549 deletions

View File

@ -1,519 +0,0 @@
package acceptance.jobs;
import static org.assertj.core.api.Assertions.assertThat;
import acceptance.AbstractAccTest;
import java.sql.SQLException;
import java.time.Instant;
import java.time.temporal.ChronoUnit;
import java.util.Arrays;
import java.util.Iterator;
import java.util.List;
import java.util.stream.Collectors;
import java.util.stream.Stream;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.DynamicTest;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.TestFactory;
import org.junit.jupiter.api.extension.ExtendWith;
import org.junit.jupiter.api.function.ThrowingConsumer;
import pro.taskana.TaskanaConfiguration;
import pro.taskana.classification.internal.jobs.ClassificationChangedJob;
import pro.taskana.common.api.ScheduledJob;
import pro.taskana.common.internal.jobs.AbstractTaskanaJob;
import pro.taskana.common.internal.util.Pair;
import pro.taskana.common.test.config.DataSourceGenerator;
import pro.taskana.common.test.security.JaasExtension;
import pro.taskana.common.test.security.WithAccessId;
import pro.taskana.simplehistory.impl.jobs.HistoryCleanupJob;
import pro.taskana.spi.history.api.events.task.TaskHistoryEvent;
import pro.taskana.spi.history.api.events.task.TaskHistoryEventType;
import pro.taskana.task.internal.jobs.TaskRefreshJob;
@ExtendWith(JaasExtension.class)
class HistoryCleanupJobAccTest extends AbstractAccTest {
@BeforeEach
void before() throws Exception {
resetDb(DataSourceGenerator.getSchemaName());
}
@Test
@WithAccessId(user = "admin")
void should_CleanHistoryEventsUntilDate_When_SameParentBusinessTrueAndEventsQualified()
throws Exception {
assertThat(getHistoryService().createTaskHistoryQuery().count()).isEqualTo(14);
TaskHistoryEvent eventToBeCleaned =
createTaskHistoryEvent(
"wbKey1",
"taskId1",
TaskHistoryEventType.CREATED.getName(),
"wbKey2",
"someUserId",
"someDetails");
eventToBeCleaned.setCreated(Instant.now().minus(20, ChronoUnit.DAYS));
eventToBeCleaned.setParentBusinessProcessId("sameParentId");
TaskHistoryEvent eventToBeCleaned2 =
createTaskHistoryEvent(
"wbKey1",
"taskId1",
TaskHistoryEventType.COMPLETED.getName(),
"wbKey2",
"someUserId",
"someDetails");
eventToBeCleaned2.setCreated(Instant.now().minus(20, ChronoUnit.DAYS));
eventToBeCleaned2.setParentBusinessProcessId("sameParentId");
TaskHistoryEvent eventToBeCleaned3 =
createTaskHistoryEvent(
"wbKey1",
"taskId2",
TaskHistoryEventType.CREATED.getName(),
"wbKey2",
"someUserId",
"someDetails");
eventToBeCleaned3.setCreated(Instant.now().minus(20, ChronoUnit.DAYS));
eventToBeCleaned3.setParentBusinessProcessId("sameParentId");
TaskHistoryEvent eventToBeCleaned4 =
createTaskHistoryEvent(
"wbKey1",
"taskId2",
TaskHistoryEventType.CANCELLED.getName(),
"wbKey2",
"someUserId",
"someDetails");
eventToBeCleaned4.setCreated(Instant.now().minus(20, ChronoUnit.DAYS));
eventToBeCleaned4.setParentBusinessProcessId("sameParentId");
TaskHistoryEvent eventToBeCleaned5 =
createTaskHistoryEvent(
"wbKey1",
"taskId3",
TaskHistoryEventType.CREATED.getName(),
"wbKey2",
"someUserId",
"someDetails");
eventToBeCleaned5.setCreated(Instant.now().minus(20, ChronoUnit.DAYS));
eventToBeCleaned5.setParentBusinessProcessId("sameParentId");
TaskHistoryEvent eventToBeCleaned6 =
createTaskHistoryEvent(
"wbKey1",
"taskId3",
TaskHistoryEventType.TERMINATED.getName(),
"wbKey2",
"someUserId",
"someDetails");
eventToBeCleaned6.setCreated(Instant.now().minus(20, ChronoUnit.DAYS));
eventToBeCleaned6.setParentBusinessProcessId("sameParentId");
getHistoryService().create(eventToBeCleaned);
getHistoryService().create(eventToBeCleaned2);
getHistoryService().create(eventToBeCleaned3);
getHistoryService().create(eventToBeCleaned4);
getHistoryService().create(eventToBeCleaned5);
getHistoryService().create(eventToBeCleaned6);
assertThat(getHistoryService().createTaskHistoryQuery().count()).isEqualTo(20);
createTaskanaEngineWithNewConfig(true);
HistoryCleanupJob job = new HistoryCleanupJob(taskanaEngine, null, null);
job.run();
assertThat(getHistoryService().createTaskHistoryQuery().count()).isEqualTo(14);
}
@Test
@WithAccessId(user = "admin")
void should_NotCleanHistoryEventsUntilDate_When_MinimumAgeNotReached() throws Exception {
assertThat(getHistoryService().createTaskHistoryQuery().count()).isEqualTo(14);
TaskHistoryEvent eventToBeCleaned =
createTaskHistoryEvent(
"wbKey1",
"taskId1",
TaskHistoryEventType.CREATED.getName(),
"wbKey2",
"someUserId",
"someDetails");
eventToBeCleaned.setCreated(Instant.now().minus(20, ChronoUnit.DAYS));
eventToBeCleaned.setParentBusinessProcessId("sameParentId");
TaskHistoryEvent eventToBeCleaned2 =
createTaskHistoryEvent(
"wbKey1",
"taskId1",
TaskHistoryEventType.COMPLETED.getName(),
"wbKey2",
"someUserId",
"someDetails");
eventToBeCleaned2.setCreated(Instant.now().minus(5, ChronoUnit.DAYS));
eventToBeCleaned2.setParentBusinessProcessId("sameParentId");
getHistoryService().create(eventToBeCleaned);
getHistoryService().create(eventToBeCleaned2);
assertThat(getHistoryService().createTaskHistoryQuery().count()).isEqualTo(16);
HistoryCleanupJob job = new HistoryCleanupJob(taskanaEngine, null, null);
job.run();
assertThat(getHistoryService().createTaskHistoryQuery().count()).isEqualTo(16);
}
@Test
@WithAccessId(user = "admin")
void should_NotCleanHistoryEvents_When_SameParentBusinessTrueAndActiveTaskInParentBusiness()
throws Exception {
assertThat(getHistoryService().createTaskHistoryQuery().count()).isEqualTo(14);
TaskHistoryEvent eventToBeCleaned =
createTaskHistoryEvent(
"wbKey1",
"taskId1",
TaskHistoryEventType.CREATED.getName(),
"wbKey2",
"someUserId",
"someDetails");
eventToBeCleaned.setCreated(Instant.now().minus(20, ChronoUnit.DAYS));
eventToBeCleaned.setParentBusinessProcessId("sameParentId");
TaskHistoryEvent eventToBeCleaned2 =
createTaskHistoryEvent(
"wbKey1",
"taskId1",
TaskHistoryEventType.COMPLETED.getName(),
"wbKey2",
"someUserId",
"someDetails");
eventToBeCleaned2.setCreated(Instant.now().minus(20, ChronoUnit.DAYS));
eventToBeCleaned2.setParentBusinessProcessId("sameParentId");
TaskHistoryEvent eventToBeCleaned3 =
createTaskHistoryEvent(
"wbKey1",
"taskId2",
TaskHistoryEventType.CREATED.getName(),
"wbKey2",
"someUserId",
"someDetails");
eventToBeCleaned3.setCreated(Instant.now().minus(1, ChronoUnit.DAYS));
eventToBeCleaned3.setParentBusinessProcessId("sameParentId");
getHistoryService().create(eventToBeCleaned);
getHistoryService().create(eventToBeCleaned2);
getHistoryService().create(eventToBeCleaned3);
assertThat(getHistoryService().createTaskHistoryQuery().count()).isEqualTo(17);
createTaskanaEngineWithNewConfig(true);
HistoryCleanupJob job = new HistoryCleanupJob(taskanaEngine, null, null);
job.run();
assertThat(getHistoryService().createTaskHistoryQuery().count()).isEqualTo(17);
}
@Test
@WithAccessId(user = "admin")
void should_NotCleanHistoryEvents_When_MinimumAgeOfOtherEndtstateEventInParentBusinessNotReached()
throws Exception {
assertThat(getHistoryService().createTaskHistoryQuery().count()).isEqualTo(14);
TaskHistoryEvent eventToBeCleaned =
createTaskHistoryEvent(
"wbKey1",
"taskId1",
TaskHistoryEventType.CREATED.getName(),
"wbKey2",
"someUserId",
"someDetails");
eventToBeCleaned.setCreated(Instant.now().minus(20, ChronoUnit.DAYS));
eventToBeCleaned.setParentBusinessProcessId("sameParentId");
TaskHistoryEvent eventToBeCleaned2 =
createTaskHistoryEvent(
"wbKey1",
"taskId1",
TaskHistoryEventType.COMPLETED.getName(),
"wbKey2",
"someUserId",
"someDetails");
eventToBeCleaned2.setCreated(Instant.now().minus(20, ChronoUnit.DAYS));
eventToBeCleaned2.setParentBusinessProcessId("sameParentId");
TaskHistoryEvent eventToBeCleaned3 =
createTaskHistoryEvent(
"wbKey1",
"taskId2",
TaskHistoryEventType.CREATED.getName(),
"wbKey2",
"someUserId",
"someDetails");
eventToBeCleaned3.setCreated(Instant.now().minus(3, ChronoUnit.DAYS));
eventToBeCleaned3.setParentBusinessProcessId("sameParentId");
TaskHistoryEvent eventToBeCleaned4 =
createTaskHistoryEvent(
"wbKey1",
"taskId2",
TaskHistoryEventType.CANCELLED.getName(),
"wbKey2",
"someUserId",
"someDetails");
eventToBeCleaned4.setCreated(Instant.now().minus(5, ChronoUnit.DAYS));
eventToBeCleaned4.setParentBusinessProcessId("sameParentId");
getHistoryService().create(eventToBeCleaned);
getHistoryService().create(eventToBeCleaned2);
getHistoryService().create(eventToBeCleaned3);
getHistoryService().create(eventToBeCleaned4);
assertThat(getHistoryService().createTaskHistoryQuery().count()).isEqualTo(18);
createTaskanaEngineWithNewConfig(true);
HistoryCleanupJob job = new HistoryCleanupJob(taskanaEngine, null, null);
job.run();
assertThat(getHistoryService().createTaskHistoryQuery().count()).isEqualTo(18);
}
@Test
@WithAccessId(user = "admin")
void should_CleanHistoryEventsUntilDate_When_SameParentBusinessFalse() throws Exception {
assertThat(getHistoryService().createTaskHistoryQuery().count()).isEqualTo(14);
TaskHistoryEvent eventToBeCleaned =
createTaskHistoryEvent(
"wbKey1",
"taskId1",
TaskHistoryEventType.CREATED.getName(),
"wbKey2",
"someUserId",
"someDetails");
eventToBeCleaned.setCreated(Instant.now().minus(20, ChronoUnit.DAYS));
eventToBeCleaned.setParentBusinessProcessId("sameParentId");
TaskHistoryEvent eventToBeCleaned2 =
createTaskHistoryEvent(
"wbKey1",
"taskId1",
TaskHistoryEventType.COMPLETED.getName(),
"wbKey2",
"someUserId",
"someDetails");
eventToBeCleaned2.setCreated(Instant.now().minus(20, ChronoUnit.DAYS));
eventToBeCleaned2.setParentBusinessProcessId("sameParentId");
TaskHistoryEvent eventToBeCleaned3 =
createTaskHistoryEvent(
"wbKey1",
"taskId2",
TaskHistoryEventType.CREATED.getName(),
"wbKey2",
"someUserId",
"someDetails");
eventToBeCleaned3.setCreated(Instant.now().minus(20, ChronoUnit.DAYS));
eventToBeCleaned3.setParentBusinessProcessId("sameParentId");
TaskHistoryEvent eventToBeCleaned4 =
createTaskHistoryEvent(
"wbKey1",
"taskId2",
TaskHistoryEventType.CANCELLED.getName(),
"wbKey2",
"someUserId",
"someDetails");
eventToBeCleaned4.setCreated(Instant.now().minus(20, ChronoUnit.DAYS));
eventToBeCleaned4.setParentBusinessProcessId("sameParentId");
TaskHistoryEvent eventToBeCleaned5 =
createTaskHistoryEvent(
"wbKey1",
"taskId3",
TaskHistoryEventType.CREATED.getName(),
"wbKey2",
"someUserId",
"someDetails");
eventToBeCleaned5.setCreated(Instant.now().minus(20, ChronoUnit.DAYS));
eventToBeCleaned5.setParentBusinessProcessId("sameParentId");
TaskHistoryEvent eventToBeCleaned6 =
createTaskHistoryEvent(
"wbKey1",
"taskId3",
TaskHistoryEventType.TERMINATED.getName(),
"wbKey2",
"someUserId",
"someDetails");
eventToBeCleaned6.setCreated(Instant.now().minus(5, ChronoUnit.DAYS));
eventToBeCleaned6.setParentBusinessProcessId("sameParentId");
getHistoryService().create(eventToBeCleaned);
getHistoryService().create(eventToBeCleaned2);
getHistoryService().create(eventToBeCleaned3);
getHistoryService().create(eventToBeCleaned4);
getHistoryService().create(eventToBeCleaned5);
getHistoryService().create(eventToBeCleaned6);
assertThat(getHistoryService().createTaskHistoryQuery().count()).isEqualTo(20);
createTaskanaEngineWithNewConfig(false);
HistoryCleanupJob job = new HistoryCleanupJob(taskanaEngine, null, null);
job.run();
assertThat(getHistoryService().createTaskHistoryQuery().count()).isEqualTo(16);
}
@Test
@WithAccessId(user = "admin")
void should_NotCleanEvents_When_NoCreatedEventsForParentBusinessProcessIdExist()
throws Exception {
assertThat(getHistoryService().createTaskHistoryQuery().count()).isEqualTo(14);
TaskHistoryEvent toBeIgnored1 =
createTaskHistoryEvent(
"wbKey1",
"taskId1",
TaskHistoryEventType.CANCELLED.getName(),
"wbKey2",
"someUserId",
"someDetails");
toBeIgnored1.setCreated(Instant.now().minus(20, ChronoUnit.DAYS));
toBeIgnored1.setParentBusinessProcessId("toBeIgnored1");
TaskHistoryEvent toBeIgnored2 =
createTaskHistoryEvent(
"wbKey1",
"taskId2",
TaskHistoryEventType.COMPLETED.getName(),
"wbKey2",
"someUserId",
"someDetails");
toBeIgnored2.setCreated(Instant.now().minus(20, ChronoUnit.DAYS));
toBeIgnored2.setParentBusinessProcessId("toBeIgnored2");
TaskHistoryEvent toBeIgnored3 =
createTaskHistoryEvent(
"wbKey1",
"taskId3",
TaskHistoryEventType.TERMINATED.getName(),
"wbKey2",
"someUserId",
"someDetails");
toBeIgnored3.setCreated(Instant.now().minus(20, ChronoUnit.DAYS));
toBeIgnored3.setParentBusinessProcessId("toBeIgnored3");
getHistoryService().create(toBeIgnored1);
getHistoryService().create(toBeIgnored2);
getHistoryService().create(toBeIgnored3);
assertThat(getHistoryService().createTaskHistoryQuery().count()).isEqualTo(17);
createTaskanaEngineWithNewConfig(true);
HistoryCleanupJob job = new HistoryCleanupJob(taskanaEngine, null, null);
job.run();
assertThat(getHistoryService().createTaskHistoryQuery().count()).isEqualTo(17);
}
@WithAccessId(user = "admin")
@Test
void should_DeleteOldHistoryCleanupJobs_When_InitializingSchedule() throws Exception {
for (int i = 0; i < 10; i++) {
ScheduledJob job = new ScheduledJob();
job.setType(HistoryCleanupJob.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<ScheduledJob> jobsToRun = getJobMapper().findJobsToRun(Instant.now());
assertThat(jobsToRun).hasSize(30);
List<ScheduledJob> historyCleanupJobs =
jobsToRun.stream()
.filter(
scheduledJob -> scheduledJob.getType().equals(HistoryCleanupJob.class.getName()))
.collect(Collectors.toList());
AbstractTaskanaJob.initializeSchedule(taskanaEngine, HistoryCleanupJob.class);
jobsToRun = getJobMapper().findJobsToRun(Instant.now());
assertThat(jobsToRun).doesNotContainAnyElementsOf(historyCleanupJobs);
}
@WithAccessId(user = "admin")
@TestFactory
Stream<DynamicTest>
should_CleanTaskHistoryEventsWithParentProcessIdEmptyOrNull_When_TaskCompleted()
throws SQLException {
Iterator<String> iterator = Arrays.asList("", null).iterator();
String taskId1 = "taskId1";
String taskId2 = "taskId2";
List<TaskHistoryEvent> events =
Stream.of(
Pair.of(taskId1, TaskHistoryEventType.CREATED),
Pair.of(taskId1, TaskHistoryEventType.COMPLETED),
Pair.of(taskId2, TaskHistoryEventType.CREATED))
.map(
pair ->
createTaskHistoryEvent(
"wbKey1",
pair.getLeft(),
pair.getRight().getName(),
"wbKey2",
"someUserId",
"someDetails"))
.collect(Collectors.toList());
createTaskanaEngineWithNewConfig(true);
HistoryCleanupJob job = new HistoryCleanupJob(taskanaEngine, null, null);
ThrowingConsumer<String> test =
parentBusinessId -> {
getHistoryService().deleteHistoryEventsByTaskIds(List.of(taskId1, taskId2));
events.forEach(x -> x.setCreated(Instant.now().minus(20, ChronoUnit.DAYS)));
events.forEach(x -> x.setParentBusinessProcessId(parentBusinessId));
events.forEach(x -> getHistoryService().create(x));
job.run();
List<TaskHistoryEvent> eventsAfterCleanup =
getHistoryService().createTaskHistoryQuery().taskIdIn(taskId1, taskId2).list();
assertThat(eventsAfterCleanup)
.extracting(TaskHistoryEvent::getTaskId)
.containsExactly(taskId2);
};
return DynamicTest.stream(iterator, c -> "for parentBusinessProcessId = '" + c + "'", test);
}
private void createTaskanaEngineWithNewConfig(
boolean simpleHistoryCleanupJobAllCompletedSameParentBusiness) throws SQLException {
TaskanaConfiguration configuration =
new TaskanaConfiguration.Builder(AbstractAccTest.taskanaConfiguration)
.simpleHistoryCleanupJobAllCompletedSameParentBusiness(
simpleHistoryCleanupJobAllCompletedSameParentBusiness)
.build();
initTaskanaEngine(configuration);
}
}

View File

@ -37,6 +37,12 @@
<version>${project.version}</version> <version>${project.version}</version>
<scope>test</scope> <scope>test</scope>
</dependency> </dependency>
<dependency>
<groupId>pro.taskana.history</groupId>
<artifactId>taskana-simplehistory-provider</artifactId>
<version>${project.version}</version>
<scope>test</scope>
</dependency>
<dependency> <dependency>
<groupId>org.slf4j</groupId> <groupId>org.slf4j</groupId>
<artifactId>slf4j-simple</artifactId> <artifactId>slf4j-simple</artifactId>

View File

@ -8,12 +8,16 @@ import java.time.Instant;
import java.time.temporal.ChronoUnit; import java.time.temporal.ChronoUnit;
import java.util.List; import java.util.List;
import java.util.stream.Collectors; import java.util.stream.Collectors;
import java.util.stream.Stream;
import org.assertj.core.api.ThrowableAssert.ThrowingCallable; import org.assertj.core.api.ThrowableAssert.ThrowingCallable;
import org.junit.jupiter.api.AfterEach; import org.junit.jupiter.api.AfterEach;
import org.junit.jupiter.api.DynamicTest;
import org.junit.jupiter.api.Nested; import org.junit.jupiter.api.Nested;
import org.junit.jupiter.api.Test; import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.TestFactory;
import org.junit.jupiter.api.TestInstance; import org.junit.jupiter.api.TestInstance;
import org.junit.jupiter.api.TestInstance.Lifecycle; import org.junit.jupiter.api.TestInstance.Lifecycle;
import org.junit.jupiter.api.function.ThrowingConsumer;
import pro.taskana.TaskanaConfiguration; import pro.taskana.TaskanaConfiguration;
import pro.taskana.TaskanaConfiguration.Builder; import pro.taskana.TaskanaConfiguration.Builder;
import pro.taskana.classification.internal.jobs.ClassificationChangedJob; import pro.taskana.classification.internal.jobs.ClassificationChangedJob;
@ -25,6 +29,8 @@ import pro.taskana.common.internal.JobMapper;
import pro.taskana.common.internal.jobs.AbstractTaskanaJob; import pro.taskana.common.internal.jobs.AbstractTaskanaJob;
import pro.taskana.common.internal.jobs.JobRunner; import pro.taskana.common.internal.jobs.JobRunner;
import pro.taskana.common.internal.transaction.TaskanaTransactionProvider; import pro.taskana.common.internal.transaction.TaskanaTransactionProvider;
import pro.taskana.common.internal.util.Pair;
import pro.taskana.simplehistory.impl.jobs.HistoryCleanupJob;
import pro.taskana.task.internal.jobs.TaskCleanupJob; import pro.taskana.task.internal.jobs.TaskCleanupJob;
import pro.taskana.task.internal.jobs.TaskRefreshJob; import pro.taskana.task.internal.jobs.TaskRefreshJob;
import pro.taskana.testapi.TaskanaConfigurationModifier; import pro.taskana.testapi.TaskanaConfigurationModifier;
@ -49,6 +55,7 @@ class AbstractTaskanaJobAccTest {
jobMapper.deleteMultiple(TaskCleanupJob.class.getName()); jobMapper.deleteMultiple(TaskCleanupJob.class.getName());
jobMapper.deleteMultiple(TaskRefreshJob.class.getName()); jobMapper.deleteMultiple(TaskRefreshJob.class.getName());
jobMapper.deleteMultiple(ClassificationChangedJob.class.getName()); jobMapper.deleteMultiple(ClassificationChangedJob.class.getName());
jobMapper.deleteMultiple(HistoryCleanupJob.class.getName());
} }
@WithAccessId(user = "admin") @WithAccessId(user = "admin")
@ -75,36 +82,6 @@ class AbstractTaskanaJobAccTest {
assertThat(jobsToRun).extracting(ScheduledJob::getDue).containsExactly(firstDue.plus(runEvery)); assertThat(jobsToRun).extracting(ScheduledJob::getDue).containsExactly(firstDue.plus(runEvery));
} }
@WithAccessId(user = "admin")
@Test
void should_DeleteOldTaskCleanupJobs_When_InitializingSchedule() {
for (int i = 0; i < 10; i++) {
ScheduledJob job = new ScheduledJob();
job.setType(TaskCleanupJob.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<ScheduledJob> jobsToRun = jobMapper.findJobsToRun(Instant.now());
assertThat(jobsToRun).hasSize(30);
List<ScheduledJob> taskCleanupJobs =
jobsToRun.stream()
.filter(scheduledJob -> scheduledJob.getType().equals(TaskCleanupJob.class.getName()))
.collect(Collectors.toList());
AbstractTaskanaJob.initializeSchedule(taskanaEngine, TaskCleanupJob.class);
jobsToRun = jobMapper.findJobsToRun(Instant.now());
assertThat(jobsToRun).doesNotContainAnyElementsOf(taskCleanupJobs);
}
@Nested @Nested
@TestInstance(Lifecycle.PER_CLASS) @TestInstance(Lifecycle.PER_CLASS)
class CleanCompletedTasks implements TaskanaConfigurationModifier { class CleanCompletedTasks implements TaskanaConfigurationModifier {
@ -131,6 +108,43 @@ class AbstractTaskanaJobAccTest {
} }
} }
@WithAccessId(user = "admin")
@TestFactory
Stream<DynamicTest> should_DeleteOldCleanupJobs_When_InitializingSchedule() throws Exception {
List<Pair<String, Class<?>>> testCases =
List.of(
Pair.of("Delete Old Task Cleanup Jobs", TaskCleanupJob.class),
Pair.of("Delete Old History Cleanup Jobs", HistoryCleanupJob.class));
ThrowingConsumer<Pair<String, Class<?>>> test =
t -> {
for (int i = 0; i < 10; i++) {
ScheduledJob job = new ScheduledJob();
job.setType(t.getRight().getName());
taskanaEngine.getJobService().createJob(job);
job.setType(TaskRefreshJob.class.getName());
taskanaEngine.getJobService().createJob(job);
job.setType(ClassificationChangedJob.class.getName());
taskanaEngine.getJobService().createJob(job);
}
List<ScheduledJob> jobsToRun = jobMapper.findJobsToRun(Instant.now());
List<ScheduledJob> cleanupJobs =
jobsToRun.stream()
.filter(scheduledJob -> scheduledJob.getType().equals(t.getRight().getName()))
.collect(Collectors.toList());
AbstractTaskanaJob.initializeSchedule(taskanaEngine, t.getRight());
jobsToRun = jobMapper.findJobsToRun(Instant.now());
assertThat(jobsToRun).doesNotContainAnyElementsOf(cleanupJobs);
cleanupJobs();
};
return DynamicTest.stream(testCases.iterator(), Pair::getLeft, test);
}
@Test @Test
void should_CreateSampleTaskanaJob_When_JobHasMoreThenOneConstructor() { void should_CreateSampleTaskanaJob_When_JobHasMoreThenOneConstructor() {

View File

@ -0,0 +1,458 @@
package acceptance.jobs;
import static org.assertj.core.api.Assertions.assertThat;
import java.sql.SQLException;
import java.time.Instant;
import java.time.temporal.ChronoUnit;
import java.util.Arrays;
import java.util.Iterator;
import java.util.List;
import java.util.stream.Stream;
import org.junit.jupiter.api.AfterEach;
import org.junit.jupiter.api.BeforeAll;
import org.junit.jupiter.api.DynamicTest;
import org.junit.jupiter.api.Nested;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.TestFactory;
import org.junit.jupiter.api.TestInstance;
import org.junit.jupiter.api.TestInstance.Lifecycle;
import org.junit.jupiter.api.function.ThrowingConsumer;
import pro.taskana.TaskanaConfiguration.Builder;
import pro.taskana.common.api.TaskanaEngine;
import pro.taskana.common.internal.util.IdGenerator;
import pro.taskana.common.internal.util.Pair;
import pro.taskana.simplehistory.impl.SimpleHistoryServiceImpl;
import pro.taskana.simplehistory.impl.jobs.HistoryCleanupJob;
import pro.taskana.spi.history.api.TaskanaHistory;
import pro.taskana.spi.history.api.events.task.TaskHistoryEvent;
import pro.taskana.spi.history.api.events.task.TaskHistoryEventType;
import pro.taskana.testapi.TaskanaConfigurationModifier;
import pro.taskana.testapi.TaskanaInject;
import pro.taskana.testapi.TaskanaIntegrationTest;
import pro.taskana.testapi.WithServiceProvider;
import pro.taskana.testapi.security.WithAccessId;
@WithServiceProvider(
serviceProviderInterface = TaskanaHistory.class,
serviceProviders = SimpleHistoryServiceImpl.class)
@TaskanaIntegrationTest
class HistoryCleanupJobAccTest {
@TaskanaInject TaskanaEngine taskanaEngine;
SimpleHistoryServiceImpl historyService;
@WithAccessId(user = "businessadmin")
@BeforeAll
void setup() throws Exception {
historyService = new SimpleHistoryServiceImpl();
historyService.initialize(taskanaEngine);
}
@WithAccessId(user = "admin")
@AfterEach
void after() throws Exception {
List<TaskHistoryEvent> taskHistoryEventList = historyService.createTaskHistoryQuery().list();
List<String> taskIds = taskHistoryEventList.stream().map(TaskHistoryEvent::getTaskId).toList();
if (!taskIds.isEmpty()) {
historyService.deleteHistoryEventsByTaskIds(taskIds);
}
}
@Test
@WithAccessId(user = "admin")
void should_NotCleanHistoryEventsUntilDate_When_MinimumAgeNotReached() throws Exception {
TaskHistoryEvent eventToBeCleaned =
createTaskHistoryEvent(
"wbKey1",
"taskId1",
TaskHistoryEventType.CREATED.getName(),
"wbKey2",
"someUserId",
"someDetails",
Instant.now().minus(20, ChronoUnit.DAYS),
"sameParentId");
historyService.create(eventToBeCleaned);
TaskHistoryEvent eventToBeCleaned2 =
createTaskHistoryEvent(
"wbKey1",
"taskId1",
TaskHistoryEventType.COMPLETED.getName(),
"wbKey2",
"someUserId",
"someDetails",
Instant.now().minus(5, ChronoUnit.DAYS),
"sameParentId");
historyService.create(eventToBeCleaned2);
HistoryCleanupJob job = new HistoryCleanupJob(taskanaEngine, null, null);
job.run();
assertThat(historyService.createTaskHistoryQuery().count()).isEqualTo(2);
}
private TaskHistoryEvent createTaskHistoryEvent(
String workbasketKey,
String taskId,
String type,
String previousWorkbasketId,
String userid,
String details,
Instant created,
String parentBusinessProcessId) {
TaskHistoryEvent historyEvent = new TaskHistoryEvent();
historyEvent.setId(IdGenerator.generateWithPrefix(IdGenerator.ID_PREFIX_TASK_HISTORY_EVENT));
historyEvent.setUserId(userid);
historyEvent.setDetails(details);
historyEvent.setWorkbasketKey(workbasketKey);
historyEvent.setTaskId(taskId);
historyEvent.setEventType(type);
historyEvent.setOldValue(previousWorkbasketId);
historyEvent.setCreated(created);
historyEvent.setParentBusinessProcessId(parentBusinessProcessId);
return historyEvent;
}
@Nested
@TestInstance(Lifecycle.PER_CLASS)
class SimpleHistoryCleanupJobAllCompletedSameParentBusinessIsTrue
implements TaskanaConfigurationModifier {
@TaskanaInject TaskanaEngine taskanaEngine;
SimpleHistoryServiceImpl historyService;
@Override
public Builder modify(Builder builder) {
return builder.simpleHistoryCleanupJobAllCompletedSameParentBusiness(true);
}
@WithAccessId(user = "businessadmin")
@BeforeAll
void setup() throws Exception {
historyService = new SimpleHistoryServiceImpl();
historyService.initialize(taskanaEngine);
}
@Test
@WithAccessId(user = "admin")
void should_CleanHistoryEventsUntilDate_When_SameParentBusinessTrueAndEventsQualified()
throws Exception {
TaskHistoryEvent eventToBeCleaned =
createTaskHistoryEvent(
"wbKey1",
"taskId1",
TaskHistoryEventType.CREATED.getName(),
"wbKey2",
"someUserId",
"someDetails",
Instant.now().minus(20, ChronoUnit.DAYS),
"sameParentId");
historyService.create(eventToBeCleaned);
TaskHistoryEvent eventToBeCleaned2 =
createTaskHistoryEvent(
"wbKey1",
"taskId1",
TaskHistoryEventType.COMPLETED.getName(),
"wbKey2",
"someUserId",
"someDetails",
Instant.now().minus(20, ChronoUnit.DAYS),
"sameParentId");
historyService.create(eventToBeCleaned2);
TaskHistoryEvent eventToBeCleaned3 =
createTaskHistoryEvent(
"wbKey1",
"taskId2",
TaskHistoryEventType.CREATED.getName(),
"wbKey2",
"someUserId",
"someDetails",
Instant.now().minus(20, ChronoUnit.DAYS),
"sameParentId");
historyService.create(eventToBeCleaned3);
TaskHistoryEvent eventToBeCleaned4 =
createTaskHistoryEvent(
"wbKey1",
"taskId2",
TaskHistoryEventType.CANCELLED.getName(),
"wbKey2",
"someUserId",
"someDetails",
Instant.now().minus(20, ChronoUnit.DAYS),
"sameParentId");
historyService.create(eventToBeCleaned4);
HistoryCleanupJob job = new HistoryCleanupJob(taskanaEngine, null, null);
job.run();
assertThat(historyService.createTaskHistoryQuery().count()).isZero();
}
@Test
@WithAccessId(user = "admin")
void should_NotCleanHistoryEvents_When_SameParentBusinessTrueAndActiveTaskInParentBusiness()
throws Exception {
TaskHistoryEvent eventToBeCleaned =
createTaskHistoryEvent(
"wbKey1",
"taskId1",
TaskHistoryEventType.CREATED.getName(),
"wbKey2",
"someUserId",
"someDetails",
Instant.now().minus(20, ChronoUnit.DAYS),
"sameParentId");
historyService.create(eventToBeCleaned);
TaskHistoryEvent eventToBeCleaned2 =
createTaskHistoryEvent(
"wbKey1",
"taskId1",
TaskHistoryEventType.COMPLETED.getName(),
"wbKey2",
"someUserId",
"someDetails",
Instant.now().minus(20, ChronoUnit.DAYS),
"sameParentId");
historyService.create(eventToBeCleaned2);
TaskHistoryEvent eventToBeCleaned3 =
createTaskHistoryEvent(
"wbKey1",
"taskId2",
TaskHistoryEventType.CREATED.getName(),
"wbKey2",
"someUserId",
"someDetails",
Instant.now().minus(1, ChronoUnit.DAYS),
"sameParentId");
historyService.create(eventToBeCleaned3);
HistoryCleanupJob job = new HistoryCleanupJob(taskanaEngine, null, null);
job.run();
assertThat(historyService.createTaskHistoryQuery().count()).isEqualTo(3);
}
@Test
@WithAccessId(user = "admin")
void
should_NotCleanHistoryEvents_When_MinimumAgeOfOtherEndStateEventInParentBusinessNotReached()
throws Exception {
TaskHistoryEvent eventToBeCleaned =
createTaskHistoryEvent(
"wbKey1",
"taskId1",
TaskHistoryEventType.CREATED.getName(),
"wbKey2",
"someUserId",
"someDetails",
Instant.now().minus(20, ChronoUnit.DAYS),
"sameParentId");
historyService.create(eventToBeCleaned);
TaskHistoryEvent eventToBeCleaned2 =
createTaskHistoryEvent(
"wbKey1",
"taskId1",
TaskHistoryEventType.COMPLETED.getName(),
"wbKey2",
"someUserId",
"someDetails",
Instant.now().minus(20, ChronoUnit.DAYS),
"sameParentId");
historyService.create(eventToBeCleaned2);
TaskHistoryEvent eventToBeCleaned3 =
createTaskHistoryEvent(
"wbKey1",
"taskId2",
TaskHistoryEventType.CREATED.getName(),
"wbKey2",
"someUserId",
"someDetails",
Instant.now().minus(3, ChronoUnit.DAYS),
"sameParentId");
historyService.create(eventToBeCleaned3);
TaskHistoryEvent eventToBeCleaned4 =
createTaskHistoryEvent(
"wbKey1",
"taskId2",
TaskHistoryEventType.CANCELLED.getName(),
"wbKey2",
"someUserId",
"someDetails",
Instant.now().minus(5, ChronoUnit.DAYS),
"sameParentId");
historyService.create(eventToBeCleaned4);
HistoryCleanupJob job = new HistoryCleanupJob(taskanaEngine, null, null);
job.run();
assertThat(historyService.createTaskHistoryQuery().count()).isEqualTo(4);
}
@Test
@WithAccessId(user = "admin")
void should_NotCleanEvents_When_NoCreatedEventsForParentBusinessProcessIdExist()
throws Exception {
TaskHistoryEvent toBeIgnored1 =
createTaskHistoryEvent(
"wbKey1",
"taskId1",
TaskHistoryEventType.CANCELLED.getName(),
"wbKey2",
"someUserId",
"someDetails",
Instant.now().minus(20, ChronoUnit.DAYS),
"toBeIgnored1");
historyService.create(toBeIgnored1);
TaskHistoryEvent toBeIgnored2 =
createTaskHistoryEvent(
"wbKey1",
"taskId2",
TaskHistoryEventType.COMPLETED.getName(),
"wbKey2",
"someUserId",
"someDetails",
Instant.now().minus(20, ChronoUnit.DAYS),
"toBeIgnored2");
historyService.create(toBeIgnored2);
TaskHistoryEvent toBeIgnored3 =
createTaskHistoryEvent(
"wbKey1",
"taskId3",
TaskHistoryEventType.TERMINATED.getName(),
"wbKey2",
"someUserId",
"someDetails",
Instant.now().minus(20, ChronoUnit.DAYS),
"toBeIgnored3");
historyService.create(toBeIgnored3);
HistoryCleanupJob job = new HistoryCleanupJob(taskanaEngine, null, null);
job.run();
assertThat(historyService.createTaskHistoryQuery().count()).isEqualTo(3);
}
@WithAccessId(user = "admin")
@TestFactory
Stream<DynamicTest>
should_CleanTaskHistoryEventsWithParentProcessIdEmptyOrNull_When_TaskCompleted()
throws SQLException {
Iterator<String> iterator = Arrays.asList("", null).iterator();
String taskId1 = "taskId1";
String taskId2 = "taskId2";
HistoryCleanupJob job = new HistoryCleanupJob(taskanaEngine, null, null);
ThrowingConsumer<String> test =
parentBusinessId -> {
List<TaskHistoryEvent> events =
Stream.of(
Pair.of(taskId1, TaskHistoryEventType.CREATED),
Pair.of(taskId1, TaskHistoryEventType.COMPLETED),
Pair.of(taskId2, TaskHistoryEventType.CREATED))
.map(
pair ->
createTaskHistoryEvent(
"wbKey1",
pair.getLeft(),
pair.getRight().getName(),
"wbKey2",
"someUserId",
"someDetails",
Instant.now().minus(20, ChronoUnit.DAYS),
parentBusinessId))
.toList();
historyService.deleteHistoryEventsByTaskIds(List.of(taskId1, taskId2));
events.forEach(x -> x.setCreated(Instant.now().minus(20, ChronoUnit.DAYS)));
events.forEach(x -> x.setParentBusinessProcessId(parentBusinessId));
events.forEach(x -> historyService.create(x));
job.run();
List<TaskHistoryEvent> eventsAfterCleanup =
historyService.createTaskHistoryQuery().taskIdIn(taskId1, taskId2).list();
assertThat(eventsAfterCleanup)
.extracting(TaskHistoryEvent::getTaskId)
.containsExactly(taskId2);
};
return DynamicTest.stream(iterator, c -> "for parentBusinessProcessId = '" + c + "'", test);
}
}
@Nested
@TestInstance(Lifecycle.PER_CLASS)
class SimpleHistoryCleanupJobAllCompletedSameParentBusinessIsFalse
implements TaskanaConfigurationModifier {
@TaskanaInject TaskanaEngine taskanaEngine;
SimpleHistoryServiceImpl historyService;
@Override
public Builder modify(Builder builder) {
return builder.simpleHistoryCleanupJobAllCompletedSameParentBusiness(false);
}
@WithAccessId(user = "businessadmin")
@BeforeAll
void setup() throws Exception {
historyService = new SimpleHistoryServiceImpl();
historyService.initialize(taskanaEngine);
}
@Test
@WithAccessId(user = "admin")
void should_CleanHistoryEventsUntilDate_When_SameParentBusinessFalse() throws Exception {
TaskHistoryEvent eventToBeCleaned =
createTaskHistoryEvent(
"wbKey1",
"taskId1",
TaskHistoryEventType.CREATED.getName(),
"wbKey2",
"someUserId",
"someDetails",
Instant.now().minus(20, ChronoUnit.DAYS),
"sameParentId");
historyService.create(eventToBeCleaned);
TaskHistoryEvent eventToBeCleaned2 =
createTaskHistoryEvent(
"wbKey1",
"taskId1",
TaskHistoryEventType.COMPLETED.getName(),
"wbKey2",
"someUserId",
"someDetails",
Instant.now().minus(20, ChronoUnit.DAYS),
"sameParentId");
historyService.create(eventToBeCleaned2);
TaskHistoryEvent eventToBeCleaned3 =
createTaskHistoryEvent(
"wbKey1",
"taskId2",
TaskHistoryEventType.CREATED.getName(),
"wbKey2",
"someUserId",
"someDetails",
Instant.now().minus(20, ChronoUnit.DAYS),
"sameParentId");
historyService.create(eventToBeCleaned3);
TaskHistoryEvent eventToBeCleaned4 =
createTaskHistoryEvent(
"wbKey1",
"taskId2",
TaskHistoryEventType.TERMINATED.getName(),
"wbKey2",
"someUserId",
"someDetails",
Instant.now().minus(5, ChronoUnit.DAYS),
"sameParentId");
historyService.create(eventToBeCleaned4);
HistoryCleanupJob job = new HistoryCleanupJob(taskanaEngine, null, null);
job.run();
assertThat(historyService.createTaskHistoryQuery().count()).isEqualTo(2);
}
}
}