From b34a943536507fcf28cbc8c3122beb4000aa74af Mon Sep 17 00:00:00 2001 From: Timo Bejan Date: Tue, 19 Apr 2022 14:10:33 +0300 Subject: [PATCH 1/6] soft delete types RED-3880 --- .../api/model/dossiertemplate/type/Type.java | 2 + .../v1/api/resources/DictionaryResource.java | 7 +- .../entity/configuration/TypeEntity.java | 6 ++ .../service/DossierTemplateCloneService.java | 9 +-- .../DictionaryPersistenceService.java | 69 +++++++++++-------- .../repository/TypeRepository.java | 12 ++-- .../controller/DictionaryController.java | 14 ++-- .../migrations/EntityTypesMigration4.java | 2 +- .../migrations/TypeToEntityMigration5.java | 11 +-- .../server/service/RedactionLogService.java | 25 +++---- ...-soft-delete-time-to-entity.changelog.yaml | 11 +++ .../integration/tests/DictionaryTest.java | 24 +++---- .../tests/DossierTemplateTest.java | 43 ++++-------- .../v1/server/integration/tests/TypeTest.java | 4 +- 14 files changed, 128 insertions(+), 111 deletions(-) create mode 100644 persistence-service-v1/persistence-service-server-v1/src/main/resources/db/changelog/22-add-soft-delete-time-to-entity.changelog.yaml diff --git a/persistence-service-v1/persistence-service-api-v1/src/main/java/com/iqser/red/service/persistence/service/v1/api/model/dossiertemplate/type/Type.java b/persistence-service-v1/persistence-service-api-v1/src/main/java/com/iqser/red/service/persistence/service/v1/api/model/dossiertemplate/type/Type.java index 32d89c571..7c319afd3 100644 --- a/persistence-service-v1/persistence-service-api-v1/src/main/java/com/iqser/red/service/persistence/service/v1/api/model/dossiertemplate/type/Type.java +++ b/persistence-service-v1/persistence-service-api-v1/src/main/java/com/iqser/red/service/persistence/service/v1/api/model/dossiertemplate/type/Type.java @@ -1,5 +1,6 @@ package com.iqser.red.service.persistence.service.v1.api.model.dossiertemplate.type; +import java.time.OffsetDateTime; import java.util.ArrayList; import java.util.List; @@ -36,6 +37,7 @@ public class Type { private boolean hasDictionary; private boolean systemManaged; private boolean autoHideSkipped; + private OffsetDateTime softDeletedTime; // For auto-mappers diff --git a/persistence-service-v1/persistence-service-api-v1/src/main/java/com/iqser/red/service/persistence/service/v1/api/resources/DictionaryResource.java b/persistence-service-v1/persistence-service-api-v1/src/main/java/com/iqser/red/service/persistence/service/v1/api/resources/DictionaryResource.java index 12fbecce0..3b7537029 100644 --- a/persistence-service-v1/persistence-service-api-v1/src/main/java/com/iqser/red/service/persistence/service/v1/api/resources/DictionaryResource.java +++ b/persistence-service-v1/persistence-service-api-v1/src/main/java/com/iqser/red/service/persistence/service/v1/api/resources/DictionaryResource.java @@ -19,6 +19,7 @@ public interface DictionaryResource { String TYPE_PARAMETER_NAME = "type"; String TYPE_PATH_VARIABLE = "/{" + TYPE_PARAMETER_NAME + "}"; + String INCLUDE_DELETED_PARAMETER_NAME = "includeDeleted"; String DOSSIER_TEMPLATE_PARAMETER_NAME = "dossierTemplateId"; String DOSSIER_TEMPLATE_PATH_VARIABLE = "/{" + DOSSIER_TEMPLATE_PARAMETER_NAME + "}"; @@ -66,10 +67,12 @@ public interface DictionaryResource { @GetMapping(value = TYPE_PATH + DOSSIER_TEMPLATE_PATH_VARIABLE, produces = MediaType.APPLICATION_JSON_VALUE) - List getAllTypesForDossierTemplate(@PathVariable(DOSSIER_TEMPLATE_PARAMETER_NAME) String dossierTemplateId); + List getAllTypesForDossierTemplate(@PathVariable(DOSSIER_TEMPLATE_PARAMETER_NAME) String dossierTemplateId, + @RequestParam(value = INCLUDE_DELETED_PARAMETER_NAME, required = false, defaultValue = "false") boolean includeDeleted); @GetMapping(value = TYPE_PATH + DOSSIER_PATH + DOSSIER_ID_PATH_VARIABLE, produces = MediaType.APPLICATION_JSON_VALUE) - List getAllTypesForDossier(@PathVariable(DOSSIER_ID_PARAMETER_NAME) String dossierId); + List getAllTypesForDossier(@PathVariable(DOSSIER_ID_PARAMETER_NAME) String dossierId, + @RequestParam(value = INCLUDE_DELETED_PARAMETER_NAME, required = false, defaultValue = "false") boolean includeDeleted); @GetMapping(value = DICTIONARY_PATH + TYPE_PATH_VARIABLE, produces = MediaType.APPLICATION_JSON_VALUE) Type getDictionaryForType(@PathVariable(TYPE_PARAMETER_NAME) String typeId, @RequestParam(value = FROM_VERSION_PARAM, required = false) Long fromVersion); diff --git a/persistence-service-v1/persistence-service-processor-v1/src/main/java/com/iqser/red/service/persistence/management/v1/processor/entity/configuration/TypeEntity.java b/persistence-service-v1/persistence-service-processor-v1/src/main/java/com/iqser/red/service/persistence/management/v1/processor/entity/configuration/TypeEntity.java index 7ee8289dc..abfba3845 100644 --- a/persistence-service-v1/persistence-service-processor-v1/src/main/java/com/iqser/red/service/persistence/management/v1/processor/entity/configuration/TypeEntity.java +++ b/persistence-service-v1/persistence-service-processor-v1/src/main/java/com/iqser/red/service/persistence/management/v1/processor/entity/configuration/TypeEntity.java @@ -2,6 +2,7 @@ package com.iqser.red.service.persistence.management.v1.processor.entity.configu import static javax.persistence.CascadeType.ALL; +import java.time.OffsetDateTime; import java.util.ArrayList; import java.util.List; @@ -64,6 +65,8 @@ public class TypeEntity { private boolean systemManaged; @Column private boolean autoHideSkipped; + @Column + private OffsetDateTime softDeletedTime; @Fetch(FetchMode.SUBSELECT) @BatchSize(size = 500) @@ -94,4 +97,7 @@ public class TypeEntity { @Column(updatable = false, insertable = false, name = "dossier_id") private String dossierId; + public boolean isDeleted() { + return this.softDeletedTime !=null; + } } diff --git a/persistence-service-v1/persistence-service-processor-v1/src/main/java/com/iqser/red/service/persistence/management/v1/processor/service/DossierTemplateCloneService.java b/persistence-service-v1/persistence-service-processor-v1/src/main/java/com/iqser/red/service/persistence/management/v1/processor/service/DossierTemplateCloneService.java index 485e0fa19..4091f76bf 100644 --- a/persistence-service-v1/persistence-service-processor-v1/src/main/java/com/iqser/red/service/persistence/management/v1/processor/service/DossierTemplateCloneService.java +++ b/persistence-service-v1/persistence-service-processor-v1/src/main/java/com/iqser/red/service/persistence/management/v1/processor/service/DossierTemplateCloneService.java @@ -10,13 +10,10 @@ import java.util.List; import java.util.UUID; import java.util.stream.Collectors; +import com.iqser.red.service.persistence.management.v1.processor.entity.configuration.*; import org.springframework.beans.BeanUtils; import org.springframework.stereotype.Service; -import com.iqser.red.service.persistence.management.v1.processor.entity.configuration.ColorsEntity; -import com.iqser.red.service.persistence.management.v1.processor.entity.configuration.FileAttributesGeneralConfigurationEntity; -import com.iqser.red.service.persistence.management.v1.processor.entity.configuration.TypeEntity; -import com.iqser.red.service.persistence.management.v1.processor.entity.configuration.WatermarkEntity; import com.iqser.red.service.persistence.management.v1.processor.entity.dossier.DossierAttributeConfigEntity; import com.iqser.red.service.persistence.management.v1.processor.entity.dossier.DossierTemplateEntity; import com.iqser.red.service.persistence.management.v1.processor.entity.dossier.FileAttributeConfigEntity; @@ -139,14 +136,14 @@ public class DossierTemplateCloneService { private List cloneDictionariesWithEntries(String dossierTemplateId, String clonedDossierTemplateId) { List clonedTypes = new ArrayList<>(); - var types = dictionaryPersistenceService.getAllTypesForDossierTemplate(dossierTemplateId); + var types = dictionaryPersistenceService.getAllTypesForDossierTemplate(dossierTemplateId,false); for (TypeEntity t : types) { TypeEntity te = dictionaryPersistenceService.addType(t.getType(), clonedDossierTemplateId, t.getHexColor(), t.getRecommendationHexColor(), t.getRank(), t.isHint(), t.isCaseInsensitive(), t.isRecommendation(), t.getDescription(), t.isAddToDictionaryAction(), t.getLabel(), null, t.isHasDictionary(), t.isSystemManaged(), t.isAutoHideSkipped()); te.setDossierTemplateId(clonedDossierTemplateId); clonedTypes.add(te); for (DictionaryEntryType det : DictionaryEntryType.values()) { var baseDictionaryEntries = entryPersistenceService.getEntries(t.getId(), det, null); - List entries = baseDictionaryEntries.stream().map(baseDictionaryEntry -> baseDictionaryEntry.getValue()).collect(Collectors.toList()); + List entries = baseDictionaryEntries.stream().map(BaseDictionaryEntry::getValue).collect(Collectors.toList()); entryPersistenceService.addEntry(te.getId(), entries, te.getVersion(), det); } } diff --git a/persistence-service-v1/persistence-service-processor-v1/src/main/java/com/iqser/red/service/persistence/management/v1/processor/service/persistence/DictionaryPersistenceService.java b/persistence-service-v1/persistence-service-processor-v1/src/main/java/com/iqser/red/service/persistence/management/v1/processor/service/persistence/DictionaryPersistenceService.java index 3db62528a..43711cb3f 100644 --- a/persistence-service-v1/persistence-service-processor-v1/src/main/java/com/iqser/red/service/persistence/management/v1/processor/service/persistence/DictionaryPersistenceService.java +++ b/persistence-service-v1/persistence-service-processor-v1/src/main/java/com/iqser/red/service/persistence/management/v1/processor/service/persistence/DictionaryPersistenceService.java @@ -1,16 +1,5 @@ package com.iqser.red.service.persistence.management.v1.processor.service.persistence; -import static com.iqser.red.service.persistence.management.v1.processor.utils.TypeIdUtils.toTypeId; - -import java.util.List; -import java.util.Optional; -import java.util.Set; - -import javax.transaction.Transactional; - -import org.springframework.beans.BeanUtils; -import org.springframework.stereotype.Service; - import com.iqser.red.service.persistence.management.v1.processor.entity.configuration.TypeEntity; import com.iqser.red.service.persistence.management.v1.processor.exception.BadRequestException; import com.iqser.red.service.persistence.management.v1.processor.exception.NotFoundException; @@ -19,8 +8,17 @@ import com.iqser.red.service.persistence.management.v1.processor.service.persist import com.iqser.red.service.persistence.management.v1.processor.service.persistence.repository.EntryRepository; import com.iqser.red.service.persistence.management.v1.processor.service.persistence.repository.TypeRepository; import com.iqser.red.service.persistence.service.v1.api.model.dossiertemplate.type.DictionarySummaryResponse; - import lombok.RequiredArgsConstructor; +import org.springframework.beans.BeanUtils; +import org.springframework.stereotype.Service; + +import javax.transaction.Transactional; +import java.util.List; +import java.util.Optional; +import java.util.Set; +import java.util.stream.Collectors; + +import static com.iqser.red.service.persistence.management.v1.processor.utils.TypeIdUtils.toTypeId; @Service @RequiredArgsConstructor @@ -70,6 +68,10 @@ public class DictionaryPersistenceService { public void updateType(String typeId, TypeEntity typeValueRequest) { typeRepository.findById(typeId).ifPresent((type) -> { + if (type.isDeleted()) { + throw new NotFoundException("Type is deleted!"); + } + type.setVersion(type.getVersion() + 1); checkRankAlreadyExists(type.getType(), type.getDossierTemplate().getId(), typeValueRequest.getRank(), type.getDossier() == null ? null : type.getDossier().getId()); if (type.isSystemManaged()) { @@ -84,7 +86,7 @@ public class DictionaryPersistenceService { } - public Optional getTypeForRank(String dossierTemplateId, int rank, String dossierId) { + private Optional getTypeForRank(String dossierTemplateId, int rank, String dossierId) { return typeRepository.findOneByDossierTemplateIdAndDossierIdAndRank(dossierTemplateId, dossierId, rank); @@ -94,47 +96,58 @@ public class DictionaryPersistenceService { private void checkRankAlreadyExists(String type, String dossierTemplateId, int rank, String dossierId) { Optional existingTypeValueForRank = getTypeForRank(dossierTemplateId, rank, dossierId); - // not the current type - which we are about to upsert -> throw exception - if (existingTypeValueForRank.isPresent() && !existingTypeValueForRank.get().getType().equalsIgnoreCase(type)) { + + if (existingTypeValueForRank.isPresent() && !existingTypeValueForRank.get().isDeleted() && !existingTypeValueForRank.get().getType().equalsIgnoreCase(type)) { throw new BadRequestException("Rank already exists: " + rank + " on type: " + existingTypeValueForRank.get().getType()); } + } - public List getCumulatedTypes(String dossierTemplateId, String dossierId) { + public List getCumulatedTypes(String dossierTemplateId, String dossierId, boolean includeDeleted) { - return typeRepository.findAllTypesByDossierTemplateIdOrDossierId(dossierTemplateId, dossierId); + var types = typeRepository.findAllTypesByDossierTemplateIdOrDossierId(dossierTemplateId, dossierId); + return filterDeleted(types,includeDeleted); } - public List getAllTypesForDossierTemplate(String dossierTemplateId) { + public List getAllTypesForDossierTemplate(String dossierTemplateId, boolean includeDeleted) { - return typeRepository.getAllTypesForDossierTemplate(dossierTemplateId); + var types = typeRepository.getAllTypesForDossierTemplate(dossierTemplateId); + return filterDeleted(types, includeDeleted); } - public List getAllTypesForDossier(String dossierId) { + public List getAllTypesForDossier(String dossierId, boolean includeDeleted) { - return typeRepository.findByDossierId(dossierId); + var types = typeRepository.findByDossierId(dossierId); + return filterDeleted(types, includeDeleted); } - public List getAllTypes() { + public List getAllTypes(boolean includeDeleted) { - return typeRepository.findAll(); + var types = typeRepository.findAll(); + return filterDeleted(types, includeDeleted); + } + + private List filterDeleted(List types, boolean includeDeleted) { + if (!includeDeleted) { + return types.stream().filter(t -> !t.isDeleted()).collect(Collectors.toList()); + } else { + return types; + } } @Transactional public void deleteType(String typeId) { - - typeRepository.deleteById(typeId); + typeRepository.softDeleteTypeById(typeId); } public TypeEntity getType(String typeId) { - - return typeRepository.findById(typeId).orElseThrow(() -> new NotFoundException("Type: " + typeId + " not found")); + return typeRepository.findByIdAndNotDeleted(typeId).orElseThrow(() -> new NotFoundException("Type: " + typeId + " not found")); } @@ -166,7 +179,7 @@ public class DictionaryPersistenceService { @Transactional public void updateTypeIdAndIncrementVersionByOne(String typeId, String newTypeId, String newDossierTemplateId) { - Optional typeEntity = typeRepository.findById(typeId); + Optional typeEntity = typeRepository.findByIdAndNotDeleted(typeId); if (typeEntity.isEmpty()) { throw new NotFoundException("Type '" + typeId + "' does not exist."); } diff --git a/persistence-service-v1/persistence-service-processor-v1/src/main/java/com/iqser/red/service/persistence/management/v1/processor/service/persistence/repository/TypeRepository.java b/persistence-service-v1/persistence-service-processor-v1/src/main/java/com/iqser/red/service/persistence/management/v1/processor/service/persistence/repository/TypeRepository.java index e2cbc9b0f..5319dfe49 100644 --- a/persistence-service-v1/persistence-service-processor-v1/src/main/java/com/iqser/red/service/persistence/management/v1/processor/service/persistence/repository/TypeRepository.java +++ b/persistence-service-v1/persistence-service-processor-v1/src/main/java/com/iqser/red/service/persistence/management/v1/processor/service/persistence/repository/TypeRepository.java @@ -14,14 +14,15 @@ import java.util.Set; public interface TypeRepository extends JpaRepository { - Optional findOneByDossierTemplateAndDossierAndRank(DossierTemplateEntity dossierTemplate, DossierEntity dossier, int rank); - + @Query("select t from TypeEntity t where t.dossierTemplateId = :dossierTemplate and t.dossierId = :dossier and t.rank = :rank and t.softDeletedTime is null") Optional findOneByDossierTemplateIdAndDossierIdAndRank(String dossierTemplate, String dossier, int rank); - List findByDossierTemplateId(String dossierTemplateId); - List findByDossierId(String dossierId); + @Query("select t from TypeEntity t where t.id = :typeId and t.softDeletedTime is null") + + Optional findByIdAndNotDeleted(String typeId); + @Modifying @Query("update TypeEntity t set t.version = t.version +1 where t.id = :typeId") void updateByIdSetIncrementVersionByOne(String typeId); @@ -46,4 +47,7 @@ public interface TypeRepository extends JpaRepository { "group by dt.id, t.id, t.type, t.label ") List findDictionarySummaryList(Set dossierTemplateIds); + @Modifying(clearAutomatically = true, flushAutomatically = true) + @Query("Update TypeEntity t set t.softDeletedTime = CURRENT_TIMESTAMP where t.id = :typeId") + void softDeleteTypeById(String typeId); } diff --git a/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/controller/DictionaryController.java b/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/controller/DictionaryController.java index 195854fbe..80e01df78 100644 --- a/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/controller/DictionaryController.java +++ b/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/controller/DictionaryController.java @@ -193,7 +193,7 @@ public class DictionaryController implements DictionaryResource { checkForDuplicateLabels(typeRequest.getDossierTemplateId(), typeRequest.getDossierId(), typeRequest.getType(), typeRequest .getLabel()); - if (dictionaryPersistenceService.getCumulatedTypes(typeRequest.getDossierTemplateId(), typeRequest.getDossierId()) + if (dictionaryPersistenceService.getCumulatedTypes(typeRequest.getDossierTemplateId(), typeRequest.getDossierId(),false) .stream() .anyMatch(typeResult -> typeRequest.getDossierId() != null && typeResult.getDossierId() != null && typeRequest .getDossierId() @@ -231,16 +231,18 @@ public class DictionaryController implements DictionaryResource { @Override public List getAllTypesForDossierTemplate( - @PathVariable(DOSSIER_TEMPLATE_PARAMETER_NAME) String dossierTemplateId) { + @PathVariable(DOSSIER_TEMPLATE_PARAMETER_NAME) String dossierTemplateId, + @RequestParam(value = INCLUDE_DELETED_PARAMETER_NAME, required = false, defaultValue = "false") boolean includeDeleted) { - return convert(dictionaryPersistenceService.getAllTypesForDossierTemplate(dossierTemplateId), Type.class); + return convert(dictionaryPersistenceService.getAllTypesForDossierTemplate(dossierTemplateId,includeDeleted), Type.class); } @Override - public List getAllTypesForDossier(@PathVariable(DOSSIER_ID_PARAMETER_NAME) String dossierId) { + public List getAllTypesForDossier(@PathVariable(DOSSIER_ID_PARAMETER_NAME) String dossierId, + @RequestParam(value = INCLUDE_DELETED_PARAMETER_NAME, required = false, defaultValue = "false") boolean includeDeleted) { - return convert(dictionaryPersistenceService.getAllTypesForDossier(dossierId), Type.class); + return convert(dictionaryPersistenceService.getAllTypesForDossier(dossierId,includeDeleted), Type.class); } @@ -333,7 +335,7 @@ public class DictionaryController implements DictionaryResource { private void checkForDuplicateLabels(String dossierTemplateId, String dossierId, String type, String labelToCheck) { - List typeResponse = dictionaryPersistenceService.getCumulatedTypes(dossierTemplateId, dossierId); + List typeResponse = dictionaryPersistenceService.getCumulatedTypes(dossierTemplateId, dossierId, false); for (TypeEntity res : typeResponse) { if (res.getDossierId() != null && res.getDossierId().equals(dossierId) && !type.equals(res.getType()) && res .getDossierTemplateId() diff --git a/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/migration/migrations/EntityTypesMigration4.java b/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/migration/migrations/EntityTypesMigration4.java index fea9481bc..5f7668180 100644 --- a/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/migration/migrations/EntityTypesMigration4.java +++ b/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/migration/migrations/EntityTypesMigration4.java @@ -47,7 +47,7 @@ public class EntityTypesMigration4 extends Migration { log.info("Will check all type entities and set autoHideSkipped flag true for {}", autoHideSkippedTypes); log.info("Will check all type entities and set hasDictionary flag true for types with entities"); - List types = dictionaryPersistenceService.getAllTypes(); + List types = dictionaryPersistenceService.getAllTypes(false); for (TypeEntity type : types) { if (type != null) { diff --git a/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/migration/migrations/TypeToEntityMigration5.java b/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/migration/migrations/TypeToEntityMigration5.java index 490c7e2fb..81891338f 100644 --- a/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/migration/migrations/TypeToEntityMigration5.java +++ b/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/migration/migrations/TypeToEntityMigration5.java @@ -7,6 +7,7 @@ import java.util.Set; import java.util.regex.Pattern; import java.util.stream.Collectors; +import com.iqser.red.service.persistence.management.v1.processor.entity.configuration.BaseDictionaryEntry; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Service; @@ -50,7 +51,7 @@ public class TypeToEntityMigration5 extends Migration { @Override protected void migrate() { - var types = dictionaryPersistenceService.getAllTypes(); + var types = dictionaryPersistenceService.getAllTypes(false); types.forEach(type -> type.setRecommendationHexColor("#8df06c")); dictionaryPersistenceService.saveAllTypes(types); @@ -59,18 +60,18 @@ public class TypeToEntityMigration5 extends Migration { dossierTemplates.forEach(dossierTemplate -> { log.info("Starting false positive migration of dossierTemplate {}", dossierTemplate.getId()); var typeIdsToDelete = new HashSet(); - var typesOfDossierTemplate = dictionaryPersistenceService.getAllTypes(); + var typesOfDossierTemplate = dictionaryPersistenceService.getAllTypes(false); var falsePositive = typesOfDossierTemplate.stream() .filter(t -> t.getType().equals("false_positive")) .findFirst(); - if (!falsePositive.isPresent()) { + if (falsePositive.isEmpty()) { return; } typeIdsToDelete.add(falsePositive.get().getId()); var falsePositiveEntries = entryPersistenceService.getEntries(falsePositive.get() .getId(), DictionaryEntryType.ENTRY, null) .stream() - .map(f -> f.getValue()) + .map(BaseDictionaryEntry::getValue) .collect(Collectors.toSet()); log.info("False positive migration of dossierTemplate {} has {} false positive entries", dossierTemplate.getId(), falsePositiveEntries.size()); @@ -85,7 +86,7 @@ public class TypeToEntityMigration5 extends Migration { var entries = entryPersistenceService.getEntries(typeEntity.getId(), DictionaryEntryType.ENTRY, null) .stream() - .map(f -> f.getValue()) + .map(BaseDictionaryEntry::getValue) .collect(Collectors.toSet()); log.info("type {} has {} entries", typeEntity.getType(), entries); diff --git a/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/RedactionLogService.java b/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/RedactionLogService.java index 502260ff2..b0a02cf3f 100644 --- a/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/RedactionLogService.java +++ b/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/RedactionLogService.java @@ -1,29 +1,22 @@ package com.iqser.red.service.peristence.v1.server.service; -import java.time.OffsetDateTime; -import java.util.ArrayList; -import java.util.Iterator; -import java.util.List; -import java.util.stream.Collectors; - -import org.springframework.http.HttpStatus; -import org.springframework.stereotype.Service; - import com.iqser.red.service.peristence.v1.server.client.RedactionClient; import com.iqser.red.service.peristence.v1.server.controller.DictionaryController; import com.iqser.red.service.persistence.management.v1.processor.exception.NotFoundException; import com.iqser.red.service.persistence.management.v1.processor.service.persistence.DossierPersistenceService; -import com.iqser.red.service.persistence.service.v1.api.model.annotations.Comment; import com.iqser.red.service.persistence.service.v1.api.model.redactionlog.FilteredRedactionLogRequest; -import com.iqser.red.service.redaction.v1.model.Change; -import com.iqser.red.service.redaction.v1.model.ManualChange; import com.iqser.red.service.redaction.v1.model.RedactionLog; import com.iqser.red.service.redaction.v1.model.RedactionLogEntry; import com.iqser.red.service.redaction.v1.model.RedactionRequest; import com.iqser.red.service.redaction.v1.model.SectionGrid; - import feign.FeignException; import lombok.RequiredArgsConstructor; +import org.springframework.http.HttpStatus; +import org.springframework.stereotype.Service; + +import java.time.OffsetDateTime; +import java.util.Iterator; +import java.util.List; @Service @RequiredArgsConstructor @@ -56,8 +49,8 @@ public class RedactionLogService { var dossier = dossierPersistenceService.findByDossierId(dossierId); var manualRedactions = manualRedactionService.getManualRedactions(fileId); var colors = dictionaryController.getColors(dossier.getDossierTemplateId()); - var types = dictionaryController.getAllTypesForDossierTemplate(dossier.getDossierTemplateId()); - var dossierTypes = dictionaryController.getAllTypesForDossier(dossierId); + var types = dictionaryController.getAllTypesForDossierTemplate(dossier.getDossierTemplateId(), true); + var dossierTypes = dictionaryController.getAllTypesForDossier(dossierId, true); types.addAll(dossierTypes); try { @@ -127,7 +120,7 @@ public class RedactionLogService { } } - if(!isAfterSpecifiedDate) { + if (!isAfterSpecifiedDate) { it.remove(); } diff --git a/persistence-service-v1/persistence-service-server-v1/src/main/resources/db/changelog/22-add-soft-delete-time-to-entity.changelog.yaml b/persistence-service-v1/persistence-service-server-v1/src/main/resources/db/changelog/22-add-soft-delete-time-to-entity.changelog.yaml new file mode 100644 index 000000000..872f30442 --- /dev/null +++ b/persistence-service-v1/persistence-service-server-v1/src/main/resources/db/changelog/22-add-soft-delete-time-to-entity.changelog.yaml @@ -0,0 +1,11 @@ +databaseChangeLog: + - changeSet: + id: add-soft-delete-time-to-entity + author: timo + changes: + - addColumn: + columns: + - column: + name: soft_deleted_time + type: TIMESTAMP WITHOUT TIME ZONE + tableName: entity diff --git a/persistence-service-v1/persistence-service-server-v1/src/test/java/com/iqser/red/service/peristence/v1/server/integration/tests/DictionaryTest.java b/persistence-service-v1/persistence-service-server-v1/src/test/java/com/iqser/red/service/peristence/v1/server/integration/tests/DictionaryTest.java index 2ac1926b1..9b4ef0653 100644 --- a/persistence-service-v1/persistence-service-server-v1/src/test/java/com/iqser/red/service/peristence/v1/server/integration/tests/DictionaryTest.java +++ b/persistence-service-v1/persistence-service-server-v1/src/test/java/com/iqser/red/service/peristence/v1/server/integration/tests/DictionaryTest.java @@ -1,14 +1,5 @@ package com.iqser.red.service.peristence.v1.server.integration.tests; -import static org.assertj.core.api.Assertions.assertThat; - -import java.util.ArrayList; -import java.util.List; -import java.util.stream.Collectors; - -import org.junit.Test; -import org.springframework.beans.factory.annotation.Autowired; - import com.iqser.red.service.peristence.v1.server.integration.client.DictionaryClient; import com.iqser.red.service.peristence.v1.server.integration.client.DossierTemplateClient; import com.iqser.red.service.peristence.v1.server.integration.service.DossierTemplateTesterAndProvider; @@ -17,8 +8,15 @@ import com.iqser.red.service.peristence.v1.server.integration.service.TypeProvid import com.iqser.red.service.peristence.v1.server.integration.utils.AbstractPersistenceServerServiceTest; import com.iqser.red.service.persistence.service.v1.api.model.dossiertemplate.type.DictionaryEntryType; import com.iqser.red.service.persistence.service.v1.api.model.dossiertemplate.type.Type; - import feign.FeignException; +import org.junit.Test; +import org.springframework.beans.factory.annotation.Autowired; + +import java.util.ArrayList; +import java.util.List; +import java.util.stream.Collectors; + +import static org.assertj.core.api.Assertions.assertThat; public class DictionaryTest extends AbstractPersistenceServerServiceTest { @@ -258,9 +256,9 @@ public class DictionaryTest extends AbstractPersistenceServerServiceTest { .dossierId(dossier2.getId()) .build()); - assertThat(dictionaryClient.getAllTypesForDossierTemplate(dossier.getDossierTemplateId())).isEmpty(); - assertThat(dictionaryClient.getAllTypesForDossier(dossier.getId()).size()).isEqualTo(1); - assertThat(dictionaryClient.getAllTypesForDossier(dossier2.getId()).size()).isEqualTo(1); + assertThat(dictionaryClient.getAllTypesForDossierTemplate(dossier.getDossierTemplateId(), false)).isEmpty(); + assertThat(dictionaryClient.getAllTypesForDossier(dossier.getId(), false).size()).isEqualTo(1); + assertThat(dictionaryClient.getAllTypesForDossier(dossier2.getId(), false).size()).isEqualTo(1); } } diff --git a/persistence-service-v1/persistence-service-server-v1/src/test/java/com/iqser/red/service/peristence/v1/server/integration/tests/DossierTemplateTest.java b/persistence-service-v1/persistence-service-server-v1/src/test/java/com/iqser/red/service/peristence/v1/server/integration/tests/DossierTemplateTest.java index 40f392d45..c0684f024 100644 --- a/persistence-service-v1/persistence-service-server-v1/src/test/java/com/iqser/red/service/peristence/v1/server/integration/tests/DossierTemplateTest.java +++ b/persistence-service-v1/persistence-service-server-v1/src/test/java/com/iqser/red/service/peristence/v1/server/integration/tests/DossierTemplateTest.java @@ -1,35 +1,12 @@ package com.iqser.red.service.peristence.v1.server.integration.tests; -import static com.iqser.red.service.persistence.management.v1.processor.utils.MagicConverter.convert; -import static org.assertj.core.api.Assertions.assertThat; - -import java.nio.charset.StandardCharsets; -import java.time.OffsetDateTime; -import java.util.Collections; -import java.util.List; - -import org.junit.Test; -import org.springframework.beans.BeanUtils; -import org.springframework.beans.factory.annotation.Autowired; - -import com.iqser.red.service.peristence.v1.server.integration.client.DictionaryClient; -import com.iqser.red.service.peristence.v1.server.integration.client.DossierAttributeConfigClient; -import com.iqser.red.service.peristence.v1.server.integration.client.DossierClient; -import com.iqser.red.service.peristence.v1.server.integration.client.DossierStatusClient; -import com.iqser.red.service.peristence.v1.server.integration.client.DossierTemplateClient; -import com.iqser.red.service.peristence.v1.server.integration.client.FileAttributeConfigClient; -import com.iqser.red.service.peristence.v1.server.integration.client.ReportTemplateClient; -import com.iqser.red.service.peristence.v1.server.integration.client.WatermarkClient; +import com.iqser.red.service.peristence.v1.server.integration.client.*; import com.iqser.red.service.peristence.v1.server.integration.service.DossierTemplateTesterAndProvider; import com.iqser.red.service.peristence.v1.server.integration.service.DossierTesterAndProvider; import com.iqser.red.service.peristence.v1.server.integration.utils.AbstractPersistenceServerServiceTest; import com.iqser.red.service.persistence.management.v1.processor.entity.dossier.DossierTemplateEntity; import com.iqser.red.service.persistence.management.v1.processor.entity.dossier.ReportTemplateEntity; -import com.iqser.red.service.persistence.service.v1.api.model.dossiertemplate.CreateOrUpdateDossierTemplateRequest; -import com.iqser.red.service.persistence.service.v1.api.model.dossiertemplate.DossierAttributeConfig; -import com.iqser.red.service.persistence.service.v1.api.model.dossiertemplate.DossierTemplateStatus; -import com.iqser.red.service.persistence.service.v1.api.model.dossiertemplate.FileAttributesGeneralConfiguration; -import com.iqser.red.service.persistence.service.v1.api.model.dossiertemplate.ReportTemplateUploadRequest; +import com.iqser.red.service.persistence.service.v1.api.model.dossiertemplate.*; import com.iqser.red.service.persistence.service.v1.api.model.dossiertemplate.configuration.Colors; import com.iqser.red.service.persistence.service.v1.api.model.dossiertemplate.configuration.Watermark; import com.iqser.red.service.persistence.service.v1.api.model.dossiertemplate.configuration.WatermarkOrientation; @@ -40,8 +17,18 @@ import com.iqser.red.service.persistence.service.v1.api.model.dossiertemplate.do import com.iqser.red.service.persistence.service.v1.api.model.dossiertemplate.type.DictionaryEntry; import com.iqser.red.service.persistence.service.v1.api.model.dossiertemplate.type.DictionaryEntryType; import com.iqser.red.service.persistence.service.v1.api.model.dossiertemplate.type.Type; - import feign.FeignException; +import org.junit.Test; +import org.springframework.beans.BeanUtils; +import org.springframework.beans.factory.annotation.Autowired; + +import java.nio.charset.StandardCharsets; +import java.time.OffsetDateTime; +import java.util.Collections; +import java.util.List; + +import static com.iqser.red.service.persistence.management.v1.processor.utils.MagicConverter.convert; +import static org.assertj.core.api.Assertions.assertThat; public class DossierTemplateTest extends AbstractPersistenceServerServiceTest { @@ -282,9 +269,9 @@ public class DossierTemplateTest extends AbstractPersistenceServerServiceTest { .getFileName()).isEqualTo(reportTemplateClient.getAvailableReportTemplates(clonedDT.getId()).get(0).getFileName()); assertThat(watermarkClient.getWatermark(dossierTemplate.getId()).getText()).isEqualTo(watermarkClient.getWatermark(clonedDT.getId()).getText()); assertThat(dictionaryClient.getColors(dossierTemplate.getId()).getRequestAdd()).isEqualTo(dictionaryClient.getColors(clonedDT.getId()).getRequestAdd()); - assertThat(dictionaryClient.getAllTypesForDossierTemplate(dossierTemplate.getId()) + assertThat(dictionaryClient.getAllTypesForDossierTemplate(dossierTemplate.getId(), false) .get(0) - .getRank()).isEqualTo(dictionaryClient.getAllTypesForDossierTemplate(clonedDT.getId()).get(0).getRank()); + .getRank()).isEqualTo(dictionaryClient.getAllTypesForDossierTemplate(clonedDT.getId(), false).get(0).getRank()); assertThat(dossierStatusClient.getAllDossierStatuses(List.of(dossierTemplate.getId())) .get(0) .getDescription()).isEqualTo(dossierStatusClient.getAllDossierStatuses(List.of(clonedDT.getId())).get(0).getDescription()); diff --git a/persistence-service-v1/persistence-service-server-v1/src/test/java/com/iqser/red/service/peristence/v1/server/integration/tests/TypeTest.java b/persistence-service-v1/persistence-service-server-v1/src/test/java/com/iqser/red/service/peristence/v1/server/integration/tests/TypeTest.java index 828faa704..064d46319 100644 --- a/persistence-service-v1/persistence-service-server-v1/src/test/java/com/iqser/red/service/peristence/v1/server/integration/tests/TypeTest.java +++ b/persistence-service-v1/persistence-service-server-v1/src/test/java/com/iqser/red/service/peristence/v1/server/integration/tests/TypeTest.java @@ -75,14 +75,14 @@ public class TypeTest extends AbstractPersistenceServerServiceTest { dictionaryClient.deleteType(type.getId()); - var typesForTemplate = dictionaryClient.getAllTypesForDossierTemplate(loadedType.getDossierTemplateId()); + var typesForTemplate = dictionaryClient.getAllTypesForDossierTemplate(loadedType.getDossierTemplateId(), false); assertThat(typesForTemplate).isEmpty(); var dossier = dossierTesterAndProvider.provideTestDossier(dossierTemplate); var dossierType = typeProvider.testAndProvideType(dossierTemplate, dossier, "dossier-dict"); - var typesForDossier = dictionaryClient.getAllTypesForDossier(dossierType.getDossierId()); + var typesForDossier = dictionaryClient.getAllTypesForDossier(dossierType.getDossierId(), false); assertThat(typesForDossier).isNotEmpty(); } From 388fef77866a844e60e3ee3ee029f984feee6827 Mon Sep 17 00:00:00 2001 From: Timo Bejan Date: Tue, 19 Apr 2022 14:22:23 +0300 Subject: [PATCH 2/6] soft delete types RED-3880 --- .../src/main/resources/db/changelog/db.changelog-master.yaml | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/persistence-service-v1/persistence-service-server-v1/src/main/resources/db/changelog/db.changelog-master.yaml b/persistence-service-v1/persistence-service-server-v1/src/main/resources/db/changelog/db.changelog-master.yaml index e478406e0..83189cb94 100644 --- a/persistence-service-v1/persistence-service-server-v1/src/main/resources/db/changelog/db.changelog-master.yaml +++ b/persistence-service-v1/persistence-service-server-v1/src/main/resources/db/changelog/db.changelog-master.yaml @@ -50,4 +50,6 @@ databaseChangeLog: - include: file: db/changelog/21-added-auto-hide-skipped-to-entities.changelog.yaml - include: - file: db/changelog/sql/22-update-file-dossier-attributes.sql \ No newline at end of file + file: db/changelog/sql/22-update-file-dossier-attributes.sql + - include: + file: db/changelog/22-add-soft-delete-time-to-entity.changelog.yaml From 6bfbeedd25d398129895c1ca79521f81a045ec18 Mon Sep 17 00:00:00 2001 From: Timo Bejan Date: Tue, 19 Apr 2022 15:01:11 +0300 Subject: [PATCH 3/6] RED-3737 passing file-name to pdftron for office to pdf conversion --- .../migration/migrations/MigrateHighlights3.java | 10 ++++------ .../peristence/v1/server/service/FileService.java | 2 +- persistence-service-v1/pom.xml | 2 +- 3 files changed, 6 insertions(+), 8 deletions(-) diff --git a/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/migration/migrations/MigrateHighlights3.java b/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/migration/migrations/MigrateHighlights3.java index f4b602531..61434eb7c 100644 --- a/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/migration/migrations/MigrateHighlights3.java +++ b/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/migration/migrations/MigrateHighlights3.java @@ -1,8 +1,5 @@ package com.iqser.red.service.peristence.v1.server.migration.migrations; -import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.stereotype.Service; - import com.iqser.red.service.pdftron.redaction.v1.api.model.DocumentRequest; import com.iqser.red.service.peristence.v1.server.migration.Migration; import com.iqser.red.service.peristence.v1.server.service.FileManagementStorageService; @@ -10,9 +7,10 @@ import com.iqser.red.service.persistence.management.v1.processor.client.PDFTronR import com.iqser.red.service.persistence.management.v1.processor.service.persistence.DossierPersistenceService; import com.iqser.red.service.persistence.management.v1.processor.service.persistence.FileStatusPersistenceService; import com.iqser.red.service.persistence.service.v1.api.model.dossiertemplate.dossier.file.FileType; - import lombok.Setter; import lombok.extern.slf4j.Slf4j; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; @Slf4j @Setter @@ -51,11 +49,11 @@ public class MigrateHighlights3 extends Migration { if (file.getHardDeletedTime() == null) { var fileBytes = fileManagementStorageService.getStoredObjectBytes(dossier.getId(), file.getId(), FileType.ORIGIN); - var hasHighlights = pdfTronRedactionClient.extractHighlights(new DocumentRequest(dossier.getId(), file.getId(), fileBytes)); + var hasHighlights = pdfTronRedactionClient.extractHighlights(new DocumentRequest(dossier.getId(), file.getId(), file.getFilename(), fileBytes)); fileStatusPersistenceService.updateHasHighlights(file.getId(), hasHighlights); } }); }); } -} \ No newline at end of file +} diff --git a/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/FileService.java b/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/FileService.java index 2d9200d6e..35aa62ef4 100644 --- a/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/FileService.java +++ b/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/FileService.java @@ -78,7 +78,7 @@ public class FileService { boolean hasHighlights; try { - hasHighlights = pdfTronRedactionClient.saveOptimizedAndAnnotations(new DocumentRequest(request.getDossierId(), fileId, request.getData())); + hasHighlights = pdfTronRedactionClient.saveOptimizedAndAnnotations(new DocumentRequest(request.getDossierId(), fileId, request.getFilename(), request.getData())); } catch (FeignException e) { log.warn("Failed to optimize file: {}", request.getFilename(), e); diff --git a/persistence-service-v1/pom.xml b/persistence-service-v1/pom.xml index 8fee2e801..cb866bebd 100755 --- a/persistence-service-v1/pom.xml +++ b/persistence-service-v1/pom.xml @@ -27,7 +27,7 @@ 3.93.0 2.26.0 - 3.63.0 + 3.69.0 3.19.0 From b6ca3e1e638b04bb4c458898e976e9c7ee805605 Mon Sep 17 00:00:00 2001 From: Timo Bejan Date: Tue, 19 Apr 2022 15:29:34 +0300 Subject: [PATCH 4/6] quartz jobs RED-3848 --- .dev/docker-compose.yaml | 9 +- .../persistence-service-server-v1/pom.xml | 11 +- .../server/jobs/CreateJobsConfiguration.java | 70 +++ .../AutomaticAnalysisJob.java} | 20 +- .../DeletedFilesCleanupJob.java} | 13 +- .../DownloadCleanupJob.java} | 14 +- .../db/changelog/23-quartz.changelog.yaml | 536 ++++++++++++++++++ .../db/changelog/db.changelog-master.yaml | 2 + 8 files changed, 641 insertions(+), 34 deletions(-) create mode 100644 persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/jobs/CreateJobsConfiguration.java rename persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/{scheduler/AutomaticAnalysisScheduler.java => job/AutomaticAnalysisJob.java} (83%) rename persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/{scheduler/DeletedFilesCleanupService.java => job/DeletedFilesCleanupJob.java} (85%) rename persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/{download/DownloadCleanupService.java => job/DownloadCleanupJob.java} (90%) create mode 100644 persistence-service-v1/persistence-service-server-v1/src/main/resources/db/changelog/23-quartz.changelog.yaml diff --git a/.dev/docker-compose.yaml b/.dev/docker-compose.yaml index 00f6876c9..480b416cd 100644 --- a/.dev/docker-compose.yaml +++ b/.dev/docker-compose.yaml @@ -11,13 +11,12 @@ services: POSTGRES_USER: redaction POSTGRES_PASSWORD: redaction POSTGRES_DB: redaction - - rabbitmq: - image: 'bitnami/rabbitmq:latest' - mem_limit: 1000m + image: 'rabbitmq:3.9-alpine' + mem_limit: 500m environment: - - RABBITMQ_PASSWORD=rabbitmq + - RABBITMQ_DEFAULT_USER=user + - RABBITMQ_DEFAULT_PASS=rabbitmq ports: - 5672:5672 - 15672:15672 diff --git a/persistence-service-v1/persistence-service-server-v1/pom.xml b/persistence-service-v1/persistence-service-server-v1/pom.xml index ec96d4983..a9374549d 100644 --- a/persistence-service-v1/persistence-service-server-v1/pom.xml +++ b/persistence-service-v1/persistence-service-server-v1/pom.xml @@ -139,24 +139,27 @@ spring-cloud-starter-openfeign + + org.springframework.boot + spring-boot-starter-quartz + + org.springframework.boot spring-boot-starter-amqp - 2.3.1.RELEASE org.springframework.amqp spring-rabbit-test - 2.3.1 test org.testcontainers postgresql - 1.16.3 + 1.17.1 test @@ -172,7 +175,7 @@ org.liquibase liquibase-core - 4.3.1 + 4.8.0 com.yannbriancon diff --git a/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/jobs/CreateJobsConfiguration.java b/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/jobs/CreateJobsConfiguration.java new file mode 100644 index 000000000..0c2f42fec --- /dev/null +++ b/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/jobs/CreateJobsConfiguration.java @@ -0,0 +1,70 @@ +package com.iqser.red.service.peristence.v1.server.jobs; + +import com.iqser.red.service.peristence.v1.server.service.job.AutomaticAnalysisJob; +import com.iqser.red.service.peristence.v1.server.service.job.DeletedFilesCleanupJob; +import com.iqser.red.service.peristence.v1.server.service.job.DownloadCleanupJob; +import org.quartz.*; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; + +import java.text.ParseException; + +@Configuration +public class CreateJobsConfiguration { + + @Bean + public JobDetail automaticAnalysisJobDetail() { + return JobBuilder.newJob().ofType(AutomaticAnalysisJob.class) + .storeDurably() + .withIdentity("AutomaticAnalysisJob") + .withDescription("Automatically queues files for analysis") + .build(); + } + + @Bean + public Trigger automaticAnalysisJobTrigger() throws ParseException { + return TriggerBuilder.newTrigger().forJob(automaticAnalysisJobDetail()) + .withIdentity("AutomaticAnalysisJobTrigger") + .withDescription("Triggers AutomaticAnalysisJob every 10 seconds") + .withSchedule(CronScheduleBuilder.cronSchedule(new CronExpression("*/10 * * * * ?"))) + .build(); + } + + @Bean + public JobDetail deletedFilesCleanupJobDetail() { + return JobBuilder.newJob().ofType(DeletedFilesCleanupJob.class) + .storeDurably() + .withIdentity("DeletedFilesCleanupJob") + .withDescription("Hard delete dossiers / files after certain time") + .build(); + } + + @Bean + public Trigger deletedFilesCleanupJobTrigger() throws ParseException { + return TriggerBuilder.newTrigger().forJob(deletedFilesCleanupJobDetail()) + .withIdentity("DeletedFilesCleanupJobTrigger") + .withDescription("Triggers DeletedFilesCleanupJob every 30 minutes") + .withSchedule(CronScheduleBuilder.cronSchedule(new CronExpression("0 */30 * * * ?"))) + .build(); + } + + + @Bean + public JobDetail downloadCleanupJobDetail() { + return JobBuilder.newJob().ofType(DownloadCleanupJob.class) + .storeDurably() + .withIdentity("DownloadCleanupJob") + .withDescription("Hard delete dossiers / files after certain time") + .build(); + } + + @Bean + public Trigger downloadCleanupJobTrigger() throws ParseException { + return TriggerBuilder.newTrigger().forJob(downloadCleanupJobDetail()) + .withIdentity("DownloadCleanupJobTrigger") + .withDescription("Triggers DownloadCleanupJob every 30 minutes") + .withSchedule(CronScheduleBuilder.cronSchedule(new CronExpression("0 */30 * * * ?"))) + .build(); + } + +} diff --git a/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/scheduler/AutomaticAnalysisScheduler.java b/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/job/AutomaticAnalysisJob.java similarity index 83% rename from persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/scheduler/AutomaticAnalysisScheduler.java rename to persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/job/AutomaticAnalysisJob.java index 364e01504..21ffc26ca 100644 --- a/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/scheduler/AutomaticAnalysisScheduler.java +++ b/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/job/AutomaticAnalysisJob.java @@ -1,30 +1,25 @@ -package com.iqser.red.service.peristence.v1.server.service.scheduler; +package com.iqser.red.service.peristence.v1.server.service.job; import com.iqser.red.service.peristence.v1.server.configuration.MessagingConfiguration; import com.iqser.red.service.peristence.v1.server.service.FileStatusService; -import com.iqser.red.service.peristence.v1.server.service.ReanalysisRequiredStatusService; import com.iqser.red.service.peristence.v1.server.settings.FileManagementServiceSettings; -import com.iqser.red.service.peristence.v1.server.utils.FileModelMapper; import com.iqser.red.service.persistence.service.v1.api.model.dossiertemplate.dossier.file.FileModel; import lombok.RequiredArgsConstructor; import lombok.extern.slf4j.Slf4j; +import org.quartz.Job; +import org.quartz.JobExecutionContext; import org.springframework.amqp.core.AmqpAdmin; import org.springframework.beans.factory.annotation.Value; -import org.springframework.scheduling.annotation.Scheduled; import org.springframework.stereotype.Service; import org.springframework.transaction.annotation.Transactional; import javax.annotation.PostConstruct; -import java.util.ArrayList; import java.util.List; -import java.util.stream.Collectors; - -import static com.iqser.red.service.persistence.management.v1.processor.utils.MagicConverter.convert; @Slf4j @Service @RequiredArgsConstructor -public class AutomaticAnalysisScheduler { +public class AutomaticAnalysisJob implements Job { @Value("${persistence-service.automaticAnalysis.pageFactor:500}") private int pageFactor; @@ -35,16 +30,15 @@ public class AutomaticAnalysisScheduler { @PostConstruct protected void postConstruct() { - log.info("Automatic Analysis pageFactor: {}", pageFactor); } + @Override @Transactional - @Scheduled(fixedDelay = 10000, initialDelay = 10000) - public void checkFilesThatRequireReanalysisAndQueueIfPossible() { + public void execute(JobExecutionContext jobExecutionContext) { - if(fileManagementServiceSettings.isMigrateOnly()){ + if (fileManagementServiceSettings.isMigrateOnly()) { log.info("Skipping scheduling during migration"); return; } diff --git a/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/scheduler/DeletedFilesCleanupService.java b/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/job/DeletedFilesCleanupJob.java similarity index 85% rename from persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/scheduler/DeletedFilesCleanupService.java rename to persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/job/DeletedFilesCleanupJob.java index 4f3937bb6..269340a94 100644 --- a/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/scheduler/DeletedFilesCleanupService.java +++ b/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/job/DeletedFilesCleanupJob.java @@ -1,9 +1,10 @@ -package com.iqser.red.service.peristence.v1.server.service.scheduler; +package com.iqser.red.service.peristence.v1.server.service.job; import java.time.OffsetDateTime; import java.util.List; -import org.springframework.scheduling.annotation.Scheduled; +import org.quartz.Job; +import org.quartz.JobExecutionContext; import org.springframework.stereotype.Service; import com.iqser.red.service.peristence.v1.server.service.DossierService; @@ -11,7 +12,6 @@ import com.iqser.red.service.peristence.v1.server.service.FileService; import com.iqser.red.service.peristence.v1.server.service.FileStatusService; import com.iqser.red.service.peristence.v1.server.settings.FileManagementServiceSettings; import com.iqser.red.service.persistence.management.v1.processor.entity.dossier.DossierEntity; -import com.iqser.red.service.persistence.management.v1.processor.entity.dossier.FileEntity; import lombok.RequiredArgsConstructor; import lombok.extern.slf4j.Slf4j; @@ -19,7 +19,7 @@ import lombok.extern.slf4j.Slf4j; @Slf4j @RequiredArgsConstructor @Service -public class DeletedFilesCleanupService { +public class DeletedFilesCleanupJob implements Job { private final DossierService dossierService; private final FileStatusService fileStatusService; @@ -27,8 +27,8 @@ public class DeletedFilesCleanupService { private final FileManagementServiceSettings settings; - @Scheduled(fixedDelay = 300000, initialDelay = 300000) - public void timedDeletion() { + @Override + public void execute(JobExecutionContext jobExecutionContext) { var now = OffsetDateTime.now(); List dossiers = dossierService.getAllDossiers(); @@ -53,4 +53,5 @@ public class DeletedFilesCleanupService { } } + } diff --git a/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/download/DownloadCleanupService.java b/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/job/DownloadCleanupJob.java similarity index 90% rename from persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/download/DownloadCleanupService.java rename to persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/job/DownloadCleanupJob.java index 07f95d6f8..db6eaebed 100644 --- a/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/download/DownloadCleanupService.java +++ b/persistence-service-v1/persistence-service-server-v1/src/main/java/com/iqser/red/service/peristence/v1/server/service/job/DownloadCleanupJob.java @@ -1,4 +1,4 @@ -package com.iqser.red.service.peristence.v1.server.service.download; +package com.iqser.red.service.peristence.v1.server.service.job; import com.iqser.red.service.peristence.v1.server.service.DossierService; import com.iqser.red.service.peristence.v1.server.settings.FileManagementServiceSettings; @@ -7,7 +7,8 @@ import com.iqser.red.service.persistence.management.v1.processor.service.persist import com.iqser.red.storage.commons.service.StorageService; import lombok.RequiredArgsConstructor; import lombok.extern.slf4j.Slf4j; -import org.springframework.scheduling.annotation.Scheduled; +import org.quartz.Job; +import org.quartz.JobExecutionContext; import org.springframework.stereotype.Service; import java.time.OffsetDateTime; @@ -17,15 +18,15 @@ import java.util.List; @Slf4j @RequiredArgsConstructor @Service -public class DownloadCleanupService { +public class DownloadCleanupJob implements Job { private final DownloadStatusPersistenceService downloadStatusPersistenceService; private final StorageService storageService; private final FileManagementServiceSettings settings; private final DossierService dossierService; - @Scheduled(fixedDelay = 300000, initialDelay = 300000) - public void processDocuments() { + @Override + public void execute(JobExecutionContext jobExecutionContext) { var now = OffsetDateTime.now().truncatedTo(ChronoUnit.MILLIS); log.info("Checking for downloads to delete at {}", now); @@ -56,7 +57,7 @@ public class DownloadCleanupService { } - public void deleteDownload(DownloadStatusEntity downloadStatus) { + private void deleteDownload(DownloadStatusEntity downloadStatus) { log.info("Deleting download status {}", downloadStatus); try { @@ -70,4 +71,5 @@ public class DownloadCleanupService { log.warn("DownloadStatus could not be deleted: {}" + e.getMessage()); } } + } diff --git a/persistence-service-v1/persistence-service-server-v1/src/main/resources/db/changelog/23-quartz.changelog.yaml b/persistence-service-v1/persistence-service-server-v1/src/main/resources/db/changelog/23-quartz.changelog.yaml new file mode 100644 index 000000000..cd8fad44f --- /dev/null +++ b/persistence-service-v1/persistence-service-server-v1/src/main/resources/db/changelog/23-quartz.changelog.yaml @@ -0,0 +1,536 @@ +databaseChangeLog: + - changeSet: + id: 1646818341589-1 + author: timobejan (generated) + changes: + - createTable: + columns: + - column: + constraints: + nullable: false + primaryKey: true + name: SCHED_NAME + type: VARCHAR(120) + - column: + constraints: + nullable: false + primaryKey: true + name: TRIGGER_NAME + type: VARCHAR(200) + - column: + constraints: + nullable: false + primaryKey: true + name: TRIGGER_GROUP + type: VARCHAR(200) + - column: + name: BLOB_DATA + type: BLOB + tableName: QRTZ_BLOB_TRIGGERS + - changeSet: + id: 1646818341589-2 + author: timobejan (generated) + changes: + - createTable: + columns: + - column: + constraints: + nullable: false + primaryKey: true + name: SCHED_NAME + type: VARCHAR(120) + - column: + constraints: + nullable: false + primaryKey: true + name: CALENDAR_NAME + type: VARCHAR(200) + - column: + constraints: + nullable: false + name: CALENDAR + type: BLOB + tableName: QRTZ_CALENDARS + - changeSet: + id: 1646818341589-3 + author: timobejan (generated) + changes: + - createTable: + columns: + - column: + constraints: + nullable: false + primaryKey: true + name: SCHED_NAME + type: VARCHAR(120) + - column: + constraints: + nullable: false + primaryKey: true + name: TRIGGER_NAME + type: VARCHAR(200) + - column: + constraints: + nullable: false + primaryKey: true + name: TRIGGER_GROUP + type: VARCHAR(200) + - column: + constraints: + nullable: false + name: CRON_EXPRESSION + type: VARCHAR(200) + - column: + name: TIME_ZONE_ID + type: VARCHAR(80) + tableName: QRTZ_CRON_TRIGGERS + - changeSet: + id: 1646818341589-4 + author: timobejan (generated) + changes: + - createTable: + columns: + - column: + constraints: + nullable: false + primaryKey: true + name: SCHED_NAME + type: VARCHAR(120) + - column: + constraints: + nullable: false + primaryKey: true + name: ENTRY_ID + type: VARCHAR(95) + - column: + constraints: + nullable: false + name: TRIGGER_NAME + type: VARCHAR(200) + - column: + constraints: + nullable: false + name: TRIGGER_GROUP + type: VARCHAR(200) + - column: + constraints: + nullable: false + name: INSTANCE_NAME + type: VARCHAR(200) + - column: + constraints: + nullable: false + name: FIRED_TIME + type: BIGINT + - column: + constraints: + nullable: false + name: SCHED_TIME + type: BIGINT + - column: + constraints: + nullable: false + name: PRIORITY + type: INT + - column: + constraints: + nullable: false + name: STATE + type: VARCHAR(16) + - column: + name: JOB_NAME + type: VARCHAR(200) + - column: + name: JOB_GROUP + type: VARCHAR(200) + - column: + name: IS_NONCONCURRENT + type: VARCHAR(1) + - column: + name: REQUESTS_RECOVERY + type: VARCHAR(1) + tableName: QRTZ_FIRED_TRIGGERS + - changeSet: + id: 1646818341589-5 + author: timobejan (generated) + changes: + - createTable: + columns: + - column: + constraints: + nullable: false + primaryKey: true + name: SCHED_NAME + type: VARCHAR(120) + - column: + constraints: + nullable: false + primaryKey: true + name: JOB_NAME + type: VARCHAR(200) + - column: + constraints: + nullable: false + primaryKey: true + name: JOB_GROUP + type: VARCHAR(200) + - column: + name: DESCRIPTION + type: VARCHAR(250) + - column: + constraints: + nullable: false + name: JOB_CLASS_NAME + type: VARCHAR(250) + - column: + constraints: + nullable: false + name: IS_DURABLE + type: VARCHAR(1) + - column: + constraints: + nullable: false + name: IS_NONCONCURRENT + type: VARCHAR(1) + - column: + constraints: + nullable: false + name: IS_UPDATE_DATA + type: VARCHAR(1) + - column: + constraints: + nullable: false + name: REQUESTS_RECOVERY + type: VARCHAR(1) + - column: + name: JOB_DATA + type: BLOB + tableName: QRTZ_JOB_DETAILS + - changeSet: + id: 1646818341589-6 + author: timobejan (generated) + changes: + - createTable: + columns: + - column: + constraints: + nullable: false + primaryKey: true + name: SCHED_NAME + type: VARCHAR(120) + - column: + constraints: + nullable: false + primaryKey: true + name: LOCK_NAME + type: VARCHAR(40) + tableName: QRTZ_LOCKS + - changeSet: + id: 1646818341589-7 + author: timobejan (generated) + changes: + - createTable: + columns: + - column: + constraints: + nullable: false + primaryKey: true + name: SCHED_NAME + type: VARCHAR(120) + - column: + constraints: + nullable: false + primaryKey: true + name: TRIGGER_GROUP + type: VARCHAR(200) + tableName: QRTZ_PAUSED_TRIGGER_GRPS + - changeSet: + id: 1646818341589-8 + author: timobejan (generated) + changes: + - createTable: + columns: + - column: + constraints: + nullable: false + primaryKey: true + name: SCHED_NAME + type: VARCHAR(120) + - column: + constraints: + nullable: false + primaryKey: true + name: INSTANCE_NAME + type: VARCHAR(200) + - column: + constraints: + nullable: false + name: LAST_CHECKIN_TIME + type: BIGINT + - column: + constraints: + nullable: false + name: CHECKIN_INTERVAL + type: BIGINT + tableName: QRTZ_SCHEDULER_STATE + - changeSet: + id: 1646818341589-9 + author: timobejan (generated) + changes: + - createTable: + columns: + - column: + constraints: + nullable: false + primaryKey: true + name: SCHED_NAME + type: VARCHAR(120) + - column: + constraints: + nullable: false + primaryKey: true + name: TRIGGER_NAME + type: VARCHAR(200) + - column: + constraints: + nullable: false + primaryKey: true + name: TRIGGER_GROUP + type: VARCHAR(200) + - column: + constraints: + nullable: false + name: REPEAT_COUNT + type: BIGINT + - column: + constraints: + nullable: false + name: REPEAT_INTERVAL + type: BIGINT + - column: + constraints: + nullable: false + name: TIMES_TRIGGERED + type: BIGINT + tableName: QRTZ_SIMPLE_TRIGGERS + - changeSet: + id: 1646818341589-10 + author: timobejan (generated) + changes: + - createTable: + columns: + - column: + constraints: + nullable: false + primaryKey: true + name: SCHED_NAME + type: VARCHAR(120) + - column: + constraints: + nullable: false + primaryKey: true + name: TRIGGER_NAME + type: VARCHAR(200) + - column: + constraints: + nullable: false + primaryKey: true + name: TRIGGER_GROUP + type: VARCHAR(200) + - column: + name: STR_PROP_1 + type: VARCHAR(512) + - column: + name: STR_PROP_2 + type: VARCHAR(512) + - column: + name: STR_PROP_3 + type: VARCHAR(512) + - column: + name: INT_PROP_1 + type: INT + - column: + name: INT_PROP_2 + type: INT + - column: + name: LONG_PROP_1 + type: BIGINT + - column: + name: LONG_PROP_2 + type: BIGINT + - column: + name: DEC_PROP_1 + type: DECIMAL(13, 4) + - column: + name: DEC_PROP_2 + type: DECIMAL(13, 4) + - column: + name: BOOL_PROP_1 + type: VARCHAR(1) + - column: + name: BOOL_PROP_2 + type: VARCHAR(1) + tableName: QRTZ_SIMPROP_TRIGGERS + - changeSet: + id: 1646818341589-11 + author: timobejan (generated) + changes: + - createTable: + columns: + - column: + constraints: + nullable: false + primaryKey: true + name: SCHED_NAME + type: VARCHAR(120) + - column: + constraints: + nullable: false + primaryKey: true + name: TRIGGER_NAME + type: VARCHAR(200) + - column: + constraints: + nullable: false + primaryKey: true + name: TRIGGER_GROUP + type: VARCHAR(200) + - column: + constraints: + nullable: false + name: JOB_NAME + type: VARCHAR(200) + - column: + constraints: + nullable: false + name: JOB_GROUP + type: VARCHAR(200) + - column: + name: DESCRIPTION + type: VARCHAR(250) + - column: + name: NEXT_FIRE_TIME + type: BIGINT + - column: + name: PREV_FIRE_TIME + type: BIGINT + - column: + name: PRIORITY + type: INT + - column: + constraints: + nullable: false + name: TRIGGER_STATE + type: VARCHAR(16) + - column: + constraints: + nullable: false + name: TRIGGER_TYPE + type: VARCHAR(8) + - column: + constraints: + nullable: false + name: START_TIME + type: BIGINT + - column: + name: END_TIME + type: BIGINT + - column: + name: CALENDAR_NAME + type: VARCHAR(200) + - column: + name: MISFIRE_INSTR + type: SMALLINT + - column: + name: JOB_DATA + type: BLOB + tableName: QRTZ_TRIGGERS + - changeSet: + id: 1646818341589-95 + author: timobejan (generated) + changes: + - createIndex: + columns: + - column: + name: SCHED_NAME + - column: + name: JOB_NAME + - column: + name: JOB_GROUP + indexName: SCHED_NAME + tableName: QRTZ_TRIGGERS + - changeSet: + id: 1646818341589-218 + author: timobejan (generated) + changes: + - addForeignKeyConstraint: + baseColumnNames: SCHED_NAME,TRIGGER_NAME,TRIGGER_GROUP + baseTableName: QRTZ_BLOB_TRIGGERS + constraintName: QRTZ_BLOB_TRIGGERS_ibfk_1 + deferrable: false + initiallyDeferred: false + onDelete: RESTRICT + onUpdate: RESTRICT + referencedColumnNames: SCHED_NAME,TRIGGER_NAME,TRIGGER_GROUP + referencedTableName: QRTZ_TRIGGERS + validate: true + - changeSet: + id: 1646818341589-219 + author: timobejan (generated) + changes: + - addForeignKeyConstraint: + baseColumnNames: SCHED_NAME,TRIGGER_NAME,TRIGGER_GROUP + baseTableName: QRTZ_CRON_TRIGGERS + constraintName: QRTZ_CRON_TRIGGERS_ibfk_1 + deferrable: false + initiallyDeferred: false + onDelete: RESTRICT + onUpdate: RESTRICT + referencedColumnNames: SCHED_NAME,TRIGGER_NAME,TRIGGER_GROUP + referencedTableName: QRTZ_TRIGGERS + validate: true + - changeSet: + id: 1646818341589-220 + author: timobejan (generated) + changes: + - addForeignKeyConstraint: + baseColumnNames: SCHED_NAME,TRIGGER_NAME,TRIGGER_GROUP + baseTableName: QRTZ_SIMPLE_TRIGGERS + constraintName: QRTZ_SIMPLE_TRIGGERS_ibfk_1 + deferrable: false + initiallyDeferred: false + onDelete: RESTRICT + onUpdate: RESTRICT + referencedColumnNames: SCHED_NAME,TRIGGER_NAME,TRIGGER_GROUP + referencedTableName: QRTZ_TRIGGERS + validate: true + - changeSet: + id: 1646818341589-221 + author: timobejan (generated) + changes: + - addForeignKeyConstraint: + baseColumnNames: SCHED_NAME,TRIGGER_NAME,TRIGGER_GROUP + baseTableName: QRTZ_SIMPROP_TRIGGERS + constraintName: QRTZ_SIMPROP_TRIGGERS_ibfk_1 + deferrable: false + initiallyDeferred: false + onDelete: RESTRICT + onUpdate: RESTRICT + referencedColumnNames: SCHED_NAME,TRIGGER_NAME,TRIGGER_GROUP + referencedTableName: QRTZ_TRIGGERS + validate: true + - changeSet: + id: 1646818341589-222 + author: timobejan (generated) + changes: + - addForeignKeyConstraint: + baseColumnNames: SCHED_NAME,JOB_NAME,JOB_GROUP + baseTableName: QRTZ_TRIGGERS + constraintName: QRTZ_TRIGGERS_ibfk_1 + deferrable: false + initiallyDeferred: false + onDelete: RESTRICT + onUpdate: RESTRICT + referencedColumnNames: SCHED_NAME,JOB_NAME,JOB_GROUP + referencedTableName: QRTZ_JOB_DETAILS + validate: true diff --git a/persistence-service-v1/persistence-service-server-v1/src/main/resources/db/changelog/db.changelog-master.yaml b/persistence-service-v1/persistence-service-server-v1/src/main/resources/db/changelog/db.changelog-master.yaml index 83189cb94..16685cf18 100644 --- a/persistence-service-v1/persistence-service-server-v1/src/main/resources/db/changelog/db.changelog-master.yaml +++ b/persistence-service-v1/persistence-service-server-v1/src/main/resources/db/changelog/db.changelog-master.yaml @@ -53,3 +53,5 @@ databaseChangeLog: file: db/changelog/sql/22-update-file-dossier-attributes.sql - include: file: db/changelog/22-add-soft-delete-time-to-entity.changelog.yaml + - include: + file: db/changelog/23-quartz.changelog.yaml From 7043f6e152f369c548f1d6901413ea9b18ddceb2 Mon Sep 17 00:00:00 2001 From: Timo Bejan Date: Tue, 19 Apr 2022 15:55:21 +0300 Subject: [PATCH 5/6] RED-3800 test fix --- persistence-service-v1/persistence-service-server-v1/pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/persistence-service-v1/persistence-service-server-v1/pom.xml b/persistence-service-v1/persistence-service-server-v1/pom.xml index a9374549d..d60de784b 100644 --- a/persistence-service-v1/persistence-service-server-v1/pom.xml +++ b/persistence-service-v1/persistence-service-server-v1/pom.xml @@ -175,7 +175,7 @@ org.liquibase liquibase-core - 4.8.0 + 4.9.1 com.yannbriancon From b47dabbc8f9545658e455bd806c726c1b6970199 Mon Sep 17 00:00:00 2001 From: Timo Bejan Date: Tue, 19 Apr 2022 16:07:53 +0300 Subject: [PATCH 6/6] RED-3800 liquibase revert --- persistence-service-v1/persistence-service-server-v1/pom.xml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/persistence-service-v1/persistence-service-server-v1/pom.xml b/persistence-service-v1/persistence-service-server-v1/pom.xml index d60de784b..4f09bd405 100644 --- a/persistence-service-v1/persistence-service-server-v1/pom.xml +++ b/persistence-service-v1/persistence-service-server-v1/pom.xml @@ -175,7 +175,7 @@ org.liquibase liquibase-core - 4.9.1 + 4.3.1 com.yannbriancon @@ -222,4 +222,5 @@ +