-
Notifications
You must be signed in to change notification settings - Fork 2.1k
FINERACT-2354: Re-aging for Interest bearing products- Interest calculation: Default Behavior #5053
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: develop
Are you sure you want to change the base?
Conversation
2ca485f
to
f9b159c
Compare
f9b159c
to
966268f
Compare
913e0a7
to
a68ea39
Compare
e6d847a
to
391fbda
Compare
391fbda
to
c70e3c5
Compare
…t bearing products with interest calculation: default behavior
c70e3c5
to
c354140
Compare
.isEqualTo("validation.msg.loan.reAge.numberOfInstallments.not.greater.than.zero"); | ||
} | ||
|
||
@Disabled |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If this test is not valid anymore, remove it.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Done
.isEqualTo("error.msg.loan.reage.supported.only.for.progressive.loan.schedule.type"); | ||
} | ||
|
||
@Disabled |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If this test is not valid anymore, remove it.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Done
...oanaccount/domain/transactionprocessor/impl/AdvancedPaymentScheduleTransactionProcessor.java
Outdated
Show resolved
Hide resolved
final LoanApplicationTerms loanApplicationTerms = new LoanApplicationTerms.Builder().submittedOnDate(expectedDisbursementDate) | ||
.currency(currency.getCurrencyData()).repaymentsStartingFromDate(reAgingStartDate) | ||
.expectedDisbursementDate(expectedDisbursementDate).principal(outstandingPrincipalBalance.get()) | ||
.loanTermFrequency(loanTransaction.getLoanReAgeParameter().getNumberOfInstallments()) | ||
.loanTermPeriodFrequencyType(loanTransaction.getLoanReAgeParameter().getFrequencyType()) | ||
.numberOfRepayments(loanTransaction.getLoanReAgeParameter().getNumberOfInstallments()) | ||
.repaymentEvery(loanTransaction.getLoanReAgeParameter().getFrequencyNumber()) | ||
.repaymentPeriodFrequencyType(loanTransaction.getLoanReAgeParameter().getFrequencyType()) | ||
.interestRatePerPeriod(interestRate) | ||
.interestRatePeriodFrequencyType(loan.getLoanRepaymentScheduleDetail().getRepaymentPeriodFrequencyType()) | ||
.annualNominalInterestRate(interestRate).daysInMonthType(loan.getLoanProduct().fetchDaysInMonthType()) | ||
.daysInYearType(loan.getLoanProduct().fetchDaysInYearType()).inArrearsTolerance(Money.zero(currency, mc)) | ||
.disbursementDatas(disbursementData).isDownPaymentEnabled(false).downPaymentPercentage(ZERO).seedDate(reAgingStartDate) | ||
.interestRecognitionOnDisbursementDate( | ||
loan.getLoanProduct().getLoanProductRelatedDetail().isInterestRecognitionOnDisbursementDate()) | ||
.daysInYearCustomStrategy(loan.getLoanProduct().getLoanProductRelatedDetail().getDaysInYearCustomStrategy()) | ||
.interestMethod(loan.getLoanProductRelatedDetail().getInterestMethod()).allowPartialPeriodInterestCalculation( | ||
loan.getLoanProduct().getLoanProductRelatedDetail().isAllowPartialPeriodInterestCalculation()) | ||
.mc(mc).build(); | ||
final LoanScheduleModel loanScheduleModelForReAging = scheduleGenerator.generate(mc, loanApplicationTerms, null, null); | ||
|
||
// Now merge the temporary schedule with existing installments | ||
mergeTemporaryScheduleWithExistingInstallments(loanScheduleModelForReAging, installments, repaymentPeriods, currency, | ||
transactionDate, ctx, loan); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@mariiaKraievska Do we need this? I mean ProgressiveEMICalculator
and existing ProgressiveLoanInterestScheduleModel
+ reage parameters would be enough to generate and update the existing ProgressiveLoanInterestScheduleModel
and once its done, just update the LoanRepaymentScheduleInstallment
based on the model. what do you think?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Done, please check
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
what changed here?
if (chargeOffTransaction.isPresent()) { | ||
repaymentPeriods.stream().filter(rp -> !rp.getDueDate().isBefore(reAgingStartDate) && !rp.isFullyPaid()) | ||
.forEach(repaymentPeriod -> { | ||
repaymentPeriod.getInterestPeriods().forEach(interestPeriod -> { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
why to set 0 rate factor and mark them as paused?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You're right, it's enough to pause them.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
why to pause them? :D
…ult Behavior, interestRecalculation = true, without dueDate change
c354140
to
3329a93
Compare
PTAL |
final Optional<LoanTransaction> chargeOffTransaction = ctx.getAlreadyProcessedTransactions().stream() | ||
.filter(t -> ((t.isChargeOff() && (loan.hasAccelerateChargeOffStrategy() || loan.hasZeroInterestChargeOffStrategy())) | ||
|| t.isContractTermination()) && !t.isReversed() && t.getTransactionDate().isBefore(reAgingStartDate)) | ||
.findFirst(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Its 2 types of transactions: chargeoff and contract termination
final Optional<LoanTransaction> chargeOffTransaction = ctx.getAlreadyProcessedTransactions().stream() | ||
.filter(t -> ((t.isChargeOff() && (loan.hasAccelerateChargeOffStrategy() || loan.hasZeroInterestChargeOffStrategy())) | ||
|| t.isContractTermination()) && !t.isReversed() && t.getTransactionDate().isBefore(reAgingStartDate)) | ||
.findFirst(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
what if txn date and reage start date are matching?
loan.getLoanProduct().getLoanProductRelatedDetail().isAllowPartialPeriodInterestCalculation()) | ||
.mc(mc).build(); | ||
final LoanScheduleModel loanScheduleModelForReAging = scheduleGenerator.generate(mc, loanApplicationTerms, null, null); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I dont think we need this. scheduleGenerator
we should use the existing model + the EmiCalculator and introduce a new action: "reage" and provide its parameters. THe EmiCalculator can calculate interim models and update existing one based on that. After the model is updated we can use to update the existing repayment installments based on the model alone.
Description
Describe the changes made and why they were made.
Ignore if these details are present on the associated Apache Fineract JIRA ticket.
Checklist
Please make sure these boxes are checked before submitting your pull request - thanks!
FYI our guidelines for code reviews are at https://cwiki.apache.org/confluence/display/FINERACT/Code+Review+Guide.