Merge pull request #502 from johnw65/externalIds
mifosx-567 allow post and put for externalId for loanproduct
This commit is contained in:
@@ -1,2 +1,2 @@
|
||||
INSERT INTO `m_permission` (grouping,code,`entity_name`,`action_name`,`can_maker_checker')
|
||||
values('portfolio_group','ASSIGNSTAFF_GROUP','GROUP','ASSIGNSTAFF',0)
|
||||
INSERT INTO `m_permission` (grouping,code,`entity_name`,`action_name`,`can_maker_checker`)
|
||||
values('portfolio_group','ASSIGNSTAFF_GROUP','GROUP','ASSIGNSTAFF',0);
|
||||
+2
-1
@@ -22,7 +22,8 @@ import org.mifosplatform.organisation.office.domain.Office;
|
||||
import org.springframework.data.jpa.domain.AbstractPersistable;
|
||||
|
||||
@Entity
|
||||
@Table(name = "m_staff", uniqueConstraints = { @UniqueConstraint(columnNames = { "display_name" }, name = "display_name") })
|
||||
@Table(name = "m_staff", uniqueConstraints = { @UniqueConstraint(columnNames = { "display_name" }, name = "display_name") ,
|
||||
@UniqueConstraint(columnNames = { "external_id" }, name = "external_id_UNIQUE") })
|
||||
public class Staff extends AbstractPersistable<Long> {
|
||||
|
||||
@Column(name = "firstname", length = 50)
|
||||
|
||||
+1
-1
@@ -69,7 +69,7 @@ public class LoanProductsApiResource {
|
||||
"graceOnInterestPayment", "graceOnInterestCharged", "interestRatePerPeriod", "minInterestRatePerPeriod",
|
||||
"maxInterestRatePerPeriod", "interestRateFrequencyType", "annualInterestRate", "amortizationType", "interestType",
|
||||
"interestCalculationPeriodType", "inArrearsTolerance", "transactionProcessingStrategyId", "transactionProcessingStrategyName",
|
||||
"charges", "accountingRule", "accountingMappings", "paymentChannelToFundSourceMappings", "fundOptions", "paymentTypeOptions",
|
||||
"charges", "accountingRule", "externalId", "accountingMappings", "paymentChannelToFundSourceMappings", "fundOptions", "paymentTypeOptions",
|
||||
"currencyOptions", "repaymentFrequencyTypeOptions", "interestRateFrequencyTypeOptions", "amortizationTypeOptions",
|
||||
"interestTypeOptions", "interestCalculationPeriodTypeOptions", "transactionProcessingStrategyOptions", "chargeOptions",
|
||||
"accountingOptions", "accountingRuleOptions", "accountingMappingOptions"));
|
||||
|
||||
+10
-4
@@ -42,6 +42,7 @@ public class LoanProductData {
|
||||
private final LocalDate startDate;
|
||||
private final LocalDate closeDate;
|
||||
private final String status;
|
||||
private final String externalId;
|
||||
// terms
|
||||
private final CurrencyData currency;
|
||||
private final BigDecimal principal;
|
||||
@@ -135,12 +136,13 @@ public class LoanProductData {
|
||||
final LocalDate startDate = null;
|
||||
final LocalDate closeDate = null;
|
||||
final String status = null;
|
||||
final String externalId = null;
|
||||
return new LoanProductData(id, name, description, currency, principal, minPrincipal, maxPrincipal, tolerance, numberOfRepayments,
|
||||
minNumberOfRepayments, maxNumberOfRepayments, repaymentEvery, interestRatePerPeriod, minInterestRatePerPeriod,
|
||||
maxInterestRatePerPeriod, annualInterestRate, repaymentFrequencyType, interestRateFrequencyType, amortizationType,
|
||||
interestType, interestCalculationPeriodType, fundId, fundName, transactionProcessingStrategyId,
|
||||
transactionProcessingStrategyName, graceOnPrincipalPayment, graceOnInterestPayment, graceOnInterestCharged, charges,
|
||||
accountingType, includeInBorrowerCycle, startDate, closeDate, status);
|
||||
accountingType, includeInBorrowerCycle, startDate, closeDate, status, externalId);
|
||||
}
|
||||
|
||||
public static LoanProductData lookupWithCurrency(final Long id, final String name, final CurrencyData currency) {
|
||||
@@ -176,13 +178,14 @@ public class LoanProductData {
|
||||
final LocalDate startDate = null;
|
||||
final LocalDate closeDate = null;
|
||||
final String status = null;
|
||||
final String externalId = null;
|
||||
|
||||
return new LoanProductData(id, name, description, currency, principal, minPrincipal, maxPrincipal, tolerance, numberOfRepayments,
|
||||
minNumberOfRepayments, maxNumberOfRepayments, repaymentEvery, interestRatePerPeriod, minInterestRatePerPeriod,
|
||||
maxInterestRatePerPeriod, annualInterestRate, repaymentFrequencyType, interestRateFrequencyType, amortizationType,
|
||||
interestType, interestCalculationPeriodType, fundId, fundName, transactionProcessingStrategyId,
|
||||
transactionProcessingStrategyName, graceOnPrincipalPayment, graceOnInterestPayment, graceOnInterestCharged, charges,
|
||||
accountingType, includeInBorrowerCycle, startDate, closeDate, status);
|
||||
accountingType, includeInBorrowerCycle, startDate, closeDate, status, externalId);
|
||||
}
|
||||
|
||||
public static LoanProductData sensibleDefaultsForNewLoanProductCreation() {
|
||||
@@ -224,13 +227,14 @@ public class LoanProductData {
|
||||
final LocalDate startDate = null;
|
||||
final LocalDate closeDate = null;
|
||||
final String status = null;
|
||||
final String externalId = null;
|
||||
|
||||
return new LoanProductData(id, name, description, currency, principal, minPrincipal, maxPrincipal, tolerance, numberOfRepayments,
|
||||
minNumberOfRepayments, maxNumberOfRepayments, repaymentEvery, interestRatePerPeriod, minInterestRatePerPeriod,
|
||||
maxInterestRatePerPeriod, annualInterestRate, repaymentFrequencyType, interestRateFrequencyType, amortizationType,
|
||||
interestType, interestCalculationPeriodType, fundId, fundName, transactionProcessingStrategyId,
|
||||
transactionProcessingStrategyName, graceOnPrincipalPayment, graceOnInterestPayment, graceOnInterestCharged, charges,
|
||||
accountingType, includeInBorrowerCycle, startDate, closeDate, status);
|
||||
accountingType, includeInBorrowerCycle, startDate, closeDate, status, externalId);
|
||||
}
|
||||
|
||||
public static LoanProductData withAccountingDetails(final LoanProductData productData, final Map<String, Object> accountingMappings,
|
||||
@@ -254,7 +258,7 @@ public class LoanProductData {
|
||||
final Long transactionProcessingStrategyId, final String transactionProcessingStrategyName,
|
||||
final Integer graceOnPrincipalPayment, final Integer graceOnInterestPayment, final Integer graceOnInterestCharged,
|
||||
final Collection<ChargeData> charges, final EnumOptionData accountingType, final boolean includeInBorrowerCycle,
|
||||
final LocalDate startDate, final LocalDate closeDate, final String status) {
|
||||
final LocalDate startDate, final LocalDate closeDate, final String status, final String externalId) {
|
||||
this.id = id;
|
||||
this.name = name;
|
||||
this.description = description;
|
||||
@@ -289,6 +293,7 @@ public class LoanProductData {
|
||||
this.startDate = startDate;
|
||||
this.closeDate = closeDate;
|
||||
this.status = status;
|
||||
this.externalId = externalId;
|
||||
|
||||
this.chargeOptions = null;
|
||||
this.penaltyOptions = null;
|
||||
@@ -343,6 +348,7 @@ public class LoanProductData {
|
||||
this.startDate = productData.startDate;
|
||||
this.closeDate = productData.closeDate;
|
||||
this.status = productData.status;
|
||||
this.externalId = productData.externalId;
|
||||
|
||||
this.charges = nullIfEmpty(productData.charges());
|
||||
this.accountingRule = productData.accountingRule;
|
||||
|
||||
+22
-3
@@ -47,7 +47,8 @@ import com.google.gson.JsonArray;
|
||||
* They allow for constraints to be added at product level.
|
||||
*/
|
||||
@Entity
|
||||
@Table(name = "m_product_loan", uniqueConstraints = { @UniqueConstraint(columnNames = { "name" }, name = "unq_name") })
|
||||
@Table(name = "m_product_loan", uniqueConstraints = { @UniqueConstraint(columnNames = { "name" }, name = "unq_name"),
|
||||
@UniqueConstraint(columnNames = { "external_id" }, name = "external_id_UNIQUE") })
|
||||
public class LoanProduct extends AbstractPersistable<Long> {
|
||||
|
||||
@ManyToOne
|
||||
@@ -87,6 +88,9 @@ public class LoanProduct extends AbstractPersistable<Long> {
|
||||
@Column(name = "close_date", nullable = true)
|
||||
@Temporal(TemporalType.DATE)
|
||||
private Date closeDate;
|
||||
|
||||
@Column(name = "external_id", length = 100, nullable = true, unique = true)
|
||||
private String externalId;
|
||||
|
||||
public static LoanProduct assembleFromJson(final Fund fund, final LoanTransactionProcessingStrategy loanTransactionProcessingStrategy,
|
||||
final List<Charge> productCharges, final JsonCommand command, final AprCalculator aprCalculator) {
|
||||
@@ -130,12 +134,13 @@ public class LoanProduct extends AbstractPersistable<Long> {
|
||||
|
||||
final LocalDate startDate = command.localDateValueOfParameterNamed("startDate");
|
||||
final LocalDate closeDate = command.localDateValueOfParameterNamed("closeDate");
|
||||
final String externalId = command.stringValueOfParameterNamed("externalId");
|
||||
|
||||
return new LoanProduct(fund, loanTransactionProcessingStrategy, name, description, currency, principal, minPrincipal, maxPrincipal,
|
||||
interestRatePerPeriod, minInterestRatePerPeriod, maxInterestRatePerPeriod, interestFrequencyType, annualInterestRate,
|
||||
interestMethod, interestCalculationPeriodMethod, repaymentEvery, repaymentFrequencyType, numberOfRepayments,
|
||||
minNumberOfRepayments, maxNumberOfRepayments, graceOnPrincipalPayment, graceOnInterestPayment, graceOnInterestCharged,
|
||||
amortizationMethod, inArrearsTolerance, productCharges, accountingRuleType, includeInBorrowerCycle, startDate, closeDate);
|
||||
amortizationMethod, inArrearsTolerance, productCharges, accountingRuleType, includeInBorrowerCycle, startDate, closeDate, externalId);
|
||||
}
|
||||
|
||||
protected LoanProduct() {
|
||||
@@ -155,7 +160,7 @@ public class LoanProduct extends AbstractPersistable<Long> {
|
||||
final Integer graceOnPrincipalPayment, final Integer graceOnInterestPayment, final Integer graceOnInterestCharged,
|
||||
final AmortizationMethod amortizationMethod, final BigDecimal inArrearsTolerance, final List<Charge> charges,
|
||||
final AccountingRuleType accountingRuleType, final boolean includeInBorrowerCycle, final LocalDate startDate,
|
||||
final LocalDate closeDate) {
|
||||
final LocalDate closeDate, final String externalId) {
|
||||
this.fund = fund;
|
||||
this.transactionProcessingStrategy = transactionProcessingStrategy;
|
||||
this.name = name.trim();
|
||||
@@ -192,6 +197,8 @@ public class LoanProduct extends AbstractPersistable<Long> {
|
||||
if (closeDate != null) {
|
||||
this.closeDate = closeDate.toDateMidnight().toDate();
|
||||
}
|
||||
|
||||
this.externalId = externalId;
|
||||
}
|
||||
|
||||
public MonetaryCurrency getCurrency() {
|
||||
@@ -329,6 +336,14 @@ public class LoanProduct extends AbstractPersistable<Long> {
|
||||
this.closeDate = null;
|
||||
}
|
||||
}
|
||||
|
||||
final String externalIdTypeParamName = "externalId";
|
||||
if (command.isChangeInStringParameterNamed(externalIdTypeParamName, this.externalId)) {
|
||||
final String newValue = command.stringValueOfParameterNamed(externalIdTypeParamName);
|
||||
actualChanges.put(accountingTypeParamName, newValue);
|
||||
this.externalId = newValue;
|
||||
}
|
||||
|
||||
return actualChanges;
|
||||
}
|
||||
|
||||
@@ -412,5 +427,9 @@ public class LoanProduct extends AbstractPersistable<Long> {
|
||||
public String productName() {
|
||||
return this.name;
|
||||
}
|
||||
|
||||
public String getExternalId() {
|
||||
return externalId;
|
||||
}
|
||||
|
||||
}
|
||||
+1
-1
@@ -43,7 +43,7 @@ public final class LoanProductDataValidator {
|
||||
"minNumberOfRepayments", "maxNumberOfRepayments", "repaymentFrequencyType", "interestRatePerPeriod",
|
||||
"minInterestRatePerPeriod", "maxInterestRatePerPeriod", "interestRateFrequencyType", "amortizationType", "interestType",
|
||||
"interestCalculationPeriodType", "inArrearsTolerance", "transactionProcessingStrategyId", "graceOnPrincipalPayment",
|
||||
"graceOnInterestPayment", "graceOnInterestCharged", "charges", "accountingRule","includeInBorrowerCycle", "startDate", "closeDate",
|
||||
"graceOnInterestPayment", "graceOnInterestCharged", "charges", "accountingRule","includeInBorrowerCycle", "startDate", "closeDate", "externalId",
|
||||
LOAN_PRODUCT_ACCOUNTING_PARAMS.FEES_RECEIVABLE.getValue(), LOAN_PRODUCT_ACCOUNTING_PARAMS.FUND_SOURCE.getValue(),
|
||||
LOAN_PRODUCT_ACCOUNTING_PARAMS.INCOME_FROM_FEES.getValue(), LOAN_PRODUCT_ACCOUNTING_PARAMS.INCOME_FROM_PENALTIES.getValue(),
|
||||
LOAN_PRODUCT_ACCOUNTING_PARAMS.INTEREST_ON_LOANS.getValue(), LOAN_PRODUCT_ACCOUNTING_PARAMS.INTEREST_RECEIVABLE.getValue(),
|
||||
|
||||
+3
-2
@@ -106,7 +106,7 @@ public class LoanProductReadPlatformServiceImpl implements LoanProductReadPlatfo
|
||||
+ "lp.grace_on_principal_periods as graceOnPrincipalPayment, lp.grace_on_interest_periods as graceOnInterestPayment, lp.grace_interest_free_periods as graceOnInterestCharged,"
|
||||
+ "lp.amortization_method_enum as amortizationMethod, lp.arrearstolerance_amount as tolerance, "
|
||||
+ "lp.accounting_type as accountingType, lp.include_in_borrower_cycle as includeInBorrowerCycle, lp.start_date as startDate, lp.close_date as closeDate, "
|
||||
+ "curr.name as currencyName, curr.internationalized_name_code as currencyNameCode, curr.display_symbol as currencyDisplaySymbol "
|
||||
+ "curr.name as currencyName, curr.internationalized_name_code as currencyNameCode, curr.display_symbol as currencyDisplaySymbol, lp.external_id as externalId "
|
||||
+ " from m_product_loan lp "
|
||||
+ " left join m_fund f on f.id = lp.fund_id"
|
||||
+ " left join ref_loan_transaction_processing_strategy ltps on ltps.id = lp.loan_transaction_strategy_id"
|
||||
@@ -180,13 +180,14 @@ public class LoanProductReadPlatformServiceImpl implements LoanProductReadPlatfo
|
||||
} else {
|
||||
status = "loanProduct.active";
|
||||
}
|
||||
final String externalId = rs.getString("externalId");
|
||||
|
||||
return new LoanProductData(id, name, description, currency, principal, minPrincipal, maxPrincipal, tolerance,
|
||||
numberOfRepayments, minNumberOfRepayments, maxNumberOfRepayments, repaymentEvery, interestRatePerPeriod,
|
||||
minInterestRatePerPeriod, maxInterestRatePerPeriod, annualInterestRate, repaymentFrequencyType,
|
||||
interestRateFrequencyType, amortizationType, interestType, interestCalculationPeriodType, fundId, fundName,
|
||||
transactionStrategyId, transactionStrategyName, graceOnPrincipalPayment, graceOnInterestPayment,
|
||||
graceOnInterestCharged, this.charges, accountingRuleType, includeInBorrowerCycle, startDate, closeDate, status);
|
||||
graceOnInterestCharged, this.charges, accountingRuleType, includeInBorrowerCycle, startDate, closeDate, status, externalId);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+7
-1
@@ -226,7 +226,13 @@ public class LoanProductWritePlatformServiceJpaRepositoryImpl implements LoanPro
|
||||
private void handleDataIntegrityIssues(final JsonCommand command, final DataIntegrityViolationException dve) {
|
||||
|
||||
Throwable realCause = dve.getMostSpecificCause();
|
||||
if (realCause.getMessage().contains("unq_name")) {
|
||||
|
||||
if (realCause.getMessage().contains("external_id")) {
|
||||
|
||||
final String externalId = command.stringValueOfParameterNamed("externalId");
|
||||
throw new PlatformDataIntegrityException("error.msg.product.loan.duplicate.externalId", "Loan Product with externalId `" + externalId
|
||||
+ "` already exists", "externalId", externalId);
|
||||
} else if (realCause.getMessage().contains("unq_name")) {
|
||||
|
||||
final String name = command.stringValueOfParameterNamed("name");
|
||||
throw new PlatformDataIntegrityException("error.msg.product.loan.duplicate.name", "Loan product with name `" + name
|
||||
|
||||
Reference in New Issue
Block a user