diff --git a/waltz-data/src/main/java/org/finos/waltz/data/attestation/AttestationInstanceDao.java b/waltz-data/src/main/java/org/finos/waltz/data/attestation/AttestationInstanceDao.java index 3fec249eb5..cf8aa42205 100644 --- a/waltz-data/src/main/java/org/finos/waltz/data/attestation/AttestationInstanceDao.java +++ b/waltz-data/src/main/java/org/finos/waltz/data/attestation/AttestationInstanceDao.java @@ -284,22 +284,12 @@ public SyncRecipientsResponse reassignRecipients() { private Set> getAttestationRunIdToInvKindId() { return dsl - .select(ATTESTATION_RUN.ID, ATTESTATION_RUN.INVOLVEMENT_KIND_IDS) + .select(ATTESTATION_RUN.ID, INVOLVEMENT_GROUP_ENTRY.INVOLVEMENT_KIND_ID) .from(ATTESTATION_RUN) - .where(ATTESTATION_RUN.INVOLVEMENT_KIND_IDS.isNotNull()) - .and(ATTESTATION_RUN.INVOLVEMENT_KIND_IDS.ne("")) - .fetch() - .stream() - .flatMap(r -> { - Long runId = r.get(ATTESTATION_RUN.ID); - String invKinds = r.get(ATTESTATION_RUN.INVOLVEMENT_KIND_IDS); - return splitThenMap( - invKinds, - ";", - d -> tuple(runId, Long.valueOf(d.trim()))) - .stream(); - }) - .collect(toSet()); + .innerJoin(INVOLVEMENT_GROUP_ENTRY) + .on(ATTESTATION_RUN.RECIPIENT_INVOLVEMENT_GROUP_ID.eq(INVOLVEMENT_GROUP_ENTRY.INVOLVEMENT_GROUP_ID)) + .where(ATTESTATION_RUN.RECIPIENT_INVOLVEMENT_GROUP_ID.isNotNull()) + .fetchSet(r -> tuple(r.get(ATTESTATION_RUN.ID), r.get(INVOLVEMENT_GROUP_ENTRY.INVOLVEMENT_KIND_ID))); } diff --git a/waltz-data/src/main/java/org/finos/waltz/data/attestation/AttestationRunDao.java b/waltz-data/src/main/java/org/finos/waltz/data/attestation/AttestationRunDao.java index f997e7746c..60262c5a04 100644 --- a/waltz-data/src/main/java/org/finos/waltz/data/attestation/AttestationRunDao.java +++ b/waltz-data/src/main/java/org/finos/waltz/data/attestation/AttestationRunDao.java @@ -18,6 +18,7 @@ package org.finos.waltz.data.attestation; +import org.finos.waltz.data.involvement_group.InvolvementGroupDao; import org.finos.waltz.schema.tables.records.AttestationRunRecord; import org.finos.waltz.data.InlineSelectFieldFactory; import org.finos.waltz.model.EntityKind; @@ -32,9 +33,12 @@ import java.math.BigDecimal; import java.util.List; +import java.util.Map; import java.util.Optional; import java.util.Set; +import static java.util.Collections.emptyList; +import static org.finos.waltz.schema.Tables.SURVEY_RUN; import static org.finos.waltz.schema.tables.AttestationInstance.ATTESTATION_INSTANCE; import static org.finos.waltz.schema.tables.AttestationInstanceRecipient.ATTESTATION_INSTANCE_RECIPIENT; import static org.finos.waltz.schema.tables.AttestationRun.ATTESTATION_RUN; @@ -42,7 +46,6 @@ import static org.finos.waltz.common.DateTimeUtilities.*; import static org.finos.waltz.common.ListUtilities.newArrayList; import static org.finos.waltz.common.StringUtilities.join; -import static org.finos.waltz.common.StringUtilities.splitThenMap; @Repository public class AttestationRunDao { @@ -69,18 +72,22 @@ public class AttestationRunDao { private static final String ID_SEPARATOR = ";"; - private static final RecordMapper TO_DOMAIN_MAPPER = r -> { + private static AttestationRun mkAttestationRun(Record r, Map> attestationInvolvementGroupKindIds) { + AttestationRunRecord record = r.into(ATTESTATION_RUN); + Long recipientInvolvementGroupId = record.getRecipientInvolvementGroupId(); + List recipients = attestationInvolvementGroupKindIds.getOrDefault(recipientInvolvementGroupId, emptyList()); + + Optional attestedEntityRef = Optional.empty(); - if(record.getAttestedEntityKind() != null && record.getAttestedEntityId() != null) { + if (record.getAttestedEntityKind() != null && record.getAttestedEntityId() != null) { attestedEntityRef = Optional.of(EntityReference.mkRef( EntityKind.valueOf(record.getAttestedEntityKind()), record.getAttestedEntityId(), r.getValue(ATTESTED_ENTITY_NAME_FIELD))); } - return ImmutableAttestationRun.builder() .id(record.getId()) .targetEntityKind(EntityKind.valueOf(record.getTargetEntityKind())) @@ -92,10 +99,7 @@ public class AttestationRunDao { record.getSelectorEntityId(), r.getValue(ENTITY_NAME_FIELD)), HierarchyQueryScope.valueOf(record.getSelectorHierarchyScope()))) - .involvementKindIds(splitThenMap( - record.getInvolvementKindIds(), - ID_SEPARATOR, - Long::valueOf)) + .involvementKindIds(recipients) .issuedBy(record.getIssuedBy()) .issuedOn(toLocalDate(record.getIssuedOn())) .dueDate(toLocalDate(record.getDueDate())) @@ -128,48 +132,61 @@ public AttestationRunDao(DSLContext dsl) { public AttestationRun getById(long attestationRunId) { - return dsl.select(ATTESTATION_RUN.fields()) + + Map> involvementsByGroupId = InvolvementGroupDao.findAllInvolvementsByGroupId(dsl); + + return dsl + .select(ATTESTATION_RUN.fields()) .select(ENTITY_NAME_FIELD) .select(ATTESTED_ENTITY_NAME_FIELD) .from(ATTESTATION_RUN) .where(ATTESTATION_RUN.ID.eq(attestationRunId)) - .fetchOne(TO_DOMAIN_MAPPER); + .fetchOne(r -> mkAttestationRun(r, involvementsByGroupId)); } public List findAll() { + + Map> involvementsByGroupId = InvolvementGroupDao.findAllInvolvementsByGroupId(dsl); + return dsl.select(ATTESTATION_RUN.fields()) .select(ENTITY_NAME_FIELD) .select(ATTESTED_ENTITY_NAME_FIELD) .from(ATTESTATION_RUN) - .fetch(TO_DOMAIN_MAPPER); + .fetch(r -> mkAttestationRun(r, involvementsByGroupId)); } public List findByRecipient(String userId) { + + Map> involvementsByGroupId = InvolvementGroupDao.findAllInvolvementsByGroupId(dsl); + return dsl.selectDistinct(ATTESTATION_RUN.fields()) .select(ENTITY_NAME_FIELD) .select(ATTESTED_ENTITY_NAME_FIELD) .from(ATTESTATION_RUN) .innerJoin(ATTESTATION_INSTANCE) - .on(ATTESTATION_INSTANCE.ATTESTATION_RUN_ID.eq(ATTESTATION_RUN.ID)) + .on(ATTESTATION_INSTANCE.ATTESTATION_RUN_ID.eq(ATTESTATION_RUN.ID)) .innerJoin(ATTESTATION_INSTANCE_RECIPIENT) - .on(ATTESTATION_INSTANCE_RECIPIENT.ATTESTATION_INSTANCE_ID.eq(ATTESTATION_INSTANCE.ID)) + .on(ATTESTATION_INSTANCE_RECIPIENT.ATTESTATION_INSTANCE_ID.eq(ATTESTATION_INSTANCE.ID)) .where(ATTESTATION_INSTANCE_RECIPIENT.USER_ID.eq(userId)) - .fetch(TO_DOMAIN_MAPPER); + .fetch(r -> mkAttestationRun(r, involvementsByGroupId)); } public List findByEntityReference(EntityReference ref) { + + Map> involvementsByGroupId = InvolvementGroupDao.findAllInvolvementsByGroupId(dsl); + return dsl.select(ATTESTATION_RUN.fields()) .select(ENTITY_NAME_FIELD) .select(ATTESTED_ENTITY_NAME_FIELD) .from(ATTESTATION_RUN) .innerJoin(ATTESTATION_INSTANCE) - .on(ATTESTATION_INSTANCE.ATTESTATION_RUN_ID.eq(ATTESTATION_RUN.ID)) + .on(ATTESTATION_INSTANCE.ATTESTATION_RUN_ID.eq(ATTESTATION_RUN.ID)) .where(ATTESTATION_INSTANCE.PARENT_ENTITY_KIND.eq(ref.kind().name())) .and(ATTESTATION_INSTANCE.PARENT_ENTITY_ID.eq(ref.id())) - .fetch(TO_DOMAIN_MAPPER); + .fetch(r -> mkAttestationRun(r, involvementsByGroupId)); } @@ -187,6 +204,8 @@ public List findResponseSummaries() { public List findByIdSelector(Select> selector) { + Map> involvementsByGroupId = InvolvementGroupDao.findAllInvolvementsByGroupId(dsl); + return dsl.select(ATTESTATION_RUN.fields()) .select(ENTITY_NAME_FIELD) .select(ATTESTED_ENTITY_NAME_FIELD) @@ -194,7 +213,7 @@ public List findByIdSelector(Select> selector) { .innerJoin(ATTESTATION_INSTANCE) .on(ATTESTATION_INSTANCE.ATTESTATION_RUN_ID.eq(ATTESTATION_RUN.ID)) .where(ATTESTATION_INSTANCE.ID.in(selector)) - .fetch(TO_DOMAIN_MAPPER); + .fetch(r -> mkAttestationRun(r, involvementsByGroupId)); } public Long create(String userId, AttestationRunCreateCommand command) { @@ -207,7 +226,6 @@ public Long create(String userId, AttestationRunCreateCommand command) { record.setSelectorEntityKind(command.selectionOptions().entityReference().kind().name()); record.setSelectorEntityId(command.selectionOptions().entityReference().id()); record.setSelectorHierarchyScope(command.selectionOptions().scope().name()); - record.setInvolvementKindIds(join(command.involvementKindIds(), ID_SEPARATOR)); record.setIssuedBy(userId); record.setIssuedOn(toSqlDate(command.issuedOn())); record.setDueDate(toSqlDate(command.dueDate())); @@ -229,13 +247,16 @@ public int getEntityCount(Select> idSelector) { public Set findPendingRuns() { + + Map> involvementsByGroupId = InvolvementGroupDao.findAllInvolvementsByGroupId(dsl); + return dsl .select(ATTESTATION_RUN.fields()) .select(ENTITY_NAME_FIELD) .select(ATTESTED_ENTITY_NAME_FIELD) .from(ATTESTATION_RUN) .where(ATTESTATION_RUN.STATUS.eq(AttestationStatus.PENDING.name())) - .fetchSet(TO_DOMAIN_MAPPER); + .fetchSet(r -> mkAttestationRun(r, involvementsByGroupId)); } @@ -256,6 +277,21 @@ public int updateStatusForRunIds(Set runIds, AttestationStatus newStatus) .where(ATTESTATION_RUN.ID.in(runIds)) .execute(); } + } + public Long getRecipientInvolvementGroupId(long attestationRunId) { + return dsl + .select(ATTESTATION_RUN.RECIPIENT_INVOLVEMENT_GROUP_ID) + .from(ATTESTATION_RUN) + .where(ATTESTATION_RUN.ID.eq(attestationRunId)) + .fetchOne(ATTESTATION_RUN.RECIPIENT_INVOLVEMENT_GROUP_ID); + } + + public int updateRecipientInvolvementGroupId(long attestationRunId, Long recipientInvGroupId) { + return dsl + .update(ATTESTATION_RUN) + .set(ATTESTATION_RUN.RECIPIENT_INVOLVEMENT_GROUP_ID, recipientInvGroupId) + .where(ATTESTATION_RUN.ID.eq(attestationRunId)) + .execute(); } } diff --git a/waltz-data/src/main/java/org/finos/waltz/data/involvement_group/InvolvementGroupDao.java b/waltz-data/src/main/java/org/finos/waltz/data/involvement_group/InvolvementGroupDao.java index e55f65281f..63461258fc 100644 --- a/waltz-data/src/main/java/org/finos/waltz/data/involvement_group/InvolvementGroupDao.java +++ b/waltz-data/src/main/java/org/finos/waltz/data/involvement_group/InvolvementGroupDao.java @@ -10,6 +10,8 @@ import org.jooq.RecordMapper; import org.springframework.stereotype.Repository; +import java.util.List; +import java.util.Map; import java.util.Set; import java.util.function.Function; import java.util.stream.Collectors; @@ -78,6 +80,17 @@ public Long createInvolvementGroup(InvolvementGroupCreateCommand cmd) { return invGroupId; } + + public static Map> findAllInvolvementsByGroupId(DSLContext dsl) { + return dsl + .select(INVOLVEMENT_GROUP_ENTRY.INVOLVEMENT_GROUP_ID, INVOLVEMENT_GROUP_ENTRY.INVOLVEMENT_KIND_ID) + .from(INVOLVEMENT_GROUP_ENTRY) + .fetchGroups( + r -> r.get(INVOLVEMENT_GROUP_ENTRY.INVOLVEMENT_GROUP_ID), + r -> r.get(INVOLVEMENT_GROUP_ENTRY.INVOLVEMENT_KIND_ID)); + } + + public void updateInvolvements(Long groupId, Set involvementKindIds) { dsl.transaction(ctx -> { diff --git a/waltz-data/src/main/java/org/finos/waltz/data/survey/SurveyRunDao.java b/waltz-data/src/main/java/org/finos/waltz/data/survey/SurveyRunDao.java index a7ec27844c..15d69282f8 100644 --- a/waltz-data/src/main/java/org/finos/waltz/data/survey/SurveyRunDao.java +++ b/waltz-data/src/main/java/org/finos/waltz/data/survey/SurveyRunDao.java @@ -19,6 +19,7 @@ package org.finos.waltz.data.survey; import org.finos.waltz.common.DateTimeUtilities; +import org.finos.waltz.data.involvement_group.InvolvementGroupDao; import org.finos.waltz.model.EntityKind; import org.finos.waltz.model.EntityReference; import org.finos.waltz.model.HierarchyQueryScope; @@ -94,7 +95,7 @@ public SurveyRunDao(DSLContext dsl) { public SurveyRun getById(long id) { - Map> surveyInvolvementGroupKindIds = findSurveyInvolvementGroupKindIds(); + Map> surveyInvolvementGroupKindIds = InvolvementGroupDao.findAllInvolvementsByGroupId(dsl); return dsl .select(SURVEY_RUN.fields()) @@ -106,7 +107,7 @@ public SurveyRun getById(long id) { public List findForRecipient(long personId) { - Map> surveyInvolvementGroupKindIds = findSurveyInvolvementGroupKindIds(); + Map> surveyInvolvementGroupKindIds = InvolvementGroupDao.findAllInvolvementsByGroupId(dsl); return dsl .select(SURVEY_RUN.fields()) @@ -218,7 +219,7 @@ public int issue(long surveyRunId) { public List findBySurveyInstanceIdSelector(Select> idSelector) { - Map> surveyInvolvementGroupKindIds = findSurveyInvolvementGroupKindIds(); + Map> surveyInvolvementGroupKindIds = InvolvementGroupDao.findAllInvolvementsByGroupId(dsl); return dsl .selectDistinct(SURVEY_RUN.fields()) @@ -231,7 +232,7 @@ public List findBySurveyInstanceIdSelector(Select> idSe public List findByTemplateId(long templateId) { - Map> surveyInvolvementGroupKindIds = findSurveyInvolvementGroupKindIds(); + Map> surveyInvolvementGroupKindIds = InvolvementGroupDao.findAllInvolvementsByGroupId(dsl); return dsl .select(SURVEY_RUN.fields()) @@ -273,11 +274,4 @@ public int updateRecipientInvolvementGroupId(long surveyRunId, Long recipientInv .execute(); } - private Map> findSurveyInvolvementGroupKindIds() { - return dsl - .select(ige.INVOLVEMENT_GROUP_ID, ige.INVOLVEMENT_KIND_ID) - .from(ige) - .fetchGroups(r -> r.get(ige.INVOLVEMENT_GROUP_ID), r -> r.get(ige.INVOLVEMENT_KIND_ID)); - } - } diff --git a/waltz-schema/src/main/resources/liquibase/db.changelog-1.51.xml b/waltz-schema/src/main/resources/liquibase/db.changelog-1.51.xml index ed8b6c0320..c6a312a186 100644 --- a/waltz-schema/src/main/resources/liquibase/db.changelog-1.51.xml +++ b/waltz-schema/src/main/resources/liquibase/db.changelog-1.51.xml @@ -136,4 +136,63 @@ columnName="owner_inv_kind_ids"/> + + + + + + + + + + + + + + insert into involvement_group (name, external_id, provenance) + select concat('Recipients for attestation run: ', name), concat('RECIPIENTS_ATTESTATION_RUN_', id), 'waltz' + from attestation_run + where involvement_kind_ids is not null + and involvement_kind_ids != ''; + + + + + + update attestation_run + set recipient_involvement_group_id = (select id + from involvement_group ig + where ig.external_id = + concat('RECIPIENTS_ATTESTATION_RUN_', attestation_run.id)) + where involvement_kind_ids is not null + and involvement_kind_ids != ''; + + + + + + + insert into involvement_group_entry (involvement_group_id, involvement_kind_id) + select ar.recipient_involvement_group_id, ik.id + from attestation_run ar + inner join involvement_kind ik + on concat(ar.involvement_kind_ids, ';') like concat('%', ik.id, ';%') + where involvement_kind_ids is not null + and involvement_kind_ids != ''; + + + + + + 6637: migrate attestation_run recipients to involvement group, drop column + + + diff --git a/waltz-service/src/main/java/org/finos/waltz/service/attestation/AttestationRunService.java b/waltz-service/src/main/java/org/finos/waltz/service/attestation/AttestationRunService.java index af898942d0..3b0aaefeeb 100644 --- a/waltz-service/src/main/java/org/finos/waltz/service/attestation/AttestationRunService.java +++ b/waltz-service/src/main/java/org/finos/waltz/service/attestation/AttestationRunService.java @@ -19,6 +19,10 @@ package org.finos.waltz.service.attestation; +import org.finos.waltz.model.involvement_group.ImmutableInvolvementGroup; +import org.finos.waltz.model.involvement_group.ImmutableInvolvementGroupCreateCommand; +import org.finos.waltz.model.involvement_group.InvolvementGroup; +import org.finos.waltz.model.involvement_group.InvolvementGroupCreateCommand; import org.finos.waltz.service.email.EmailService; import org.finos.waltz.data.GenericSelector; import org.finos.waltz.data.GenericSelectorFactory; @@ -29,6 +33,7 @@ import org.finos.waltz.model.*; import org.finos.waltz.model.attestation.*; import org.finos.waltz.model.person.Person; +import org.finos.waltz.service.involvement_group.InvolvementGroupService; import org.jooq.Record1; import org.jooq.Select; import org.springframework.beans.factory.annotation.Autowired; @@ -37,6 +42,7 @@ import java.time.LocalDate; import java.util.*; +import static java.lang.String.format; import static java.util.stream.Collectors.groupingBy; import static java.util.stream.Collectors.toList; import static org.finos.waltz.common.Checks.checkNotNull; @@ -58,24 +64,27 @@ public class AttestationRunService { private final EmailService emailService; private final GenericSelectorFactory genericSelectorFactory = new GenericSelectorFactory(); private final InvolvementDao involvementDao; + private final InvolvementGroupService involvementGroupService; @Autowired public AttestationRunService(AttestationInstanceDao attestationInstanceDao, AttestationInstanceRecipientDao attestationInstanceRecipientDao, AttestationRunDao attestationRunDao, EmailService emailService, - InvolvementDao involvementDao) { + InvolvementDao involvementDao, InvolvementGroupService involvementGroupService) { checkNotNull(attestationInstanceRecipientDao, "attestationInstanceRecipientDao cannot be null"); checkNotNull(attestationInstanceDao, "attestationInstanceDao cannot be null"); checkNotNull(attestationRunDao, "attestationRunDao cannot be null"); checkNotNull(emailService, "emailService cannot be null"); checkNotNull(involvementDao, "involvementDao cannot be null"); + checkNotNull(involvementGroupService, "involvementGroupService cannot be null"); this.attestationInstanceDao = attestationInstanceDao; this.attestationInstanceRecipientDao = attestationInstanceRecipientDao; this.attestationRunDao = attestationRunDao; this.emailService = emailService; this.involvementDao = involvementDao; + this.involvementGroupService = involvementGroupService; } @@ -141,6 +150,7 @@ public AttestationCreateSummary getCreateSummary(AttestationRunCreateCommand com public IdCommandResponse create(String userId, AttestationRunCreateCommand command) { // create run Long runId = attestationRunDao.create(userId, command); + createRecipientsGroup(runId, command.name(), command.involvementKindIds(), userId); // generate instances and recipients List instanceRecipients = generateAttestationInstanceRecipients( @@ -290,10 +300,28 @@ public int issueInstancesForPendingRuns() { Set runsBeingIssued = toIds(pendingRuns); attestationRunDao.updateStatusForRunIds(runsBeingIssued, ISSUING); - if(!isEmpty(instanceRecipients)){ + if (!isEmpty(instanceRecipients)) { createAttestationInstancesAndRecipients(instanceRecipients); } return attestationRunDao.updateStatusForRunIds(runsBeingIssued, ISSUED); } + + + public void createRecipientsGroup(long runId, String runName, Set involvementKindIds, String userName) { + + InvolvementGroup group = ImmutableInvolvementGroup.builder() + .name(format("Recipients for attestation run: %s", runName)) + .externalId(format("RECIPIENTS_ATTESTATION_RUN_%d", runId)) + .build(); + + InvolvementGroupCreateCommand recipientsCmd = ImmutableInvolvementGroupCreateCommand + .builder() + .involvementGroup(group) + .involvementKindIds(involvementKindIds) + .build(); + + long recipientInvGroupId = involvementGroupService.createGroup(recipientsCmd, userName); + attestationRunDao.updateRecipientInvolvementGroupId(runId, recipientInvGroupId); + } }