This is an automated email from the ASF dual-hosted git repository.
adamsaghy pushed a commit to branch develop
in repository https://gitbox.apache.org/repos/asf/fineract.git
The following commit(s) were added to refs/heads/develop by this push:
new bcf04b7e6 FINERACT-1971: Enhancing re-Amortization validation
bcf04b7e6 is described below
commit bcf04b7e6f9e5030f830daed57c2aa4c7c188160
Author: Ruchi Dhamankar <[email protected]>
AuthorDate: Fri May 10 19:48:01 2024 +0530
FINERACT-1971: Enhancing re-Amortization validation
---
.../LoanReAmortizationValidator.java | 4 +-
.../integrationtests/BaseLoanIntegrationTest.java | 4 +
.../LoanReAmortizationIntegrationTest.java | 99 ++++++++++++++++++++++
3 files changed, 105 insertions(+), 2 deletions(-)
diff --git
a/fineract-provider/src/main/java/org/apache/fineract/portfolio/loanaccount/service/reamortization/LoanReAmortizationValidator.java
b/fineract-provider/src/main/java/org/apache/fineract/portfolio/loanaccount/service/reamortization/LoanReAmortizationValidator.java
index b530714c1..28087f74a 100644
---
a/fineract-provider/src/main/java/org/apache/fineract/portfolio/loanaccount/service/reamortization/LoanReAmortizationValidator.java
+++
b/fineract-provider/src/main/java/org/apache/fineract/portfolio/loanaccount/service/reamortization/LoanReAmortizationValidator.java
@@ -114,8 +114,8 @@ public class LoanReAmortizationValidator {
}
// validate if there's no payment between the reamortization and today
- boolean repaymentExistsAfterReAmortization =
loan.getLoanTransactions().stream()
- .anyMatch(tx -> tx.getTypeOf().isRepaymentType() &&
transactionHappenedAfterOther(tx, optionalReAmortizationTx.get()));
+ boolean repaymentExistsAfterReAmortization =
loan.getLoanTransactions().stream().anyMatch(tx ->
tx.getTypeOf().isRepaymentType()
+ && !tx.isReversed() && transactionHappenedAfterOther(tx,
optionalReAmortizationTx.get()));
if (repaymentExistsAfterReAmortization) {
throw new
GeneralPlatformDomainRuleException("error.msg.loan.reamortize.repayment.exists.after.reamortization",
"Undoing a reamortization can only be done if there hasn't
been any repayment afterwards", loan.getId());
diff --git
a/integration-tests/src/test/java/org/apache/fineract/integrationtests/BaseLoanIntegrationTest.java
b/integration-tests/src/test/java/org/apache/fineract/integrationtests/BaseLoanIntegrationTest.java
index 6b56a36b6..800474ada 100644
---
a/integration-tests/src/test/java/org/apache/fineract/integrationtests/BaseLoanIntegrationTest.java
+++
b/integration-tests/src/test/java/org/apache/fineract/integrationtests/BaseLoanIntegrationTest.java
@@ -481,6 +481,10 @@ public abstract class BaseLoanIntegrationTest {
loanTransactionHelper.undoDisbursal(loanId);
}
+ protected void undoLastDisbursement(Long loanId) {
+ loanTransactionHelper.undoLastDisbursalLoan(loanId, new
PostLoansLoanIdRequest());
+ }
+
protected void verifyJournalEntries(Long loanId, Journal... entries) {
GetJournalEntriesTransactionIdResponse journalEntriesForLoan =
journalEntryHelper.getJournalEntriesForLoan(loanId);
Assertions.assertEquals(entries.length,
journalEntriesForLoan.getPageItems().size());
diff --git
a/integration-tests/src/test/java/org/apache/fineract/integrationtests/loan/reamortization/LoanReAmortizationIntegrationTest.java
b/integration-tests/src/test/java/org/apache/fineract/integrationtests/loan/reamortization/LoanReAmortizationIntegrationTest.java
index fb555ad4a..c1f81ab17 100644
---
a/integration-tests/src/test/java/org/apache/fineract/integrationtests/loan/reamortization/LoanReAmortizationIntegrationTest.java
+++
b/integration-tests/src/test/java/org/apache/fineract/integrationtests/loan/reamortization/LoanReAmortizationIntegrationTest.java
@@ -797,6 +797,105 @@ public class LoanReAmortizationIntegrationTest extends
BaseLoanIntegrationTest {
});
}
+ @Test
+ public void
undoReAmortizationAfterSecondDownPaymentWhenDisbursementIsReversedTest() {
+
+ runAt("01 January 2023", () -> {
+ Long clientId =
clientHelper.createClient(ClientHelper.defaultClientCreationRequest()).getClientId();
+ Long loanProductId =
createLoanProductWithMultiDisbursalAndRepaymentsWithEnableDownPayment(3, 15);
+
+ loanId.set(applyAndApproveLoan(clientId, loanProductId, "01
January 2023", 1000.0, 3, req -> {
+ req.setRepaymentEvery(15);
+ req.setLoanTermFrequency(45);
+
req.setTransactionProcessingStrategyCode("advanced-payment-allocation-strategy");
+
req.setLoanScheduleProcessingType(LoanScheduleType.PROGRESSIVE.toString());
+
req.setLoanScheduleProcessingType(LoanScheduleProcessingType.HORIZONTAL.toString());
+ }));
+
+ disburseLoan(loanId.get(), BigDecimal.valueOf(500.00), "01 January
2023");
+
+ verifyRepaymentSchedule(loanId.get(), //
+ installment(500, null, "01 January 2023"), //
+ installment(125.0, true, "01 January 2023"), //
+ installment(125.0, false, "16 January 2023"), //
+ installment(125.0, false, "31 January 2023"), //
+ installment(125.0, false, "15 February 2023") //
+ );
+ });
+ runAt("25 January 2023", () -> {
+
+ reAmortizeLoan(loanId.get());
+
+ verifyRepaymentSchedule(loanId.get(), //
+ installment(500, null, "01 January 2023"), //
+ installment(125.0, true, "01 January 2023"), //
+ installment(0.0, true, "16 January 2023"), //
+ installment(187.5, false, "31 January 2023"), //
+ installment(187.5, false, "15 February 2023") //
+ );
+
+ // verify transactions
+ verifyTransactions(loanId.get(), //
+ transaction(500.0, "Disbursement", "01 January 2023"), //
+ transaction(125.0, "Down Payment", "01 January 2023"), //
+ transaction(125.0, "Re-amortize", "25 January 2023") //
+ );
+ });
+ runAt("26 January 2023", () -> {
+ disburseLoan(loanId.get(), BigDecimal.valueOf(500.00), "26 January
2023");
+
+ verifyRepaymentSchedule(loanId.get(), //
+ installment(500, null, "01 January 2023"), //
+ installment(125.0, true, "01 January 2023"), //
+ installment(0.0, true, "16 January 2023"), //
+ installment(500.0, null, "26 January 2023"), //
+ installment(125.0, true, "26 January 2023"), //
+ installment(375.0, false, "31 January 2023"), //
+ installment(375.0, false, "15 February 2023") //
+ );
+
+ // verify transactions
+ verifyTransactions(loanId.get(), //
+ transaction(500.0, "Disbursement", "01 January 2023"), //
+ transaction(125.0, "Down Payment", "01 January 2023"), //
+ transaction(125.0, "Re-amortize", "25 January 2023"), //
+ transaction(500.0, "Disbursement", "26 January 2023"), //
+ transaction(125.0, "Down Payment", "26 January 2023") //
+ );
+
+ // undo second disbursal
+ undoLastDisbursement(loanId.get());
+
+ verifyRepaymentSchedule(loanId.get(), //
+ installment(500, null, "01 January 2023"), //
+ installment(125.0, true, "01 January 2023"), //
+ installment(0.0, true, "16 January 2023"), //
+ installment(187.5, false, "31 January 2023"), //
+ installment(187.5, false, "15 February 2023") //
+ );
+
+ // verify transactions
+ verifyTransactions(loanId.get(), //
+ transaction(500.0, "Disbursement", "01 January 2023"), //
+ transaction(125.0, "Down Payment", "01 January 2023"), //
+ transaction(125.0, "Re-amortize", "25 January 2023") //
+ );
+
+ // undo re-Amortization
+ undoReAmortizeLoan(loanId.get());
+
+ verifyRepaymentSchedule(loanId.get(), //
+ installment(500, null, "01 January 2023"), //
+ installment(125.0, true, "01 January 2023"), //
+ installment(125.0, false, "16 January 2023"), //
+ installment(125.0, false, "31 January 2023"), //
+ installment(125.0, false, "15 February 2023") //
+ );
+
+ });
+
+ }
+
private Long
createLoanProductWithMultiDisbursalAndRepaymentsWithEnableDownPayment(int
numberOfInstallments, int repaymentEvery) {
return
createLoanProductWithMultiDisbursalAndRepaymentsWithEnableDownPayment(numberOfInstallments,
repaymentEvery,
DOWN_PAYMENT_PERCENTAGE);