This is an automated email from the ASF dual-hosted git repository. avikg 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 9752366 FINERACT-1108-Custom-installment-in-reshedule new bd9119e Merge pull request #1211 from fynmanoj/AL-9 9752366 is described below commit 9752366c70c667ed43fe0687f5d9454bfdda7284 Author: Manoj <ma...@fynarfin.io> AuthorDate: Fri Aug 14 21:44:50 2020 +0530 FINERACT-1108-Custom-installment-in-reshedule --- .../LoanRescheduleRequestTest.java | 21 +++++++++++++++++ .../loans/LoanRescheduleRequestTestBuilder.java | 20 +++++++++++++++++ .../RescheduleLoansApiConstants.java | 3 +++ .../data/LoanRescheduleRequestDataValidator.java | 26 ++++++++++++++++++++-- ...nRescheduleRequestWritePlatformServiceImpl.java | 25 +++++++++++++++++++-- 5 files changed, 91 insertions(+), 4 deletions(-) diff --git a/fineract-provider/src/integrationTest/java/org/apache/fineract/integrationtests/LoanRescheduleRequestTest.java b/fineract-provider/src/integrationTest/java/org/apache/fineract/integrationtests/LoanRescheduleRequestTest.java index d3d30e5..de62d0d 100644 --- a/fineract-provider/src/integrationTest/java/org/apache/fineract/integrationtests/LoanRescheduleRequestTest.java +++ b/fineract-provider/src/integrationTest/java/org/apache/fineract/integrationtests/LoanRescheduleRequestTest.java @@ -206,4 +206,25 @@ public class LoanRescheduleRequestTest { LOG.info("Successfully approved loan reschedule request (ID: {})", this.loanRescheduleRequestId); } + + /** + * create new loan reschedule request + **/ + private void createLoanRescheduleChangeEMIRequest() { + LOG.info("---------------------------------CREATING LOAN RESCHEDULE REQUEST CHANGE EMI------------------------------------------"); + + final String requestJSON = new LoanRescheduleRequestTestBuilder().updateGraceOnPrincipal(null).updateGraceOnInterest(null) + .updateExtraTerms(null).updateEMI("5000").updateEmiChangeEndDate("4 February 2015") + .updateRescheduleFromDate("04 January 2015").updateRecalculateInterest(true).build(this.loanId.toString()); + + this.loanRescheduleRequestId = this.loanRescheduleRequestHelper.createLoanRescheduleRequest(requestJSON); + this.loanRescheduleRequestHelper.verifyCreationOfLoanRescheduleRequest(this.loanRescheduleRequestId); + + LOG.info("Successfully created loan reschedule request (ID: {} )", this.loanRescheduleRequestId); + } + + @Test + public void testCreateLoanRescheduleChangeEMIRequest() { + this.createLoanRescheduleChangeEMIRequest(); + } } diff --git a/fineract-provider/src/integrationTest/java/org/apache/fineract/integrationtests/common/loans/LoanRescheduleRequestTestBuilder.java b/fineract-provider/src/integrationTest/java/org/apache/fineract/integrationtests/common/loans/LoanRescheduleRequestTestBuilder.java index a445416..f1dfb1f 100644 --- a/fineract-provider/src/integrationTest/java/org/apache/fineract/integrationtests/common/loans/LoanRescheduleRequestTestBuilder.java +++ b/fineract-provider/src/integrationTest/java/org/apache/fineract/integrationtests/common/loans/LoanRescheduleRequestTestBuilder.java @@ -33,6 +33,8 @@ public class LoanRescheduleRequestTestBuilder { private String rescheduleReasonId = "1"; private String rescheduleReasonComment = null; private String submittedOnDate = "04 September 2014"; + private String emi = null; + private String emiEndDate = null; public String build(final String loanId) { final HashMap<String, Object> map = new HashMap<>(); @@ -71,6 +73,14 @@ public class LoanRescheduleRequestTestBuilder { map.put("rescheduleReasonComment", rescheduleReasonComment); } + if (emi != null) { + map.put("emi", emi); + } + + if (emiEndDate != null) { + map.put("endDate", emiEndDate); + } + return new Gson().toJson(map); } @@ -136,6 +146,16 @@ public class LoanRescheduleRequestTestBuilder { return this; } + public LoanRescheduleRequestTestBuilder updateEmiChangeEndDate(final String emiChangeEndDate) { + this.emiEndDate = emiChangeEndDate; + return this; + } + + public LoanRescheduleRequestTestBuilder updateEMI(final String emi) { + this.emi = emi; + return this; + } + public String getRejectLoanRescheduleRequestJSON() { final HashMap<String, String> map = new HashMap<>(); map.put("locale", "en"); diff --git a/fineract-provider/src/main/java/org/apache/fineract/portfolio/loanaccount/rescheduleloan/RescheduleLoansApiConstants.java b/fineract-provider/src/main/java/org/apache/fineract/portfolio/loanaccount/rescheduleloan/RescheduleLoansApiConstants.java index 3904fa8..7cbdc37 100644 --- a/fineract-provider/src/main/java/org/apache/fineract/portfolio/loanaccount/rescheduleloan/RescheduleLoansApiConstants.java +++ b/fineract-provider/src/main/java/org/apache/fineract/portfolio/loanaccount/rescheduleloan/RescheduleLoansApiConstants.java @@ -53,6 +53,9 @@ public class RescheduleLoansApiConstants { public static final String pendingCommandParamName = "pending"; public static final String rejectCommandParamName = "reject"; + public static final String endDateParamName = "endDate"; + public static final String emiParamName = "emi"; + // reject action request parameters public static final String rejectedOnDateParam = "rejectedOnDate"; diff --git a/fineract-provider/src/main/java/org/apache/fineract/portfolio/loanaccount/rescheduleloan/data/LoanRescheduleRequestDataValidator.java b/fineract-provider/src/main/java/org/apache/fineract/portfolio/loanaccount/rescheduleloan/data/LoanRescheduleRequestDataValidator.java index 0e4f05b..ee35f99 100644 --- a/fineract-provider/src/main/java/org/apache/fineract/portfolio/loanaccount/rescheduleloan/data/LoanRescheduleRequestDataValidator.java +++ b/fineract-provider/src/main/java/org/apache/fineract/portfolio/loanaccount/rescheduleloan/data/LoanRescheduleRequestDataValidator.java @@ -21,6 +21,7 @@ package org.apache.fineract.portfolio.loanaccount.rescheduleloan.data; import com.google.gson.JsonElement; import com.google.gson.reflect.TypeToken; import java.lang.reflect.Type; +import java.math.BigDecimal; import java.util.ArrayList; import java.util.Arrays; import java.util.Collection; @@ -56,7 +57,8 @@ public class LoanRescheduleRequestDataValidator { RescheduleLoansApiConstants.rescheduleFromDateParamName, RescheduleLoansApiConstants.newInterestRateParamName, RescheduleLoansApiConstants.rescheduleReasonIdParamName, RescheduleLoansApiConstants.rescheduleReasonCommentParamName, RescheduleLoansApiConstants.submittedOnDateParamName, RescheduleLoansApiConstants.loanIdParamName, - RescheduleLoansApiConstants.adjustedDueDateParamName, RescheduleLoansApiConstants.recalculateInterestParamName)); + RescheduleLoansApiConstants.adjustedDueDateParamName, RescheduleLoansApiConstants.recalculateInterestParamName, + RescheduleLoansApiConstants.endDateParamName, RescheduleLoansApiConstants.emiParamName)); private static final Set<String> REJECT_REQUEST_DATA_PARAMETERS = new HashSet<>( Arrays.asList(RescheduleLoansApiConstants.localeParamName, RescheduleLoansApiConstants.dateFormatParamName, @@ -141,6 +143,25 @@ public class LoanRescheduleRequestDataValidator { dataValidatorBuilder.reset().parameter(RescheduleLoansApiConstants.rescheduleReasonCommentParamName).value(rescheduleReasonComment) .ignoreIfNull().notExceedingLengthOf(500); + if (this.fromJsonHelper.parameterExists(RescheduleLoansApiConstants.emiParamName, jsonElement) + || this.fromJsonHelper.parameterExists(RescheduleLoansApiConstants.endDateParamName, jsonElement)) { + final LocalDate endDate = jsonCommand.localDateValueOfParameterNamed(RescheduleLoansApiConstants.endDateParamName); + final BigDecimal emi = jsonCommand.bigDecimalValueOfParameterNamed(RescheduleLoansApiConstants.emiParamName); + + dataValidatorBuilder.reset().parameter(RescheduleLoansApiConstants.endDateParamName).value(endDate).notNull(); + dataValidatorBuilder.reset().parameter(RescheduleLoansApiConstants.emiParamName).value(emi).notNull().positiveAmount(); + + if (endDate != null) { + LoanRepaymentScheduleInstallment endInstallment = loan.getRepaymentScheduleInstallment(endDate); + + if (endInstallment == null) { + dataValidatorBuilder.reset().parameter(RescheduleLoansApiConstants.endDateParamName) + .failWithCode("repayment.schedule.installment.does.not.exist", "Repayment schedule installment does not exist"); + } + } + + } + final LocalDate adjustedDueDate = this.fromJsonHelper.extractLocalDateNamed(RescheduleLoansApiConstants.adjustedDueDateParamName, jsonElement); @@ -155,7 +176,8 @@ public class LoanRescheduleRequestDataValidator { && !this.fromJsonHelper.parameterExists(RescheduleLoansApiConstants.graceOnInterestParamName, jsonElement) && !this.fromJsonHelper.parameterExists(RescheduleLoansApiConstants.extraTermsParamName, jsonElement) && !this.fromJsonHelper.parameterExists(RescheduleLoansApiConstants.newInterestRateParamName, jsonElement) - && !this.fromJsonHelper.parameterExists(RescheduleLoansApiConstants.adjustedDueDateParamName, jsonElement)) { + && !this.fromJsonHelper.parameterExists(RescheduleLoansApiConstants.adjustedDueDateParamName, jsonElement) + && !this.fromJsonHelper.parameterExists(RescheduleLoansApiConstants.emiParamName, jsonElement)) { dataValidatorBuilder.reset().parameter(RescheduleLoansApiConstants.graceOnPrincipalParamName).notNull(); } LoanRepaymentScheduleInstallment installment = null; diff --git a/fineract-provider/src/main/java/org/apache/fineract/portfolio/loanaccount/rescheduleloan/service/LoanRescheduleRequestWritePlatformServiceImpl.java b/fineract-provider/src/main/java/org/apache/fineract/portfolio/loanaccount/rescheduleloan/service/LoanRescheduleRequestWritePlatformServiceImpl.java index c7aa49f..6399310 100644 --- a/fineract-provider/src/main/java/org/apache/fineract/portfolio/loanaccount/rescheduleloan/service/LoanRescheduleRequestWritePlatformServiceImpl.java +++ b/fineract-provider/src/main/java/org/apache/fineract/portfolio/loanaccount/rescheduleloan/service/LoanRescheduleRequestWritePlatformServiceImpl.java @@ -212,6 +212,9 @@ public class LoanRescheduleRequestWritePlatformServiceImpl implements LoanResche final Boolean recalculateInterest = jsonCommand .booleanObjectValueOfParameterNamed(RescheduleLoansApiConstants.recalculateInterestParamName); + final Date endDate = jsonCommand.dateValueOfParameterNamed(RescheduleLoansApiConstants.endDateParamName); + final BigDecimal emi = jsonCommand.bigDecimalValueOfParameterNamed(RescheduleLoansApiConstants.emiParamName); + // initialize set the value to null Date submittedOnDate = null; @@ -277,7 +280,7 @@ public class LoanRescheduleRequestWritePlatformServiceImpl implements LoanResche // create term variations for flat and declining balance loans createLoanTermVariationsForRegularLoans(loan, graceOnPrincipal, graceOnInterest, extraTerms, interestRate, rescheduleFromDate, adjustedDueDate, loanRescheduleRequest, loanRescheduleRequestToTermVariationMappings, isActive, isSpecificToInstallment, - decimalValue, dueDate); + decimalValue, dueDate, endDate, emi); // create a new entry in the m_loan_reschedule_request table this.loanRescheduleRequestRepository.save(loanRescheduleRequest); @@ -301,7 +304,25 @@ public class LoanRescheduleRequestWritePlatformServiceImpl implements LoanResche final Integer extraTerms, final BigDecimal interestRate, Date rescheduleFromDate, Date adjustedDueDate, final LoanRescheduleRequest loanRescheduleRequest, List<LoanRescheduleRequestToTermVariationMapping> loanRescheduleRequestToTermVariationMappings, final Boolean isActive, - final boolean isSpecificToInstallment, BigDecimal decimalValue, Date dueDate) { + final boolean isSpecificToInstallment, BigDecimal decimalValue, Date dueDate, Date endDate, BigDecimal emi) { + + if (rescheduleFromDate != null && endDate != null && emi != null) { + LoanTermVariations parent = null; + LocalDate rescheduleFromLocDate = new LocalDate(rescheduleFromDate); + LocalDate endDateLocDate = new LocalDate(endDate); + final Integer termType = LoanTermVariationType.EMI_AMOUNT.getValue(); + List<LoanRepaymentScheduleInstallment> installments = loan.getRepaymentScheduleInstallments(); + for (LoanRepaymentScheduleInstallment installment : installments) { + if (installment.getDueDate().isEqual(rescheduleFromLocDate) || installment.getDueDate().isEqual(endDateLocDate) + || (installment.getDueDate().isAfter(rescheduleFromLocDate) && installment.getDueDate().isBefore(endDateLocDate))) { + createLoanTermVariations(termType, loan, installment.getDueDate().toDate(), installment.getDueDate().toDate(), + loanRescheduleRequestToTermVariationMappings, isActive, true, emi, parent); + } + if (installment.getDueDate().isAfter(endDateLocDate)) { + break; + } + } + } if (rescheduleFromDate != null && adjustedDueDate != null) { LoanTermVariations parent = null;