MIFOSX-32: support ability to modify loan application (or loan contract).
This commit is contained in:
@@ -4,13 +4,13 @@ import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.Collection;
|
||||
import java.util.HashSet;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
|
||||
import javax.ws.rs.Consumes;
|
||||
import javax.ws.rs.DELETE;
|
||||
import javax.ws.rs.GET;
|
||||
import javax.ws.rs.POST;
|
||||
import javax.ws.rs.PUT;
|
||||
import javax.ws.rs.Path;
|
||||
import javax.ws.rs.PathParam;
|
||||
import javax.ws.rs.Produces;
|
||||
@@ -25,10 +25,9 @@ import org.mifosng.platform.api.commands.AdjustLoanTransactionCommand;
|
||||
import org.mifosng.platform.api.commands.CalculateLoanScheduleCommand;
|
||||
import org.mifosng.platform.api.commands.LoanStateTransitionCommand;
|
||||
import org.mifosng.platform.api.commands.LoanTransactionCommand;
|
||||
import org.mifosng.platform.api.commands.SubmitLoanApplicationCommand;
|
||||
import org.mifosng.platform.api.commands.LoanApplicationCommand;
|
||||
import org.mifosng.platform.api.commands.UndoStateTransitionCommand;
|
||||
import org.mifosng.platform.api.data.ChargeData;
|
||||
import org.mifosng.platform.api.data.CurrencyData;
|
||||
import org.mifosng.platform.api.data.EntityIdentifier;
|
||||
import org.mifosng.platform.api.data.EnumOptionData;
|
||||
import org.mifosng.platform.api.data.FundData;
|
||||
@@ -47,7 +46,6 @@ import org.mifosng.platform.api.infrastructure.ApiDataConversionService;
|
||||
import org.mifosng.platform.api.infrastructure.ApiJsonSerializerService;
|
||||
import org.mifosng.platform.api.infrastructure.ApiParameterHelper;
|
||||
import org.mifosng.platform.charge.service.ChargeReadPlatformService;
|
||||
import org.mifosng.platform.currency.service.CurrencyReadPlatformService;
|
||||
import org.mifosng.platform.exceptions.UnrecognizedQueryParamException;
|
||||
import org.mifosng.platform.fund.service.FundReadPlatformService;
|
||||
import org.mifosng.platform.loan.service.CalculationPlatformService;
|
||||
@@ -167,14 +165,14 @@ public class LoansApiResource {
|
||||
}
|
||||
|
||||
Collection<LoanProductLookup> productOptions = new ArrayList<LoanProductLookup>();
|
||||
List<EnumOptionData> loanTermFrequencyTypeOptions = new ArrayList<EnumOptionData>();
|
||||
List<EnumOptionData> repaymentFrequencyTypeOptions = new ArrayList<EnumOptionData>();
|
||||
Collection<EnumOptionData> loanTermFrequencyTypeOptions = new ArrayList<EnumOptionData>();
|
||||
Collection<EnumOptionData> repaymentFrequencyTypeOptions = new ArrayList<EnumOptionData>();
|
||||
Collection<TransactionProcessingStrategyData> transactionProcessingStrategyOptions = new ArrayList<TransactionProcessingStrategyData>();
|
||||
|
||||
List<EnumOptionData> interestRateFrequencyTypeOptions = new ArrayList<EnumOptionData>();
|
||||
List<EnumOptionData> amortizationTypeOptions = new ArrayList<EnumOptionData>();
|
||||
List<EnumOptionData> interestTypeOptions = new ArrayList<EnumOptionData>();
|
||||
List<EnumOptionData> interestCalculationPeriodTypeOptions = new ArrayList<EnumOptionData>();
|
||||
Collection<EnumOptionData> interestRateFrequencyTypeOptions = new ArrayList<EnumOptionData>();
|
||||
Collection<EnumOptionData> amortizationTypeOptions = new ArrayList<EnumOptionData>();
|
||||
Collection<EnumOptionData> interestTypeOptions = new ArrayList<EnumOptionData>();
|
||||
Collection<EnumOptionData> interestCalculationPeriodTypeOptions = new ArrayList<EnumOptionData>();
|
||||
Collection<FundData> fundOptions = new ArrayList<FundData>();
|
||||
|
||||
final boolean template = ApiParameterHelper.template(uriInfo.getQueryParameters());
|
||||
@@ -195,10 +193,10 @@ public class LoansApiResource {
|
||||
transactionProcessingStrategyOptions = this.dropdownReadPlatformService.retreiveTransactionProcessingStrategies();
|
||||
}
|
||||
|
||||
LoanAccountData loanAccount = new LoanAccountData(loanBasicDetails, summary, repaymentSchedule, loanRepayments, permissions, charges,
|
||||
final LoanAccountData loanAccount = new LoanAccountData(loanBasicDetails, summary, repaymentSchedule, loanRepayments, permissions, charges,
|
||||
productOptions, loanTermFrequencyTypeOptions, repaymentFrequencyTypeOptions,
|
||||
transactionProcessingStrategyOptions, interestRateFrequencyTypeOptions,
|
||||
fundOptions);
|
||||
transactionProcessingStrategyOptions, interestRateFrequencyTypeOptions,
|
||||
amortizationTypeOptions, interestTypeOptions, interestCalculationPeriodTypeOptions, fundOptions);
|
||||
|
||||
return this.apiJsonSerializerService.serialzieLoanAccountDataToJson(prettyPrint, responseParameters, loanAccount);
|
||||
}
|
||||
@@ -210,8 +208,7 @@ public class LoansApiResource {
|
||||
@QueryParam("command") final String commandParam,
|
||||
final String jsonRequestBody) {
|
||||
|
||||
SubmitLoanApplicationCommand command = this.apiDataConversionService
|
||||
.convertJsonToSubmitLoanApplicationCommand(jsonRequestBody);
|
||||
LoanApplicationCommand command = this.apiDataConversionService.convertJsonToLoanApplicationCommand(null, jsonRequestBody);
|
||||
|
||||
CalculateLoanScheduleCommand calculateLoanScheduleCommand = command.toCalculateLoanScheduleCommand();
|
||||
LoanSchedule loanSchedule = this.calculationPlatformService.calculateLoanSchedule(calculateLoanScheduleCommand);
|
||||
@@ -228,6 +225,33 @@ public class LoansApiResource {
|
||||
|
||||
return Response.ok().entity(identifier).build();
|
||||
}
|
||||
|
||||
@PUT
|
||||
@Path("{loanId}")
|
||||
@Consumes({MediaType.APPLICATION_JSON})
|
||||
@Produces({MediaType.APPLICATION_JSON})
|
||||
public Response modifyLoanApplication(
|
||||
@PathParam("loanId") final Long loanId,
|
||||
@QueryParam("command") final String commandParam,
|
||||
final String jsonRequestBody) {
|
||||
|
||||
final LoanApplicationCommand command = this.apiDataConversionService.convertJsonToLoanApplicationCommand(loanId, jsonRequestBody);
|
||||
|
||||
final CalculateLoanScheduleCommand calculateLoanScheduleCommand = command.toCalculateLoanScheduleCommand();
|
||||
final LoanSchedule loanSchedule = this.calculationPlatformService.calculateLoanSchedule(calculateLoanScheduleCommand);
|
||||
|
||||
// for now just auto generating the loan schedule and setting support
|
||||
// for 'manual' loan schedule creation later.
|
||||
command.setLoanSchedule(loanSchedule);
|
||||
|
||||
if (is(commandParam, "calculateLoanSchedule")) {
|
||||
return Response.ok().entity(loanSchedule).build();
|
||||
}
|
||||
|
||||
EntityIdentifier identifier = this.loanWritePlatformService.modifyLoanApplication(command);
|
||||
|
||||
return Response.ok().entity(identifier).build();
|
||||
}
|
||||
|
||||
@DELETE
|
||||
@Path("{loanId}")
|
||||
|
||||
+55
-2
@@ -1,6 +1,7 @@
|
||||
package org.mifosng.platform.api.commands;
|
||||
|
||||
import java.math.BigDecimal;
|
||||
import java.util.Set;
|
||||
|
||||
import org.joda.time.LocalDate;
|
||||
import org.mifosng.platform.api.data.LoanSchedule;
|
||||
@@ -8,8 +9,9 @@ import org.mifosng.platform.api.data.LoanSchedule;
|
||||
/**
|
||||
* Immutable command for submitting new loan application.
|
||||
*/
|
||||
public class SubmitLoanApplicationCommand {
|
||||
public class LoanApplicationCommand {
|
||||
|
||||
private final Long loanId;
|
||||
private final Long clientId;
|
||||
private final Long productId;
|
||||
private final String externalId;
|
||||
@@ -42,8 +44,12 @@ public class SubmitLoanApplicationCommand {
|
||||
private final LoanChargeCommand[] charges;
|
||||
|
||||
private LoanSchedule loanSchedule;
|
||||
|
||||
private final Set<String> modifiedParameters;
|
||||
|
||||
public SubmitLoanApplicationCommand(
|
||||
public LoanApplicationCommand(
|
||||
final Set<String> modifiedParameters,
|
||||
final Long loanId,
|
||||
final Long clientId, final Long productId, final String externalId,
|
||||
final Long fundId, final Long transactionProcessingStrategyId,
|
||||
final LocalDate submittedOnDate, final String submittedOnNote,
|
||||
@@ -58,6 +64,8 @@ public class SubmitLoanApplicationCommand {
|
||||
final Integer repaymentEvery, final Integer repaymentFrequency, final Integer numberOfRepayments, Integer amortizationMethod,
|
||||
final Integer loanTermFrequency, final Integer loanTermFrequencyType,
|
||||
final BigDecimal toleranceAmount, final LoanChargeCommand[] charges) {
|
||||
this.modifiedParameters = modifiedParameters;
|
||||
this.loanId = loanId;
|
||||
this.clientId = clientId;
|
||||
this.productId = productId;
|
||||
this.externalId = externalId;
|
||||
@@ -101,6 +109,10 @@ public class SubmitLoanApplicationCommand {
|
||||
public void setLoanSchedule(LoanSchedule loanSchedule) {
|
||||
this.loanSchedule = loanSchedule;
|
||||
}
|
||||
|
||||
public Long getLoanId() {
|
||||
return loanId;
|
||||
}
|
||||
|
||||
public Long getClientId() {
|
||||
return clientId;
|
||||
@@ -194,4 +206,45 @@ public class SubmitLoanApplicationCommand {
|
||||
return charges;
|
||||
}
|
||||
|
||||
public LoanProductCommand toLoanProductCommand() {
|
||||
|
||||
// TODO - FIX UP FOR CHARGES.
|
||||
return new LoanProductCommand(modifiedParameters, this.productId, null, null,
|
||||
this.fundId, this.transactionProcessingStrategyId,
|
||||
null, null,
|
||||
this.principal, this.inArrearsTolerance,
|
||||
this.numberOfRepayments, this.repaymentEvery, this.interestRatePerPeriod,
|
||||
this.repaymentFrequencyType, this.interestRateFrequencyType,
|
||||
this.amortizationType, this.interestType,
|
||||
this.interestCalculationPeriodType,
|
||||
null);
|
||||
}
|
||||
|
||||
public boolean isClientChanged() {
|
||||
return this.modifiedParameters.contains("clientId");
|
||||
}
|
||||
|
||||
public boolean isProductChanged() {
|
||||
return this.modifiedParameters.contains("productId");
|
||||
}
|
||||
|
||||
public boolean isFundChanged() {
|
||||
return this.modifiedParameters.contains("fundId");
|
||||
}
|
||||
|
||||
public boolean isTransactionStrategyChanged() {
|
||||
return this.modifiedParameters.contains("transactionProcessingStrategyId");
|
||||
}
|
||||
|
||||
public boolean isTermFrequencyChanged() {
|
||||
return this.modifiedParameters.contains("loanTermFrequency");
|
||||
}
|
||||
|
||||
public boolean isTermFrequencyTypeChanged() {
|
||||
return this.modifiedParameters.contains("loanTermFrequencyType");
|
||||
}
|
||||
|
||||
public boolean isSubmittedOnDateChanged() {
|
||||
return this.modifiedParameters.contains("submittedOnDate");
|
||||
}
|
||||
}
|
||||
@@ -2,7 +2,6 @@ package org.mifosng.platform.api.data;
|
||||
|
||||
import java.math.BigDecimal;
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
|
||||
import org.joda.time.LocalDate;
|
||||
|
||||
@@ -52,9 +51,13 @@ public class LoanAccountData {
|
||||
|
||||
// template
|
||||
private final Collection<LoanProductLookup> productOptions;
|
||||
private final List<EnumOptionData> termFrequencyTypeOptions;
|
||||
private final List<EnumOptionData> repaymentFrequencyTypeOptions;
|
||||
private final Collection<EnumOptionData> termFrequencyTypeOptions;
|
||||
private final Collection<EnumOptionData> repaymentFrequencyTypeOptions;
|
||||
private final Collection<TransactionProcessingStrategyData> repaymentStrategyOptions;
|
||||
private final Collection<EnumOptionData> interestRateFrequencyTypeOptions;
|
||||
private final Collection<EnumOptionData> amortizationTypeOptions;
|
||||
private final Collection<EnumOptionData> interestTypeOptions;
|
||||
private final Collection<EnumOptionData> interestCalculationPeriodTypeOptions;
|
||||
private final Collection<FundData> fundOptions;
|
||||
|
||||
// associations
|
||||
@@ -64,8 +67,6 @@ public class LoanAccountData {
|
||||
|
||||
private final LoanPermissionData permissions;
|
||||
private final LoanConvenienceData convenienceData;
|
||||
private final List<EnumOptionData> interestRateFrequencyTypeOptions;
|
||||
|
||||
|
||||
public LoanAccountData(
|
||||
final LoanBasicDetailsData basicDetails,
|
||||
@@ -75,10 +76,13 @@ public class LoanAccountData {
|
||||
final LoanPermissionData permissions,
|
||||
final Collection<ChargeData> charges,
|
||||
final Collection<LoanProductLookup> productOptions,
|
||||
final List<EnumOptionData> termFrequencyTypeOptions,
|
||||
final List<EnumOptionData> repaymentFrequencyTypeOptions,
|
||||
final Collection<EnumOptionData> termFrequencyTypeOptions,
|
||||
final Collection<EnumOptionData> repaymentFrequencyTypeOptions,
|
||||
final Collection<TransactionProcessingStrategyData> transactionProcessingStrategyOptions,
|
||||
final List<EnumOptionData> interestRateFrequencyTypeOptions,
|
||||
final Collection<EnumOptionData> interestRateFrequencyTypeOptions,
|
||||
final Collection<EnumOptionData> amortizationTypeOptions,
|
||||
final Collection<EnumOptionData> interestTypeOptions,
|
||||
final Collection<EnumOptionData> interestCalculationPeriodTypeOptions,
|
||||
final Collection<FundData> fundOptions) {
|
||||
this.summary = summary;
|
||||
this.repaymentSchedule = repaymentSchedule;
|
||||
@@ -90,6 +94,9 @@ public class LoanAccountData {
|
||||
this.repaymentFrequencyTypeOptions = repaymentFrequencyTypeOptions;
|
||||
this.repaymentStrategyOptions = transactionProcessingStrategyOptions;
|
||||
this.interestRateFrequencyTypeOptions = interestRateFrequencyTypeOptions;
|
||||
this.amortizationTypeOptions = amortizationTypeOptions;
|
||||
this.interestTypeOptions = interestTypeOptions;
|
||||
this.interestCalculationPeriodTypeOptions = interestCalculationPeriodTypeOptions;
|
||||
this.fundOptions = fundOptions;
|
||||
|
||||
int maxSubmittedOnOffsetFromToday = basicDetails
|
||||
@@ -315,27 +322,39 @@ public class LoanAccountData {
|
||||
public void setCharges(Collection<ChargeData> charges) {
|
||||
this.charges = charges;
|
||||
}
|
||||
|
||||
|
||||
public Collection<LoanProductLookup> getProductOptions() {
|
||||
return productOptions;
|
||||
}
|
||||
|
||||
public List<EnumOptionData> getTermFrequencyTypeOptions() {
|
||||
|
||||
public Collection<EnumOptionData> getTermFrequencyTypeOptions() {
|
||||
return termFrequencyTypeOptions;
|
||||
}
|
||||
|
||||
public List<EnumOptionData> getRepaymentFrequencyTypeOptions() {
|
||||
public Collection<EnumOptionData> getRepaymentFrequencyTypeOptions() {
|
||||
return repaymentFrequencyTypeOptions;
|
||||
}
|
||||
|
||||
|
||||
public Collection<TransactionProcessingStrategyData> getRepaymentStrategyOptions() {
|
||||
return repaymentStrategyOptions;
|
||||
}
|
||||
|
||||
public List<EnumOptionData> getInterestRateFrequencyTypeOptions() {
|
||||
|
||||
public Collection<EnumOptionData> getInterestRateFrequencyTypeOptions() {
|
||||
return interestRateFrequencyTypeOptions;
|
||||
}
|
||||
|
||||
public Collection<EnumOptionData> getAmortizationTypeOptions() {
|
||||
return amortizationTypeOptions;
|
||||
}
|
||||
|
||||
public Collection<EnumOptionData> getInterestTypeOptions() {
|
||||
return interestTypeOptions;
|
||||
}
|
||||
|
||||
public Collection<EnumOptionData> getInterestCalculationPeriodTypeOptions() {
|
||||
return interestCalculationPeriodTypeOptions;
|
||||
}
|
||||
|
||||
public Collection<FundData> getFundOptions() {
|
||||
return fundOptions;
|
||||
}
|
||||
|
||||
+2
-2
@@ -19,7 +19,7 @@ import org.mifosng.platform.api.commands.OrganisationCurrencyCommand;
|
||||
import org.mifosng.platform.api.commands.RoleCommand;
|
||||
import org.mifosng.platform.api.commands.SavingProductCommand;
|
||||
import org.mifosng.platform.api.commands.StaffCommand;
|
||||
import org.mifosng.platform.api.commands.SubmitLoanApplicationCommand;
|
||||
import org.mifosng.platform.api.commands.LoanApplicationCommand;
|
||||
import org.mifosng.platform.api.commands.UserCommand;
|
||||
|
||||
public interface ApiDataConversionService {
|
||||
@@ -46,7 +46,7 @@ public interface ApiDataConversionService {
|
||||
|
||||
GroupCommand convertJsonToGroupCommand(Long resourceIdentifier, String jsonRequestBody);
|
||||
|
||||
SubmitLoanApplicationCommand convertJsonToSubmitLoanApplicationCommand(String jsonRequestBody);
|
||||
LoanApplicationCommand convertJsonToLoanApplicationCommand(Long resourceIdentifier, String jsonRequestBody);
|
||||
|
||||
LoanStateTransitionCommand convertJsonToLoanStateTransitionCommand(Long resourceIdentifier, String jsonRequestBody);
|
||||
|
||||
|
||||
+4
-3
@@ -37,7 +37,7 @@ import org.mifosng.platform.api.commands.OrganisationCurrencyCommand;
|
||||
import org.mifosng.platform.api.commands.RoleCommand;
|
||||
import org.mifosng.platform.api.commands.SavingProductCommand;
|
||||
import org.mifosng.platform.api.commands.StaffCommand;
|
||||
import org.mifosng.platform.api.commands.SubmitLoanApplicationCommand;
|
||||
import org.mifosng.platform.api.commands.LoanApplicationCommand;
|
||||
import org.mifosng.platform.api.commands.UserCommand;
|
||||
import org.mifosng.platform.api.data.ApiParameterError;
|
||||
import org.mifosng.platform.api.errorhandling.InvalidJsonException;
|
||||
@@ -430,7 +430,7 @@ public class ApiDataConversionServiceImpl implements ApiDataConversionService {
|
||||
}
|
||||
|
||||
@Override
|
||||
public SubmitLoanApplicationCommand convertJsonToSubmitLoanApplicationCommand(final String json) {
|
||||
public LoanApplicationCommand convertJsonToLoanApplicationCommand(final Long resourceIdentifier, final String json) {
|
||||
|
||||
if (StringUtils.isBlank(json)) {
|
||||
throw new InvalidJsonException();
|
||||
@@ -516,7 +516,8 @@ public class ApiDataConversionServiceImpl implements ApiDataConversionService {
|
||||
}
|
||||
}
|
||||
|
||||
return new SubmitLoanApplicationCommand(clientId, productId, externalId, fundId, transactionProcessingStrategyId,
|
||||
return new LoanApplicationCommand(modifiedParameters,
|
||||
resourceIdentifier, clientId, productId, externalId, fundId, transactionProcessingStrategyId,
|
||||
submittedOnDate, submittedOnNote,
|
||||
expectedDisbursementDate, repaymentsStartingFromDate, interestChargedFromDate,
|
||||
principal, interestRatePerPeriod, interestRateFrequencyTypeValue, interestTypeValue, interestCalculationPeriodTypeValue,
|
||||
|
||||
@@ -83,7 +83,7 @@ public class Note extends AbstractAuditableCustom<AppUser, Long> {
|
||||
|
||||
private Note(Loan loan, String note) {
|
||||
this.loan = loan;
|
||||
this.client = loan.getClient();
|
||||
this.client = loan.client();
|
||||
this.note = note;
|
||||
this.noteTypeId = NoteType.LOAN.getValue();
|
||||
}
|
||||
@@ -91,7 +91,7 @@ public class Note extends AbstractAuditableCustom<AppUser, Long> {
|
||||
private Note(Loan loan, LoanTransaction loanTransaction, String note) {
|
||||
this.loan = loan;
|
||||
this.loanTransaction = loanTransaction;
|
||||
this.client = loan.getClient();
|
||||
this.client = loan.client();
|
||||
this.note = note;
|
||||
this.noteTypeId = NoteType.LOAN_TRANSACTION.getValue();
|
||||
}
|
||||
|
||||
@@ -11,8 +11,6 @@ import javax.persistence.CascadeType;
|
||||
import javax.persistence.Column;
|
||||
import javax.persistence.Embedded;
|
||||
import javax.persistence.Entity;
|
||||
import javax.persistence.EnumType;
|
||||
import javax.persistence.Enumerated;
|
||||
import javax.persistence.JoinColumn;
|
||||
import javax.persistence.ManyToOne;
|
||||
import javax.persistence.OneToMany;
|
||||
@@ -29,6 +27,10 @@ import org.hibernate.annotations.LazyCollection;
|
||||
import org.hibernate.annotations.LazyCollectionOption;
|
||||
import org.joda.time.DateTime;
|
||||
import org.joda.time.LocalDate;
|
||||
import org.mifosng.platform.api.commands.LoanApplicationCommand;
|
||||
import org.mifosng.platform.api.data.LoanSchedule;
|
||||
import org.mifosng.platform.api.data.MoneyData;
|
||||
import org.mifosng.platform.api.data.ScheduledLoanInstallment;
|
||||
import org.mifosng.platform.client.domain.Client;
|
||||
import org.mifosng.platform.currency.domain.MonetaryCurrency;
|
||||
import org.mifosng.platform.currency.domain.Money;
|
||||
@@ -44,12 +46,13 @@ public class Loan extends AbstractAuditableCustom<AppUser, Long> {
|
||||
|
||||
@ManyToOne
|
||||
@JoinColumn(name = "client_id", nullable = false)
|
||||
private final Client client;
|
||||
private Client client;
|
||||
|
||||
@ManyToOne
|
||||
@JoinColumn(name = "product_id")
|
||||
private final LoanProduct loanProduct;
|
||||
private LoanProduct loanProduct;
|
||||
|
||||
@SuppressWarnings("unused")
|
||||
@ManyToOne
|
||||
@JoinColumn(name = "fund_id", nullable = true)
|
||||
private Fund fund;
|
||||
@@ -62,16 +65,15 @@ public class Loan extends AbstractAuditableCustom<AppUser, Long> {
|
||||
private String externalId;
|
||||
|
||||
@Embedded
|
||||
private final LoanProductRelatedDetail loanRepaymentScheduleDetail;
|
||||
private LoanProductRelatedDetail loanRepaymentScheduleDetail;
|
||||
|
||||
@SuppressWarnings("unused")
|
||||
@Column(name = "term_frequency", nullable = false)
|
||||
private Integer termFrequency;
|
||||
|
||||
@SuppressWarnings("unused")
|
||||
@Enumerated(EnumType.ORDINAL)
|
||||
@Column(name = "term_period_frequency_enum", nullable = false)
|
||||
private PeriodFrequencyType termPeriodFrequencyType;
|
||||
private Integer termPeriodFrequencyType;
|
||||
|
||||
@Column(name = "loan_status_id", nullable = false)
|
||||
private Integer loanStatus;
|
||||
@@ -184,21 +186,76 @@ public class Loan extends AbstractAuditableCustom<AppUser, Long> {
|
||||
this.interestRebateOwed = BigDecimal.ZERO;
|
||||
}
|
||||
|
||||
public Client getClient() {
|
||||
public Client client() {
|
||||
return this.client;
|
||||
}
|
||||
|
||||
public Fund getFund() {
|
||||
return this.fund;
|
||||
}
|
||||
|
||||
public LoanProduct getLoanProduct() {
|
||||
public LoanProduct loanProduct() {
|
||||
return this.loanProduct;
|
||||
}
|
||||
|
||||
public LoanProductRelatedDetail getLoanRepaymentScheduleDetail() {
|
||||
public LoanProductRelatedDetail repaymentScheduleDetail() {
|
||||
return this.loanRepaymentScheduleDetail;
|
||||
}
|
||||
|
||||
public void modifyLoanApplication(final LoanApplicationCommand command, final Client client, final LoanProduct loanProduct,
|
||||
final Fund fund, final LoanTransactionProcessingStrategy strategy, final LoanSchedule modifiedLoanSchedule) {
|
||||
|
||||
if (command.isClientChanged()) {
|
||||
this.client = client;
|
||||
}
|
||||
if (command.isProductChanged()) {
|
||||
this.loanProduct = loanProduct;
|
||||
}
|
||||
if (command.isFundChanged()) {
|
||||
this.fund = fund;
|
||||
}
|
||||
if (command.isTransactionStrategyChanged()) {
|
||||
this.transactionProcessingStrategy = strategy;
|
||||
}
|
||||
|
||||
if (command.isTermFrequencyChanged()) {
|
||||
this.termFrequency = command.getLoanTermFrequency();
|
||||
}
|
||||
|
||||
if (command.isTermFrequencyTypeChanged()) {
|
||||
this.termPeriodFrequencyType = PeriodFrequencyType.fromInt(command.getLoanTermFrequencyType()).getValue();
|
||||
}
|
||||
|
||||
if (command.isSubmittedOnDateChanged()) {
|
||||
this.submittedOnDate = command.getSubmittedOnDate().toDate();
|
||||
}
|
||||
|
||||
this.loanRepaymentScheduleDetail.update(command.toLoanProductCommand());
|
||||
|
||||
// FIXME - rewrite over loan schedule by default for now but worth putting in check to see if required
|
||||
// i.e. only a client change wouldn't require it, only if one of parameters related to loan schedule calculation is changed.
|
||||
this.repaymentScheduleInstallments.clear();
|
||||
for (ScheduledLoanInstallment scheduledLoanInstallment : modifiedLoanSchedule.getScheduledLoanInstallments()) {
|
||||
|
||||
MoneyData readPrincipalDue = scheduledLoanInstallment.getPrincipalDue();
|
||||
MoneyData readInterestDue = scheduledLoanInstallment.getInterestDue();
|
||||
|
||||
LoanRepaymentScheduleInstallment installment = new LoanRepaymentScheduleInstallment(
|
||||
this, scheduledLoanInstallment.getInstallmentNumber(),
|
||||
scheduledLoanInstallment.getPeriodEnd(), readPrincipalDue.getAmount(),
|
||||
readInterestDue.getAmount());
|
||||
this.addRepaymentScheduleInstallment(installment);
|
||||
}
|
||||
|
||||
// if the loan application/contract is modified when repayments are already against it - then need to re-process it
|
||||
List<LoanTransaction> repaymentsOrWaivers = new ArrayList<LoanTransaction>();
|
||||
for (LoanTransaction transaction : this.loanTransactions) {
|
||||
if (!transaction.isDisbursement() && transaction.isNotContra()) {
|
||||
repaymentsOrWaivers.add(transaction);
|
||||
}
|
||||
}
|
||||
LoanTransactionComparator transactionComparator = new LoanTransactionComparator();
|
||||
Collections.sort(repaymentsOrWaivers, transactionComparator);
|
||||
|
||||
final LoanRepaymentScheduleTransactionProcessor loanRepaymentScheduleTransactionProcessor = this.transactionProcessor.determineProcessor(this.transactionProcessingStrategy);
|
||||
loanRepaymentScheduleTransactionProcessor.handleTransaction(repaymentsOrWaivers, getCurrency(), this.repaymentScheduleInstallments);
|
||||
}
|
||||
|
||||
public void submitApplication(
|
||||
final Integer loanTermFrequency,
|
||||
@@ -218,7 +275,7 @@ public class Loan extends AbstractAuditableCustom<AppUser, Long> {
|
||||
this.loanStatus = statusEnum.getValue();
|
||||
|
||||
this.termFrequency = loanTermFrequency;
|
||||
this.termPeriodFrequencyType = loanTermFrequencyType;
|
||||
this.termPeriodFrequencyType = loanTermFrequencyType.getValue();
|
||||
|
||||
this.submittedOnDate = submittedOn.toDateTimeAtCurrentTime().toDate();
|
||||
|
||||
@@ -257,8 +314,7 @@ public class Loan extends AbstractAuditableCustom<AppUser, Long> {
|
||||
}
|
||||
}
|
||||
|
||||
public void reject(final LocalDate rejectedOn,
|
||||
LoanLifecycleStateMachine loanLifecycleStateMachine) {
|
||||
public void reject(final LocalDate rejectedOn, final LoanLifecycleStateMachine loanLifecycleStateMachine) {
|
||||
|
||||
LoanStatus statusEnum = loanLifecycleStateMachine.transition(LoanEvent.LOAN_REJECTED, LoanStatus.fromInt(this.loanStatus));
|
||||
this.loanStatus = statusEnum.getValue();
|
||||
@@ -1118,5 +1174,4 @@ public class Loan extends AbstractAuditableCustom<AppUser, Long> {
|
||||
return this.loanRepaymentScheduleDetail.getPrincipal()
|
||||
.getCurrencyCode();
|
||||
}
|
||||
|
||||
}
|
||||
+1
-2
@@ -17,8 +17,7 @@ import org.mifosng.platform.currency.domain.Money;
|
||||
* {@link LoanProduct} that are also used and persisted by a {@link Loan}.
|
||||
*/
|
||||
@Embeddable
|
||||
public class LoanProductRelatedDetail implements
|
||||
LoanProductMinimumRepaymentScheduleRelatedDetail {
|
||||
public class LoanProductRelatedDetail implements LoanProductMinimumRepaymentScheduleRelatedDetail {
|
||||
|
||||
@Embedded
|
||||
private MonetaryCurrency currency;
|
||||
|
||||
+4
-4
@@ -5,15 +5,15 @@ import java.util.List;
|
||||
|
||||
import org.mifosng.platform.api.commands.CalculateLoanScheduleCommand;
|
||||
import org.mifosng.platform.api.commands.LoanChargeCommand;
|
||||
import org.mifosng.platform.api.commands.SubmitLoanApplicationCommand;
|
||||
import org.mifosng.platform.api.commands.LoanApplicationCommand;
|
||||
import org.mifosng.platform.api.data.ApiParameterError;
|
||||
import org.mifosng.platform.exceptions.PlatformApiDataValidationException;
|
||||
|
||||
public class SubmitLoanApplicationCommandValidator {
|
||||
public class LoanApplicationCommandValidator {
|
||||
|
||||
private final SubmitLoanApplicationCommand command;
|
||||
private final LoanApplicationCommand command;
|
||||
|
||||
public SubmitLoanApplicationCommandValidator(SubmitLoanApplicationCommand command) {
|
||||
public LoanApplicationCommandValidator(LoanApplicationCommand command) {
|
||||
this.command = command;
|
||||
}
|
||||
|
||||
+29
-22
@@ -7,7 +7,7 @@ import java.util.List;
|
||||
import java.util.Set;
|
||||
|
||||
import org.mifosng.platform.api.commands.LoanChargeCommand;
|
||||
import org.mifosng.platform.api.commands.SubmitLoanApplicationCommand;
|
||||
import org.mifosng.platform.api.commands.LoanApplicationCommand;
|
||||
import org.mifosng.platform.api.data.LoanSchedule;
|
||||
import org.mifosng.platform.api.data.MoneyData;
|
||||
import org.mifosng.platform.api.data.ScheduledLoanInstallment;
|
||||
@@ -69,7 +69,7 @@ public class LoanAssembler {
|
||||
this.loanTransactionProcessingStrategyRepository = loanTransactionProcessingStrategyRepository;
|
||||
}
|
||||
|
||||
public Loan assembleFrom(final SubmitLoanApplicationCommand command) {
|
||||
public Loan assembleFrom(final LoanApplicationCommand command) {
|
||||
|
||||
LoanProduct loanProduct = this.loanProductRepository.findOne(command.getProductId());
|
||||
if (loanProduct == null) {
|
||||
@@ -82,26 +82,10 @@ public class LoanAssembler {
|
||||
}
|
||||
|
||||
MonetaryCurrency currency = loanProduct.getCurrency();
|
||||
final BigDecimal defaultNominalInterestRatePerPeriod = command.getInterestRatePerPeriod();
|
||||
final PeriodFrequencyType interestPeriodFrequencyType = PeriodFrequencyType.fromInt(command.getInterestRateFrequencyType());
|
||||
|
||||
BigDecimal defaultAnnualNominalInterestRate = aprCalculator.calculateFrom(interestPeriodFrequencyType, command.getInterestRatePerPeriod());
|
||||
|
||||
final InterestMethod interestMethod = InterestMethod.fromInt(command.getInterestType());
|
||||
final InterestCalculationPeriodMethod interestCalculationPeriodMethod = InterestCalculationPeriodMethod.fromInt(command.getInterestCalculationPeriodType());
|
||||
|
||||
final Integer loanTermFrequency = command.getLoanTermFrequency();
|
||||
final PeriodFrequencyType loanTermFrequencyType = PeriodFrequencyType.fromInt(command.getLoanTermFrequencyType());
|
||||
final Integer defaultNumberOfInstallments = command.getNumberOfRepayments();
|
||||
final Integer repayEvery = command.getRepaymentEvery();
|
||||
final PeriodFrequencyType repaymentFrequencyType = PeriodFrequencyType.fromInt(command.getRepaymentFrequencyType());
|
||||
|
||||
final AmortizationMethod amortizationMethod = AmortizationMethod.fromInt(command.getAmortizationType());
|
||||
|
||||
LoanProductRelatedDetail loanRepaymentScheduleDetail = new LoanProductRelatedDetail(currency,
|
||||
command.getPrincipal(), defaultNominalInterestRatePerPeriod, interestPeriodFrequencyType, defaultAnnualNominalInterestRate,
|
||||
interestMethod, interestCalculationPeriodMethod,
|
||||
repayEvery, repaymentFrequencyType, defaultNumberOfInstallments, amortizationMethod, command.getInArrearsTolerance());
|
||||
LoanProductRelatedDetail loanRepaymentScheduleDetail = assembleLoanProductRelatedDetailFrom(command, currency);
|
||||
|
||||
LoanSchedule loanSchedule = command.getLoanSchedule();
|
||||
List<ScheduledLoanInstallment> loanRepaymentSchedule = loanSchedule.getScheduledLoanInstallments();
|
||||
@@ -136,12 +120,35 @@ public class LoanAssembler {
|
||||
return loan;
|
||||
}
|
||||
|
||||
public LoanProductRelatedDetail assembleLoanProductRelatedDetailFrom(final LoanApplicationCommand command, MonetaryCurrency currency) {
|
||||
final BigDecimal defaultNominalInterestRatePerPeriod = command.getInterestRatePerPeriod();
|
||||
final PeriodFrequencyType interestPeriodFrequencyType = PeriodFrequencyType.fromInt(command.getInterestRateFrequencyType());
|
||||
|
||||
BigDecimal defaultAnnualNominalInterestRate = aprCalculator.calculateFrom(interestPeriodFrequencyType, command.getInterestRatePerPeriod());
|
||||
|
||||
final InterestMethod interestMethod = InterestMethod.fromInt(command.getInterestType());
|
||||
final InterestCalculationPeriodMethod interestCalculationPeriodMethod = InterestCalculationPeriodMethod.fromInt(command.getInterestCalculationPeriodType());
|
||||
|
||||
|
||||
final Integer defaultNumberOfInstallments = command.getNumberOfRepayments();
|
||||
final Integer repayEvery = command.getRepaymentEvery();
|
||||
final PeriodFrequencyType repaymentFrequencyType = PeriodFrequencyType.fromInt(command.getRepaymentFrequencyType());
|
||||
|
||||
final AmortizationMethod amortizationMethod = AmortizationMethod.fromInt(command.getAmortizationType());
|
||||
|
||||
LoanProductRelatedDetail loanRepaymentScheduleDetail = new LoanProductRelatedDetail(currency,
|
||||
command.getPrincipal(), defaultNominalInterestRatePerPeriod, interestPeriodFrequencyType, defaultAnnualNominalInterestRate,
|
||||
interestMethod, interestCalculationPeriodMethod,
|
||||
repayEvery, repaymentFrequencyType, defaultNumberOfInstallments, amortizationMethod, command.getInArrearsTolerance());
|
||||
return loanRepaymentScheduleDetail;
|
||||
}
|
||||
|
||||
private LoanLifecycleStateMachine defaultLoanLifecycleStateMachine() {
|
||||
List<LoanStatus> allowedLoanStatuses = Arrays.asList(LoanStatus.values());
|
||||
return new DefaultLoanLifecycleStateMachine(allowedLoanStatuses);
|
||||
}
|
||||
|
||||
private Fund findFundByIdIfProvided(final Long fundId) {
|
||||
public Fund findFundByIdIfProvided(final Long fundId) {
|
||||
Fund fund = null;
|
||||
if (fundId != null) {
|
||||
fund = this.fundRepository.findOne(fundId);
|
||||
@@ -152,7 +159,7 @@ public class LoanAssembler {
|
||||
return fund;
|
||||
}
|
||||
|
||||
private LoanTransactionProcessingStrategy findStrategyByIdIfProvided(final Long transactionProcessingStrategyId) {
|
||||
public LoanTransactionProcessingStrategy findStrategyByIdIfProvided(final Long transactionProcessingStrategyId) {
|
||||
LoanTransactionProcessingStrategy strategy = null;
|
||||
if (transactionProcessingStrategyId != null) {
|
||||
strategy = this.loanTransactionProcessingStrategyRepository.findOne(transactionProcessingStrategyId);
|
||||
@@ -163,7 +170,7 @@ public class LoanAssembler {
|
||||
return strategy;
|
||||
}
|
||||
|
||||
private Set<LoanCharge> assembleSetOfCharges(final SubmitLoanApplicationCommand command, final Loan loan,
|
||||
private Set<LoanCharge> assembleSetOfCharges(final LoanApplicationCommand command, final Loan loan,
|
||||
final LoanProduct product, final String currencyCode) {
|
||||
|
||||
Set<LoanCharge> charges = new HashSet<LoanCharge>();
|
||||
|
||||
+3
-3
@@ -293,7 +293,7 @@ public class LoanReadPlatformServiceImpl implements LoanReadPlatformService {
|
||||
throw new LoanNotFoundException(loanId);
|
||||
}
|
||||
|
||||
final String currencyCode = loan.getLoanRepaymentScheduleDetail()
|
||||
final String currencyCode = loan.repaymentScheduleDetail()
|
||||
.getPrincipal().getCurrencyCode();
|
||||
ApplicationCurrency currency = this.applicationCurrencyRepository
|
||||
.findOneByCode(currencyCode);
|
||||
@@ -332,7 +332,7 @@ public class LoanReadPlatformServiceImpl implements LoanReadPlatformService {
|
||||
throw new LoanNotFoundException(loanId);
|
||||
}
|
||||
|
||||
final String currencyCode = loan.getLoanRepaymentScheduleDetail()
|
||||
final String currencyCode = loan.repaymentScheduleDetail()
|
||||
.getPrincipal().getCurrencyCode();
|
||||
ApplicationCurrency currency = this.applicationCurrencyRepository
|
||||
.findOneByCode(currencyCode);
|
||||
@@ -368,7 +368,7 @@ public class LoanReadPlatformServiceImpl implements LoanReadPlatformService {
|
||||
throw new LoanNotFoundException(loanId);
|
||||
}
|
||||
|
||||
final String currencyCode = loan.getLoanRepaymentScheduleDetail()
|
||||
final String currencyCode = loan.repaymentScheduleDetail()
|
||||
.getPrincipal().getCurrencyCode();
|
||||
ApplicationCurrency currency = this.applicationCurrencyRepository
|
||||
.findOneByCode(currencyCode);
|
||||
|
||||
+5
-2
@@ -3,7 +3,7 @@ package org.mifosng.platform.loan.service;
|
||||
import org.mifosng.platform.api.commands.AdjustLoanTransactionCommand;
|
||||
import org.mifosng.platform.api.commands.LoanStateTransitionCommand;
|
||||
import org.mifosng.platform.api.commands.LoanTransactionCommand;
|
||||
import org.mifosng.platform.api.commands.SubmitLoanApplicationCommand;
|
||||
import org.mifosng.platform.api.commands.LoanApplicationCommand;
|
||||
import org.mifosng.platform.api.commands.UndoStateTransitionCommand;
|
||||
import org.mifosng.platform.api.data.EntityIdentifier;
|
||||
import org.springframework.security.access.prepost.PreAuthorize;
|
||||
@@ -11,7 +11,10 @@ import org.springframework.security.access.prepost.PreAuthorize;
|
||||
public interface LoanWritePlatformService {
|
||||
|
||||
@PreAuthorize(value = "hasAnyRole('PORTFOLIO_MANAGEMENT_SUPER_USER_ROLE', 'CAN_SUBMIT_NEW_LOAN_APPLICATION_ROLE', 'CAN_SUBMIT_HISTORIC_LOAN_APPLICATION_ROLE')")
|
||||
EntityIdentifier submitLoanApplication(SubmitLoanApplicationCommand command);
|
||||
EntityIdentifier submitLoanApplication(LoanApplicationCommand command);
|
||||
|
||||
@PreAuthorize(value = "hasAnyRole('PORTFOLIO_MANAGEMENT_SUPER_USER_ROLE', 'CAN_SUBMIT_NEW_LOAN_APPLICATION_ROLE', 'CAN_SUBMIT_HISTORIC_LOAN_APPLICATION_ROLE')")
|
||||
EntityIdentifier modifyLoanApplication(LoanApplicationCommand command);
|
||||
|
||||
@PreAuthorize(value = "hasAnyRole('PORTFOLIO_MANAGEMENT_SUPER_USER_ROLE', 'CAN_DELETE_LOAN_THAT_IS_SUBMITTED_AND_NOT_APPROVED')")
|
||||
EntityIdentifier deleteLoan(Long loanId);
|
||||
|
||||
+74
-16
@@ -9,28 +9,36 @@ import org.apache.commons.lang.StringUtils;
|
||||
import org.joda.time.LocalDate;
|
||||
import org.mifosng.platform.api.commands.AdjustLoanTransactionCommand;
|
||||
import org.mifosng.platform.api.commands.CalculateLoanScheduleCommand;
|
||||
import org.mifosng.platform.api.commands.LoanApplicationCommand;
|
||||
import org.mifosng.platform.api.commands.LoanStateTransitionCommand;
|
||||
import org.mifosng.platform.api.commands.LoanTransactionCommand;
|
||||
import org.mifosng.platform.api.commands.SubmitLoanApplicationCommand;
|
||||
import org.mifosng.platform.api.commands.UndoStateTransitionCommand;
|
||||
import org.mifosng.platform.api.data.EntityIdentifier;
|
||||
import org.mifosng.platform.api.data.LoanSchedule;
|
||||
import org.mifosng.platform.api.data.ScheduledLoanInstallment;
|
||||
import org.mifosng.platform.client.domain.Client;
|
||||
import org.mifosng.platform.client.domain.ClientRepository;
|
||||
import org.mifosng.platform.client.domain.Note;
|
||||
import org.mifosng.platform.client.domain.NoteRepository;
|
||||
import org.mifosng.platform.currency.domain.MonetaryCurrency;
|
||||
import org.mifosng.platform.currency.domain.Money;
|
||||
import org.mifosng.platform.exceptions.ClientNotFoundException;
|
||||
import org.mifosng.platform.exceptions.LoanNotFoundException;
|
||||
import org.mifosng.platform.exceptions.LoanNotInSubmittedAndPendingApprovalStateCannotBeDeleted;
|
||||
import org.mifosng.platform.exceptions.LoanProductNotFoundException;
|
||||
import org.mifosng.platform.exceptions.LoanTransactionNotFoundException;
|
||||
import org.mifosng.platform.exceptions.NoAuthorizationException;
|
||||
import org.mifosng.platform.fund.domain.Fund;
|
||||
import org.mifosng.platform.loan.domain.DefaultLoanLifecycleStateMachine;
|
||||
import org.mifosng.platform.loan.domain.Loan;
|
||||
import org.mifosng.platform.loan.domain.LoanLifecycleStateMachine;
|
||||
import org.mifosng.platform.loan.domain.LoanProduct;
|
||||
import org.mifosng.platform.loan.domain.LoanProductRepository;
|
||||
import org.mifosng.platform.loan.domain.LoanRepaymentScheduleInstallment;
|
||||
import org.mifosng.platform.loan.domain.LoanRepository;
|
||||
import org.mifosng.platform.loan.domain.LoanStatus;
|
||||
import org.mifosng.platform.loan.domain.LoanTransaction;
|
||||
import org.mifosng.platform.loan.domain.LoanTransactionProcessingStrategy;
|
||||
import org.mifosng.platform.loan.domain.LoanTransactionRepository;
|
||||
import org.mifosng.platform.loan.domain.PeriodFrequencyType;
|
||||
import org.mifosng.platform.security.PlatformSecurityContext;
|
||||
@@ -49,17 +57,22 @@ public class LoanWritePlatformServiceJpaRepositoryImpl implements LoanWritePlatf
|
||||
private final CalculationPlatformService calculationPlatformService;
|
||||
private final LoanTransactionRepository loanTransactionRepository;
|
||||
private final LoanAssembler loanAssembler;
|
||||
private final ClientRepository clientRepository;
|
||||
private final LoanProductRepository loanProductRepository;
|
||||
|
||||
@Autowired
|
||||
public LoanWritePlatformServiceJpaRepositoryImpl(final PlatformSecurityContext context, final LoanAssembler loanAssembler,
|
||||
final LoanRepository loanRepository, final LoanTransactionRepository loanTransactionRepository,
|
||||
final NoteRepository noteRepository, final CalculationPlatformService calculationPlatformService) {
|
||||
final NoteRepository noteRepository, final CalculationPlatformService calculationPlatformService,
|
||||
final ClientRepository clientRepository, final LoanProductRepository loanProductRepository) {
|
||||
this.context = context;
|
||||
this.loanAssembler = loanAssembler;
|
||||
this.loanRepository = loanRepository;
|
||||
this.loanTransactionRepository = loanTransactionRepository;
|
||||
this.noteRepository = noteRepository;
|
||||
this.calculationPlatformService = calculationPlatformService;
|
||||
this.clientRepository = clientRepository;
|
||||
this.loanProductRepository = loanProductRepository;
|
||||
}
|
||||
|
||||
private boolean isBeforeToday(final LocalDate date) {
|
||||
@@ -73,11 +86,11 @@ public class LoanWritePlatformServiceJpaRepositoryImpl implements LoanWritePlatf
|
||||
|
||||
@Transactional
|
||||
@Override
|
||||
public EntityIdentifier submitLoanApplication(final SubmitLoanApplicationCommand command) {
|
||||
public EntityIdentifier submitLoanApplication(final LoanApplicationCommand command) {
|
||||
|
||||
AppUser currentUser = context.authenticatedUser();
|
||||
|
||||
SubmitLoanApplicationCommandValidator validator = new SubmitLoanApplicationCommandValidator(command);
|
||||
LoanApplicationCommandValidator validator = new LoanApplicationCommandValidator(command);
|
||||
validator.validate();
|
||||
|
||||
LocalDate submittedOn = command.getSubmittedOnDate();
|
||||
@@ -97,6 +110,51 @@ public class LoanWritePlatformServiceJpaRepositoryImpl implements LoanWritePlatf
|
||||
return new EntityIdentifier(loan.getId());
|
||||
}
|
||||
|
||||
@Transactional
|
||||
@Override
|
||||
public EntityIdentifier modifyLoanApplication(final LoanApplicationCommand command) {
|
||||
AppUser currentUser = context.authenticatedUser();
|
||||
|
||||
LoanApplicationCommandValidator validator = new LoanApplicationCommandValidator(command);
|
||||
validator.validate();
|
||||
|
||||
// TODO - fix up permissions for loan modification
|
||||
LocalDate submittedOn = command.getSubmittedOnDate();
|
||||
if (this.isBeforeToday(submittedOn) && currentUser.hasNotPermissionForAnyOf("CAN_SUBMIT_HISTORIC_LOAN_APPLICATION_ROLE", "PORTFOLIO_MANAGEMENT_SUPER_USER_ROLE")) {
|
||||
throw new NoAuthorizationException("Cannot modify backdated loan.");
|
||||
}
|
||||
|
||||
Loan loan = this.loanRepository.findOne(command.getLoanId());
|
||||
if (loan == null) {
|
||||
throw new LoanNotFoundException(command.getLoanId());
|
||||
}
|
||||
|
||||
LoanProduct loanProduct = this.loanProductRepository.findOne(command.getProductId());
|
||||
if (loanProduct == null) {
|
||||
throw new LoanProductNotFoundException(command.getProductId());
|
||||
}
|
||||
|
||||
Client client = this.clientRepository.findOne(command.getClientId());
|
||||
if (client == null || client.isDeleted()) {
|
||||
throw new ClientNotFoundException(command.getClientId());
|
||||
}
|
||||
|
||||
Fund fund = this.loanAssembler.findFundByIdIfProvided(command.getFundId());
|
||||
LoanTransactionProcessingStrategy strategy = this.loanAssembler.findStrategyByIdIfProvided(command.getTransactionProcessingStrategyId());
|
||||
|
||||
LoanSchedule loanSchedule = this.calculationPlatformService.calculateLoanSchedule(command.toCalculateLoanScheduleCommand());
|
||||
loan.modifyLoanApplication(command, client, loanProduct, fund, strategy, loanSchedule);
|
||||
|
||||
this.loanRepository.save(loan);
|
||||
|
||||
if (StringUtils.isNotBlank(command.getSubmittedOnNote())) {
|
||||
Note note = Note.loanNote(loan, command.getSubmittedOnNote());
|
||||
this.noteRepository.save(note);
|
||||
}
|
||||
|
||||
return new EntityIdentifier(loan.getId());
|
||||
}
|
||||
|
||||
@Transactional
|
||||
@Override
|
||||
public EntityIdentifier deleteLoan(final Long loanId) {
|
||||
@@ -261,13 +319,13 @@ public class LoanWritePlatformServiceJpaRepositoryImpl implements LoanWritePlatf
|
||||
LocalDate repaymentsStartingFromDate = loan.getExpectedFirstRepaymentOnDate();
|
||||
LocalDate interestCalculatedFromDate = loan.getInterestChargedFromDate();
|
||||
|
||||
BigDecimal principalAsDecimal = loan.getLoanRepaymentScheduleDetail().getPrincipal().getAmount();
|
||||
BigDecimal interestRatePerYear = loan.getLoanRepaymentScheduleDetail().getAnnualNominalInterestRate();
|
||||
Integer numberOfInstallments = loan.getLoanRepaymentScheduleDetail().getNumberOfRepayments();
|
||||
BigDecimal principalAsDecimal = loan.repaymentScheduleDetail().getPrincipal().getAmount();
|
||||
BigDecimal interestRatePerYear = loan.repaymentScheduleDetail().getAnnualNominalInterestRate();
|
||||
Integer numberOfInstallments = loan.repaymentScheduleDetail().getNumberOfRepayments();
|
||||
|
||||
Integer repaidEvery = loan.getLoanRepaymentScheduleDetail().getRepayEvery();
|
||||
Integer selectedRepaymentFrequency = loan.getLoanRepaymentScheduleDetail().getRepaymentPeriodFrequencyType().getValue();
|
||||
Integer selectedAmortizationMethod = loan.getLoanRepaymentScheduleDetail().getAmortizationMethod().getValue();
|
||||
Integer repaidEvery = loan.repaymentScheduleDetail().getRepayEvery();
|
||||
Integer selectedRepaymentFrequency = loan.repaymentScheduleDetail().getRepaymentPeriodFrequencyType().getValue();
|
||||
Integer selectedAmortizationMethod = loan.repaymentScheduleDetail().getAmortizationMethod().getValue();
|
||||
|
||||
// FIXME - use values from loan table here instead of inferring.
|
||||
Integer loanTermFrequency = repaidEvery * numberOfInstallments;
|
||||
@@ -277,11 +335,11 @@ public class LoanWritePlatformServiceJpaRepositoryImpl implements LoanWritePlatf
|
||||
BigDecimal interestRatePerPeriod = interestRatePerYear;
|
||||
Integer interestRateFrequencyMethod = PeriodFrequencyType.YEARS.getValue();
|
||||
|
||||
Integer interestMethod = loan.getLoanRepaymentScheduleDetail().getInterestMethod().getValue();
|
||||
Integer interestCalculationInPeriod = loan.getLoanRepaymentScheduleDetail().getInterestCalculationPeriodMethod().getValue();
|
||||
Integer interestMethod = loan.repaymentScheduleDetail().getInterestMethod().getValue();
|
||||
Integer interestCalculationInPeriod = loan.repaymentScheduleDetail().getInterestCalculationPeriodMethod().getValue();
|
||||
|
||||
CalculateLoanScheduleCommand calculateCommand = new CalculateLoanScheduleCommand(
|
||||
loan.getLoanProduct().getId(),
|
||||
loan.loanProduct().getId(),
|
||||
principalAsDecimal,
|
||||
interestRatePerPeriod, interestRateFrequencyMethod, interestMethod, interestCalculationInPeriod,
|
||||
repaidEvery, selectedRepaymentFrequency, numberOfInstallments, selectedAmortizationMethod,
|
||||
@@ -374,7 +432,7 @@ public class LoanWritePlatformServiceJpaRepositoryImpl implements LoanWritePlatf
|
||||
throw new NoAuthorizationException("error.msg.no.permission.to.make.repayment.on.loan.in.past");
|
||||
}
|
||||
|
||||
Money repayment = Money.of(loan.getLoanRepaymentScheduleDetail()
|
||||
Money repayment = Money.of(loan.repaymentScheduleDetail()
|
||||
.getPrincipal().getCurrency(),
|
||||
command.getTransactionAmount());
|
||||
|
||||
@@ -412,7 +470,7 @@ public class LoanWritePlatformServiceJpaRepositoryImpl implements LoanWritePlatf
|
||||
}
|
||||
|
||||
Money transactionAmount = Money.of(loan
|
||||
.getLoanRepaymentScheduleDetail().getPrincipal()
|
||||
.repaymentScheduleDetail().getPrincipal()
|
||||
.getCurrency(), command.getTransactionAmount());
|
||||
|
||||
// adjustment is only supported for repayments and waivers at present
|
||||
@@ -451,7 +509,7 @@ public class LoanWritePlatformServiceJpaRepositoryImpl implements LoanWritePlatf
|
||||
throw new LoanNotFoundException(command.getLoanId());
|
||||
}
|
||||
|
||||
Money waived = Money.of(loan.getLoanRepaymentScheduleDetail()
|
||||
Money waived = Money.of(loan.repaymentScheduleDetail()
|
||||
.getPrincipal().getCurrency(),
|
||||
command.getTransactionAmount());
|
||||
|
||||
|
||||
Reference in New Issue
Block a user