diff --git a/fineract-avro-schemas/src/main/avro/loan/v1/LoanOwnershipTransferDataV1.avsc b/fineract-avro-schemas/src/main/avro/loan/v1/LoanOwnershipTransferDataV1.avsc index e2131228c..985170e4b 100644 --- a/fineract-avro-schemas/src/main/avro/loan/v1/LoanOwnershipTransferDataV1.avsc +++ b/fineract-avro-schemas/src/main/avro/loan/v1/LoanOwnershipTransferDataV1.avsc @@ -161,6 +161,17 @@ "null", "string" ] + }, + { + "default": null, + "name": "customData", + "type": [ + "null", + { + "values": "bytes", + "type": "map" + } + ] } ] } diff --git a/fineract-provider/src/main/java/org/apache/fineract/infrastructure/event/external/service/serialization/serializer/AbstractBusinessEventWithCustomDataSerializer.java b/fineract-core/src/main/java/org/apache/fineract/infrastructure/event/external/service/serialization/serializer/AbstractBusinessEventWithCustomDataSerializer.java similarity index 100% rename from fineract-provider/src/main/java/org/apache/fineract/infrastructure/event/external/service/serialization/serializer/AbstractBusinessEventWithCustomDataSerializer.java rename to fineract-core/src/main/java/org/apache/fineract/infrastructure/event/external/service/serialization/serializer/AbstractBusinessEventWithCustomDataSerializer.java diff --git a/fineract-investor/src/main/java/org/apache/fineract/investor/service/serialization/serializer/investor/InvestorBusinessEventSerializer.java b/fineract-investor/src/main/java/org/apache/fineract/investor/service/serialization/serializer/investor/InvestorBusinessEventSerializer.java index fc6f09013..9d7fc6db9 100644 --- a/fineract-investor/src/main/java/org/apache/fineract/investor/service/serialization/serializer/investor/InvestorBusinessEventSerializer.java +++ b/fineract-investor/src/main/java/org/apache/fineract/investor/service/serialization/serializer/investor/InvestorBusinessEventSerializer.java @@ -39,7 +39,8 @@ import org.apache.fineract.avro.generic.v1.CurrencyDataV1; import org.apache.fineract.avro.loan.v1.LoanOwnershipTransferDataV1; import org.apache.fineract.avro.loan.v1.UnpaidChargeDataV1; import org.apache.fineract.infrastructure.event.business.domain.BusinessEvent; -import org.apache.fineract.infrastructure.event.external.service.serialization.serializer.BusinessEventSerializer; +import org.apache.fineract.infrastructure.event.external.service.serialization.serializer.AbstractBusinessEventWithCustomDataSerializer; +import org.apache.fineract.infrastructure.event.external.service.serialization.serializer.ExternalEventCustomDataSerializer; import org.apache.fineract.investor.data.ExternalTransferData; import org.apache.fineract.investor.data.ExternalTransferStatus; import org.apache.fineract.investor.data.ExternalTransferSubStatus; @@ -52,12 +53,13 @@ import org.springframework.stereotype.Component; @Component @RequiredArgsConstructor -public class InvestorBusinessEventSerializer implements BusinessEventSerializer { +public class InvestorBusinessEventSerializer extends AbstractBusinessEventWithCustomDataSerializer { private static final Set EXECUTED_TRANSFER_STATUSES = Set.of(ACTIVE, ACTIVE_INTERMEDIATE, BUYBACK, BUYBACK_INTERMEDIATE); private final ExternalAssetOwnersReadService externalAssetOwnersReadService; + private final List> externalEventCustomDataSerializers; private static CurrencyDataV1 getCurrencyFromEvent(InvestorBusinessEvent event) { MonetaryCurrency loanCurrency = event.getLoan().getCurrency(); @@ -76,6 +78,11 @@ public class InvestorBusinessEventSerializer implements BusinessEventSerializer return LoanOwnershipTransferDataV1.class; } + @Override + protected List> getExternalEventCustomDataSerializers() { + return externalEventCustomDataSerializers; + } + @Override public ByteBufferSerializable toAvroDTO(BusinessEvent rawEvent) { InvestorBusinessEvent event = (InvestorBusinessEvent) rawEvent; @@ -95,7 +102,7 @@ public class InvestorBusinessEventSerializer implements BusinessEventSerializer .setSettlementDate(transferData.getSettlementDate().format(DEFAULT_DATE_FORMATTER)) .setSubmittedDate(transferData.getSettlementDate().format(DEFAULT_DATE_FORMATTER)).setType(transferType) .setTransferStatus(getStatus(transferData.getStatus())) - .setTransferStatusReason(getTransferStatusReason(transferData.getSubStatus())); + .setTransferStatusReason(getTransferStatusReason(transferData.getSubStatus())).setCustomData(collectCustomData(event)); if (transferData.getDetails() != null) { builder.setTotalOutstandingBalanceAmount(transferData.getDetails().getTotalOutstanding()) diff --git a/fineract-investor/src/test/java/org/apache/fineract/investor/service/serialization/serializer/investor/InvestorBusinessEventSerializerTest.java b/fineract-investor/src/test/java/org/apache/fineract/investor/service/serialization/serializer/investor/InvestorBusinessEventSerializerTest.java index 19e5bdfee..8783e9251 100644 --- a/fineract-investor/src/test/java/org/apache/fineract/investor/service/serialization/serializer/investor/InvestorBusinessEventSerializerTest.java +++ b/fineract-investor/src/test/java/org/apache/fineract/investor/service/serialization/serializer/investor/InvestorBusinessEventSerializerTest.java @@ -18,6 +18,7 @@ */ package org.apache.fineract.investor.service.serialization.serializer.investor; +import static java.nio.charset.StandardCharsets.UTF_8; import static org.apache.fineract.investor.data.ExternalTransferStatus.ACTIVE; import static org.apache.fineract.investor.data.ExternalTransferStatus.ACTIVE_INTERMEDIATE; import static org.apache.fineract.investor.data.ExternalTransferStatus.BUYBACK; @@ -30,12 +31,14 @@ import static org.apache.fineract.investor.data.ExternalTransferSubStatus.BALANC import static org.apache.fineract.investor.data.ExternalTransferSubStatus.BALANCE_ZERO; import static org.apache.fineract.investor.data.ExternalTransferSubStatus.SAMEDAY_TRANSFERS; import static org.junit.jupiter.api.Assertions.assertEquals; +import static org.junit.jupiter.api.Assertions.assertNotNull; import static org.junit.jupiter.api.Assertions.assertTrue; import static org.mockito.ArgumentMatchers.any; import static org.mockito.Mockito.mock; import static org.mockito.Mockito.when; import java.math.BigDecimal; +import java.nio.ByteBuffer; import java.time.LocalDate; import java.util.ArrayList; import java.util.List; @@ -46,6 +49,7 @@ import org.apache.fineract.avro.generator.ByteBufferSerializable; import org.apache.fineract.avro.loan.v1.LoanOwnershipTransferDataV1; import org.apache.fineract.avro.loan.v1.UnpaidChargeDataV1; import org.apache.fineract.infrastructure.core.domain.ExternalId; +import org.apache.fineract.infrastructure.event.external.service.serialization.serializer.ExternalEventCustomDataSerializer; import org.apache.fineract.investor.data.ExternalTransferData; import org.apache.fineract.investor.data.ExternalTransferDataDetails; import org.apache.fineract.investor.data.ExternalTransferLoanData; @@ -53,6 +57,7 @@ import org.apache.fineract.investor.data.ExternalTransferOwnerData; import org.apache.fineract.investor.data.ExternalTransferStatus; import org.apache.fineract.investor.data.ExternalTransferSubStatus; import org.apache.fineract.investor.domain.ExternalAssetOwnerTransfer; +import org.apache.fineract.investor.domain.InvestorBusinessEvent; import org.apache.fineract.investor.domain.LoanOwnershipTransferBusinessEvent; import org.apache.fineract.investor.service.ExternalAssetOwnersReadService; import org.apache.fineract.organisation.monetary.domain.MonetaryCurrency; @@ -69,6 +74,8 @@ public class InvestorBusinessEventSerializerTest { public static final String LOAN_EXTERNAL_ID = "29641fe0-0ac6-409a-bb8b-24fdf08d2891"; public static final ExternalId TRANSFER_EXTERNAL_ID = new ExternalId("ac303982-46a5-4cea-9f71-67b69063a2b7"); + private static final String CUSTOM_DATA_PREFIX = "test_data_invertor_business_event"; + @Test public void testSerializationSellOK() { doTest(ACTIVE, null, null, "SALE", "EXECUTED", null); @@ -134,11 +141,16 @@ public class InvestorBusinessEventSerializerTest { createExternalAssetOwnerTransfer(status, subStatus), loan); // when - InvestorBusinessEventSerializer serializer = new InvestorBusinessEventSerializer(mockReadService); - ByteBufferSerializable byteBufferSerializable = serializer.toAvroDTO(loanOwnershipTransferBusinessEvent); + InvestorBusinessEventSerializer serializer = new InvestorBusinessEventSerializer(mockReadService, createCustomDataForEvents()); + final ByteBufferSerializable byteBufferSerializable = serializer.toAvroDTO(loanOwnershipTransferBusinessEvent); + final LoanOwnershipTransferDataV1 result = (LoanOwnershipTransferDataV1) byteBufferSerializable; // then verifyFields(byteBufferSerializable, expectedType, expectedStatus, expectedReason); + assertNotNull(result.getCustomData()); + final Map customData = result.getCustomData(); + assertEquals(CUSTOM_DATA_PREFIX + "_1", new String(customData.get("test_key_1").array(), UTF_8)); + assertEquals(CUSTOM_DATA_PREFIX + "_2", new String(customData.get("test_key_2").array(), UTF_8)); } private List createMockCharges() { @@ -232,4 +244,41 @@ public class InvestorBusinessEventSerializerTest { return data; } + private List> createCustomDataForEvents() { + return List.of(new ExternalEventCustomDataSerializer<>() { + + @Override + public ByteBuffer serialize(final InvestorBusinessEvent event) { + return ByteBuffer.wrap(CUSTOM_DATA_PREFIX.getBytes(UTF_8)); + } + + @Override + public String key() { + return "test_key_1"; + } + }, new ExternalEventCustomDataSerializer<>() { + + @Override + public ByteBuffer serialize(final InvestorBusinessEvent event) { + return ByteBuffer.wrap((CUSTOM_DATA_PREFIX + "_1").getBytes(UTF_8)); + } + + @Override + public String key() { + return "test_key_1"; + } + }, new ExternalEventCustomDataSerializer<>() { + + @Override + public ByteBuffer serialize(final InvestorBusinessEvent event) { + return ByteBuffer.wrap((CUSTOM_DATA_PREFIX + "_2").getBytes(UTF_8)); + } + + @Override + public String key() { + return "test_key_2"; + } + }); + } + }