feat: update savings product backend changes
This commit is contained in:
File diff suppressed because it is too large
Load Diff
+10109
-2
File diff suppressed because it is too large
Load Diff
+116
@@ -19,7 +19,27 @@
|
||||
package org.apache.fineract.portfolio.savings.domain;
|
||||
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.SAVINGS_ACCOUNT_RESOURCE_NAME;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.accountFacilityConfigParamName;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.accountNoParamName;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.accountStatusParamName;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.guardianClientIdParamName;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.modeOfOperationParamName;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.accountTypeParamName;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.customerSegmentParamName;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.guardianCifNumberParamName;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.guardianNameParamName;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.guardianRelationshipParamName;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.introducerCifNumberParamName;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.introducerIdParamName;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.introducerNameParamName;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.jointHoldersParamName;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.linkedAccountIdParamName;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.linkedAccountNoParamName;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.linkedAccountTypeParamName;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.minorDateOfBirthParamName;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.nomineeParamName;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.specialCategoryParamName;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.weakerSectionParamName;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.allowOverdraftParamName;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.clientIdParamName;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.enforceMinRequiredBalanceParamName;
|
||||
@@ -45,7 +65,10 @@ import static org.apache.fineract.portfolio.savings.SavingsApiConstants.submitte
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.withHoldTaxParamName;
|
||||
import static org.apache.fineract.portfolio.savings.SavingsApiConstants.withdrawalFeeForTransfersParamName;
|
||||
|
||||
import com.google.gson.Gson;
|
||||
import com.google.gson.JsonArray;
|
||||
import com.google.gson.JsonElement;
|
||||
import com.google.gson.JsonObject;
|
||||
import java.math.BigDecimal;
|
||||
import java.time.LocalDate;
|
||||
import java.util.ArrayList;
|
||||
@@ -336,9 +359,102 @@ public class SavingsAccountAssembler {
|
||||
|
||||
account.validateAccountValuesWithProduct();
|
||||
|
||||
// CBS extended fields
|
||||
applyCbsFields(command, element, account);
|
||||
|
||||
return account;
|
||||
}
|
||||
|
||||
private static final Gson GSON = new Gson();
|
||||
|
||||
private void applyCbsFields(final JsonCommand command, final JsonElement element, final SavingsAccount account) {
|
||||
// Product classification
|
||||
final String cbsAccountType = this.fromApiJsonHelper.extractStringNamed(accountTypeParamName, element);
|
||||
if (cbsAccountType != null) account.setCbsAccountType(cbsAccountType);
|
||||
|
||||
final String customerSegment = this.fromApiJsonHelper.extractStringNamed(customerSegmentParamName, element);
|
||||
if (customerSegment != null) account.setCustomerSegment(customerSegment);
|
||||
|
||||
// Status of Account
|
||||
final String accountStatus = this.fromApiJsonHelper.extractStringNamed(accountStatusParamName, element);
|
||||
if (accountStatus != null) account.setAccountStatus(accountStatus);
|
||||
|
||||
final String modeOfOperation = this.fromApiJsonHelper.extractStringNamed(modeOfOperationParamName, element);
|
||||
if (modeOfOperation != null) account.setModeOfOperation(modeOfOperation);
|
||||
|
||||
account.setSpecialCategory(this.fromApiJsonHelper.extractStringNamed(specialCategoryParamName, element));
|
||||
account.setWeakerSection(this.fromApiJsonHelper.extractStringNamed(weakerSectionParamName, element));
|
||||
account.setGuardianName(this.fromApiJsonHelper.extractStringNamed(guardianNameParamName, element));
|
||||
account.setGuardianCifNumber(this.fromApiJsonHelper.extractStringNamed(guardianCifNumberParamName, element));
|
||||
account.setGuardianRelationship(this.fromApiJsonHelper.extractStringNamed(guardianRelationshipParamName, element));
|
||||
|
||||
if (command.parameterExists(minorDateOfBirthParamName)) {
|
||||
final LocalDate minorDob = this.fromApiJsonHelper.extractLocalDateNamed(minorDateOfBirthParamName, element);
|
||||
account.setMinorDateOfBirth(minorDob);
|
||||
}
|
||||
|
||||
final Long guardianClientId = this.fromApiJsonHelper.extractLongNamed(guardianClientIdParamName, element);
|
||||
if (guardianClientId != null) account.setGuardianClientId(guardianClientId);
|
||||
|
||||
// Introducer
|
||||
final Long introducerId = this.fromApiJsonHelper.extractLongNamed(introducerIdParamName, element);
|
||||
if (introducerId != null) account.setIntroducerClientId(introducerId);
|
||||
account.setIntroducerName(this.fromApiJsonHelper.extractStringNamed(introducerNameParamName, element));
|
||||
account.setIntroducerCifNumber(this.fromApiJsonHelper.extractStringNamed(introducerCifNumberParamName, element));
|
||||
|
||||
// Nominee (stored as JSON string)
|
||||
if (element.getAsJsonObject().has(nomineeParamName)) {
|
||||
final JsonElement nomineeEl = element.getAsJsonObject().get(nomineeParamName);
|
||||
if (nomineeEl != null && !nomineeEl.isJsonNull()) {
|
||||
account.setNomineeData(nomineeEl.toString());
|
||||
}
|
||||
}
|
||||
|
||||
// Deposit Account Link
|
||||
final Long linkedAccountId = this.fromApiJsonHelper.extractLongNamed(linkedAccountIdParamName, element);
|
||||
if (linkedAccountId != null) account.setLinkedAccountId(linkedAccountId);
|
||||
account.setLinkedAccountType(this.fromApiJsonHelper.extractStringNamed(linkedAccountTypeParamName, element));
|
||||
account.setLinkedAccountNo(this.fromApiJsonHelper.extractStringNamed(linkedAccountNoParamName, element));
|
||||
|
||||
// Account Facility Config
|
||||
if (element.getAsJsonObject().has(accountFacilityConfigParamName)) {
|
||||
final JsonElement configEl = element.getAsJsonObject().get(accountFacilityConfigParamName);
|
||||
if (configEl != null && !configEl.isJsonNull() && configEl.isJsonObject()) {
|
||||
SavingsAccountFacilityConfig facilityConfig = account.getFacilityConfig();
|
||||
if (facilityConfig == null) {
|
||||
facilityConfig = new SavingsAccountFacilityConfig(account);
|
||||
account.setFacilityConfig(facilityConfig);
|
||||
}
|
||||
facilityConfig.updateFrom(configEl.getAsJsonObject());
|
||||
}
|
||||
}
|
||||
|
||||
// Joint holders
|
||||
if (element.getAsJsonObject().has(jointHoldersParamName)) {
|
||||
final JsonElement holdersEl = element.getAsJsonObject().get(jointHoldersParamName);
|
||||
if (holdersEl != null && !holdersEl.isJsonNull() && holdersEl.isJsonArray()) {
|
||||
final com.google.gson.JsonArray holdersArray = holdersEl.getAsJsonArray();
|
||||
final List<SavingsAccountJointHolder> holders = new ArrayList<>();
|
||||
for (int i = 0; i < holdersArray.size(); i++) {
|
||||
final JsonObject h = holdersArray.get(i).getAsJsonObject();
|
||||
final Long clientId = h.has("clientId") && !h.get("clientId").isJsonNull()
|
||||
? h.get("clientId").getAsLong() : null;
|
||||
final String cifNumber = h.has("cifNumber") ? h.get("cifNumber").getAsString() : null;
|
||||
final String displayName = h.has("displayName") ? h.get("displayName").getAsString() : null;
|
||||
final BigDecimal sharePercentage = h.has("sharePercentage") && !h.get("sharePercentage").isJsonNull()
|
||||
? h.get("sharePercentage").getAsBigDecimal() : null;
|
||||
final String signingAuthority = h.has("signingAuthority") ? h.get("signingAuthority").getAsString() : null;
|
||||
final String role = h.has("role") ? h.get("role").getAsString() : null;
|
||||
final boolean isPrimary = h.has("isPrimary") && h.get("isPrimary").getAsBoolean();
|
||||
holders.add(new SavingsAccountJointHolder(account, clientId, cifNumber, displayName,
|
||||
sharePercentage, signingAuthority, role, isPrimary));
|
||||
}
|
||||
account.getJointHolders().clear();
|
||||
account.getJointHolders().addAll(holders);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public SavingsAccount assembleFrom(final Long savingsId, final boolean backdatedTxnsAllowedTill) {
|
||||
SavingsAccount account = this.savingsAccountRepository.findSavingsWithNotFoundDetection(savingsId, backdatedTxnsAllowedTill);
|
||||
return loadTransactionsToSavingsAccount(account, backdatedTxnsAllowedTill);
|
||||
|
||||
+118
-10
@@ -215,7 +215,22 @@ public class SavingsAccountReadPlatformServiceImpl implements SavingsAccountRead
|
||||
try {
|
||||
final String sql = "select " + this.savingAccountMapper.schema() + " where sa.id = ?";
|
||||
|
||||
return this.jdbcTemplate.queryForObject(sql, this.savingAccountMapper, new Object[] { accountId }); // NOSONAR
|
||||
final SavingsAccountData accountData = this.jdbcTemplate.queryForObject(sql, this.savingAccountMapper,
|
||||
new Object[] { accountId }); // NOSONAR
|
||||
|
||||
// Load joint holders
|
||||
if (accountData != null) {
|
||||
final String jointSql = "SELECT jh.id as id, jh.client_id as clientId, jh.cif_number as cifNumber, "
|
||||
+ "jh.display_name as displayName, jh.share_percentage as sharePercentage, "
|
||||
+ "jh.signing_authority as signingAuthority, jh.role as role, jh.is_primary as isPrimary "
|
||||
+ "FROM m_savings_account_joint_holders jh WHERE jh.savings_account_id = ?";
|
||||
final List<java.util.Map<String, Object>> jointHolders = this.jdbcTemplate.queryForList(jointSql, accountId);
|
||||
if (!jointHolders.isEmpty()) {
|
||||
accountData.setJointHolders(jointHolders);
|
||||
}
|
||||
}
|
||||
|
||||
return accountData;
|
||||
} catch (final EmptyResultDataAccessException e) {
|
||||
throw new SavingsAccountNotFoundException(accountId, e);
|
||||
}
|
||||
@@ -763,7 +778,43 @@ public class SavingsAccountReadPlatformServiceImpl implements SavingsAccountRead
|
||||
sqlBuilder.append("sp.is_dormancy_tracking_active as isDormancyTrackingActive, ");
|
||||
sqlBuilder.append("sp.days_to_inactive as daysToInactive, ");
|
||||
sqlBuilder.append("sp.days_to_dormancy as daysToDormancy, ");
|
||||
sqlBuilder.append("sp.days_to_escheat as daysToEscheat ");
|
||||
sqlBuilder.append("sp.days_to_escheat as daysToEscheat, ");
|
||||
// CBS extended fields
|
||||
sqlBuilder.append("sa.cbs_account_type as cbsAccountType, ");
|
||||
sqlBuilder.append("sa.customer_segment as customerSegment, ");
|
||||
sqlBuilder.append("sa.account_status as accountStatus, ");
|
||||
sqlBuilder.append("sa.mode_of_operation as modeOfOperation, ");
|
||||
sqlBuilder.append("sa.special_category as specialCategory, ");
|
||||
sqlBuilder.append("sa.weaker_section as weakerSection, ");
|
||||
sqlBuilder.append("sa.guardian_name as guardianName, ");
|
||||
sqlBuilder.append("sa.guardian_cif_number as guardianCifNumber, ");
|
||||
sqlBuilder.append("sa.guardian_relationship as guardianRelationship, ");
|
||||
sqlBuilder.append("sa.minor_date_of_birth as minorDateOfBirth, ");
|
||||
sqlBuilder.append("sa.guardian_client_id as guardianClientId, ");
|
||||
sqlBuilder.append("sa.introducer_client_id as introducerClientId, ");
|
||||
sqlBuilder.append("sa.introducer_name as introducerName, ");
|
||||
sqlBuilder.append("sa.introducer_cif_number as introducerCifNumber, ");
|
||||
sqlBuilder.append("sa.nominee_data as nomineeData, ");
|
||||
sqlBuilder.append("sa.linked_account_id as linkedAccountId, ");
|
||||
sqlBuilder.append("sa.linked_account_type as linkedAccountType, ");
|
||||
sqlBuilder.append("sa.linked_account_no as linkedAccountNo, ");
|
||||
// Facility config fields
|
||||
sqlBuilder.append("safc.atm_facility as atmFacility, ");
|
||||
sqlBuilder.append("safc.atm_withdrawal_facility as atmWithdrawalFacility, ");
|
||||
sqlBuilder.append("safc.upi_facility as upiFacility, ");
|
||||
sqlBuilder.append("safc.pos_transactions_facility as posTransactionsFacility, ");
|
||||
sqlBuilder.append("safc.cheque_book as chequeBook, ");
|
||||
sqlBuilder.append("safc.imps_facility as impsFacility, ");
|
||||
sqlBuilder.append("safc.sms_alerts as smsAlerts, ");
|
||||
sqlBuilder.append("safc.bbps_facility as bbpsFacility, ");
|
||||
sqlBuilder.append("safc.insurance_cover as insuranceCover, ");
|
||||
sqlBuilder.append("safc.bepg_facility as bepgFacility, ");
|
||||
sqlBuilder.append("safc.neft_facility as neftFacility, ");
|
||||
sqlBuilder.append("safc.rtgs_facility as rtgsFacility, ");
|
||||
sqlBuilder.append("safc.inter_bank_total_cap_facility as interBankTotalCapFacility, ");
|
||||
sqlBuilder.append("safc.withdrawal_facility as withdrawalFacility, ");
|
||||
sqlBuilder.append("safc.deposit_facility_kyc as depositFacilityKyc, ");
|
||||
sqlBuilder.append("safc.virtual_debit_card as virtualDebitCard ");
|
||||
sqlBuilder.append("from m_savings_account sa ");
|
||||
sqlBuilder.append("join m_savings_product sp ON sa.product_id = sp.id ");
|
||||
sqlBuilder.append("join m_currency curr on curr.code = sa.currency_code ");
|
||||
@@ -777,6 +828,7 @@ public class SavingsAccountReadPlatformServiceImpl implements SavingsAccountRead
|
||||
sqlBuilder.append("left join m_appuser avbu on avbu.id = sa.activatedon_userid ");
|
||||
sqlBuilder.append("left join m_appuser cbu on cbu.id = sa.closedon_userid ");
|
||||
sqlBuilder.append("left join m_tax_group tg on tg.id = sa.tax_group_id ");
|
||||
sqlBuilder.append("left join m_savings_account_facility_config safc on safc.savings_account_id = sa.id ");
|
||||
|
||||
this.schemaSql = sqlBuilder.toString();
|
||||
}
|
||||
@@ -970,14 +1022,70 @@ public class SavingsAccountReadPlatformServiceImpl implements SavingsAccountRead
|
||||
taxGroupData = TaxGroupData.lookup(taxGroupId, taxGroupName);
|
||||
}
|
||||
|
||||
return SavingsAccountData.instance(id, accountNo, depositType, externalId, groupId, groupName, clientId, clientName, productId,
|
||||
productName, fieldOfficerId, fieldOfficerName, status, subStatus, reasonForBlock, timeline, currency,
|
||||
nominalAnnualInterestRate, interestCompoundingPeriodType, interestPostingPeriodType, interestCalculationType,
|
||||
interestCalculationDaysInYearType, minRequiredOpeningBalance, lockinPeriodFrequency, lockinPeriodFrequencyType,
|
||||
withdrawalFeeForTransfers, summary, allowOverdraft, overdraftLimit, minRequiredBalance, enforceMinRequiredBalance,
|
||||
maxAllowedLienLimit, lienAllowed, minBalanceForInterestCalculation, onHoldFunds, nominalAnnualInterestRateOverdraft,
|
||||
minOverdraftForInterestCalculation, withHoldTax, taxGroupData, lastActiveTransactionDate, isDormancyTrackingActive,
|
||||
daysToInactive, daysToDormancy, daysToEscheat, onHoldAmount);
|
||||
final SavingsAccountData accountData = SavingsAccountData.instance(id, accountNo, depositType, externalId, groupId, groupName,
|
||||
clientId, clientName, productId, productName, fieldOfficerId, fieldOfficerName, status, subStatus, reasonForBlock,
|
||||
timeline, currency, nominalAnnualInterestRate, interestCompoundingPeriodType, interestPostingPeriodType,
|
||||
interestCalculationType, interestCalculationDaysInYearType, minRequiredOpeningBalance, lockinPeriodFrequency,
|
||||
lockinPeriodFrequencyType, withdrawalFeeForTransfers, summary, allowOverdraft, overdraftLimit, minRequiredBalance,
|
||||
enforceMinRequiredBalance, maxAllowedLienLimit, lienAllowed, minBalanceForInterestCalculation, onHoldFunds,
|
||||
nominalAnnualInterestRateOverdraft, minOverdraftForInterestCalculation, withHoldTax, taxGroupData,
|
||||
lastActiveTransactionDate, isDormancyTrackingActive, daysToInactive, daysToDormancy, daysToEscheat, onHoldAmount);
|
||||
|
||||
// CBS extended fields
|
||||
accountData.setCbsAccountType(rs.getString("cbsAccountType"));
|
||||
accountData.setCustomerSegment(rs.getString("customerSegment"));
|
||||
accountData.setAccountStatus(rs.getString("accountStatus"));
|
||||
accountData.setModeOfOperation(rs.getString("modeOfOperation"));
|
||||
accountData.setSpecialCategory(rs.getString("specialCategory"));
|
||||
accountData.setWeakerSection(rs.getString("weakerSection"));
|
||||
accountData.setGuardianName(rs.getString("guardianName"));
|
||||
accountData.setGuardianCifNumber(rs.getString("guardianCifNumber"));
|
||||
accountData.setGuardianRelationship(rs.getString("guardianRelationship"));
|
||||
accountData.setMinorDateOfBirth(JdbcSupport.getLocalDate(rs, "minorDateOfBirth"));
|
||||
accountData.setGuardianClientId(JdbcSupport.getLong(rs, "guardianClientId"));
|
||||
accountData.setIntroducerClientId(JdbcSupport.getLong(rs, "introducerClientId"));
|
||||
accountData.setIntroducerName(rs.getString("introducerName"));
|
||||
accountData.setIntroducerCifNumber(rs.getString("introducerCifNumber"));
|
||||
accountData.setLinkedAccountId(JdbcSupport.getLong(rs, "linkedAccountId"));
|
||||
accountData.setLinkedAccountType(rs.getString("linkedAccountType"));
|
||||
accountData.setLinkedAccountNo(rs.getString("linkedAccountNo"));
|
||||
|
||||
// Nominee as parsed map
|
||||
final String nomineeDataStr = rs.getString("nomineeData");
|
||||
if (nomineeDataStr != null && !nomineeDataStr.isEmpty()) {
|
||||
try {
|
||||
com.google.gson.Gson gson = new com.google.gson.Gson();
|
||||
@SuppressWarnings("unchecked")
|
||||
java.util.Map<String, Object> nomineeMap = gson.fromJson(nomineeDataStr,
|
||||
new com.google.gson.reflect.TypeToken<java.util.Map<String, Object>>() {}.getType());
|
||||
accountData.setNomineeData(nomineeMap);
|
||||
} catch (Exception ignored) {}
|
||||
}
|
||||
|
||||
// Facility config
|
||||
final boolean hasFacilityConfig = rs.getObject("atmFacility") != null;
|
||||
if (hasFacilityConfig) {
|
||||
final java.util.Map<String, Object> facilityConfigMap = new java.util.LinkedHashMap<>();
|
||||
facilityConfigMap.put("atmFacility", rs.getBoolean("atmFacility"));
|
||||
facilityConfigMap.put("atmWithdrawalFacility", rs.getBoolean("atmWithdrawalFacility"));
|
||||
facilityConfigMap.put("upiFacility", rs.getBoolean("upiFacility"));
|
||||
facilityConfigMap.put("posTransactionsFacility", rs.getBoolean("posTransactionsFacility"));
|
||||
facilityConfigMap.put("chequeBook", rs.getBoolean("chequeBook"));
|
||||
facilityConfigMap.put("impsFacility", rs.getBoolean("impsFacility"));
|
||||
facilityConfigMap.put("smsAlerts", rs.getBoolean("smsAlerts"));
|
||||
facilityConfigMap.put("bbpsFacility", rs.getBoolean("bbpsFacility"));
|
||||
facilityConfigMap.put("insuranceCover", rs.getBoolean("insuranceCover"));
|
||||
facilityConfigMap.put("bepgFacility", rs.getBoolean("bepgFacility"));
|
||||
facilityConfigMap.put("neftFacility", rs.getBoolean("neftFacility"));
|
||||
facilityConfigMap.put("rtgsFacility", rs.getBoolean("rtgsFacility"));
|
||||
facilityConfigMap.put("interBankTotalCapFacility", rs.getBoolean("interBankTotalCapFacility"));
|
||||
facilityConfigMap.put("withdrawalFacility", rs.getBoolean("withdrawalFacility"));
|
||||
facilityConfigMap.put("depositFacilityKyc", rs.getBoolean("depositFacilityKyc"));
|
||||
facilityConfigMap.put("virtualDebitCard", rs.getBoolean("virtualDebitCard"));
|
||||
accountData.setAccountFacilityConfig(facilityConfigMap);
|
||||
}
|
||||
|
||||
return accountData;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
+2
@@ -263,6 +263,8 @@
|
||||
<class>org.apache.fineract.portfolio.savings.domain.SavingsProductDepositLimitKyc</class>
|
||||
<class>org.apache.fineract.portfolio.savings.domain.SavingsProductFacilityConfig</class>
|
||||
<class>org.apache.fineract.portfolio.savings.domain.SavingsProductFacilityLimit</class>
|
||||
<class>org.apache.fineract.portfolio.savings.domain.SavingsAccountFacilityConfig</class>
|
||||
<class>org.apache.fineract.portfolio.savings.domain.SavingsAccountJointHolder</class>
|
||||
|
||||
<!-- Progressive Loan Module Entities -->
|
||||
<class>org.apache.fineract.portfolio.loanaccount.domain.LoanCapitalizedIncomeBalance</class>
|
||||
|
||||
Reference in New Issue
Block a user