FINERACT-1396: Bulk Import Feature

This commit is contained in:
xurror
2021-10-09 09:03:44 +08:00
committed by Petri Tuomola
parent d2521886ba
commit 0b51ab2429
13 changed files with 468 additions and 41 deletions
@@ -0,0 +1,34 @@
/**
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
package org.apache.fineract.infrastructure.bulkimport.constants;
public final class ChargeConstants {
private ChargeConstants() {
}
// Column indices
public static final int CHARGE_NAME_COL = 1;
public static final int CHARGE_AMOUNT_COL = 2;
public static final int CHARGE_CALCULATION_TYPE_COL = 3;
// public static final int CHARGE_DUE_DATE_COL = 4;
public static final int CHARGE_TIME_TYPE_COL = 4;
}
@@ -60,10 +60,11 @@ public final class LoanConstants {
public static final int LOAN_ID_COL = 33;// AH
public static final int FAILURE_REPORT_COL = 34;// AI
public static final int EXTERNAL_ID_COL = 35;// AJ
public static final int CHARGE_ID_1 = 36;// AK
public static final int CHARGE_NAME_1 = 36;// AK
public static final int CHARGE_AMOUNT_1 = 37;// AL
public static final int CHARGE_DUE_DATE_1 = 38;// AM
public static final int CHARGE_ID_2 = 39;// AN
public static final int CHARGE_NAME_2 = 39;// AO
public static final int CHARGE_AMOUNT_2 = 40;// AO
public static final int CHARGE_DUE_DATE_2 = 41;// AP
public static final int GROUP_ID = 42;// AQ
@@ -71,8 +72,10 @@ public final class LoanConstants {
public static final int LOOKUP_CLIENT_EXTERNAL_ID = 44;// AS
public static final int LOOKUP_ACTIVATION_DATE_COL = 45;// AT
public static final int LINK_ACCOUNT_ID = 46;// AU
public static final int LOAN_COLLATERAL_ID = 47;
public static final int LOAN_COLLATERAL_QUANTITY = 48;
public static final int LOAN_COLLATERAL_ID = 47;// AV
public static final int LOAN_COLLATERAL_QUANTITY = 48;// AW
public static final int CHARGE_AMOUNT_TYPE_1 = 49;// AX
public static final int CHARGE_AMOUNT_TYPE_2 = 50;// AY
public static final String LOAN_TYPE_INDIVIDUAL = "Individual";
public static final String LOAN_TYPE_GROUP = "Group";
@@ -35,6 +35,7 @@ public final class TemplatePopulateImportConstants {
public static final String CENTER_SHEET_NAME = "Centers";
public static final String STAFF_SHEET_NAME = "Staff";
public static final String GROUP_SHEET_NAME = "Groups";
public static final String CHARGE_SHEET_NAME = "Charges";
public static final String CHART_OF_ACCOUNTS_SHEET_NAME = "ChartOfAccounts";
public static final String CLIENT_ENTITY_SHEET_NAME = "ClientEntity";
public static final String CLIENT_PERSON_SHEET_NAME = "ClientPerson";
@@ -24,6 +24,7 @@ import java.time.LocalDate;
import java.util.List;
import org.apache.fineract.infrastructure.bulkimport.constants.TemplatePopulateImportConstants;
import org.apache.fineract.infrastructure.core.data.ApiParameterError;
import org.apache.fineract.infrastructure.core.data.EnumOptionData;
import org.apache.fineract.infrastructure.core.exception.AbstractPlatformException;
import org.apache.fineract.infrastructure.core.exception.UnsupportedParameterException;
import org.apache.fineract.infrastructure.core.service.DateUtils;
@@ -304,6 +305,7 @@ public final class ImportHandlerUtils {
if (sheetName.equals(TemplatePopulateImportConstants.OFFICE_SHEET_NAME)
|| sheetName.equals(TemplatePopulateImportConstants.GL_ACCOUNTS_SHEET_NAME)
|| sheetName.equals(TemplatePopulateImportConstants.EXTRAS_SHEET_NAME)
|| sheetName.equals(TemplatePopulateImportConstants.CHARGE_SHEET_NAME)
|| sheetName.equals(TemplatePopulateImportConstants.SHARED_PRODUCTS_SHEET_NAME)
|| sheetName.equals(TemplatePopulateImportConstants.ROLES_SHEET_NAME)) {
if (row.getCell(cell.getColumnIndex() - 1).getCellType() == CellType.NUMERIC) {
@@ -342,6 +344,48 @@ public final class ImportHandlerUtils {
return 0L;
}
public static EnumOptionData getChargeTimeTypeEmun(Sheet sheet, String name) {
String sheetName = sheet.getSheetName();
String chargeTimeType = "";
EnumOptionData chargeTimeTypeEnum = null;
if (sheetName.equals(TemplatePopulateImportConstants.CHARGE_SHEET_NAME)) {
for (Row row : sheet) {
for (Cell cell : row) {
if (name != null) {
if (cell.getCellType() == CellType.STRING && cell.getRichStringCellValue().getString().trim().equals(name)) {
chargeTimeType = row.getCell(cell.getColumnIndex() + 3).getStringCellValue().toString();
}
}
}
}
}
if (!chargeTimeType.equals("")) {
String chargeTimeTypeId = "";
if (chargeTimeType.equalsIgnoreCase("Disbursement")) {
chargeTimeTypeId = "1";
}
chargeTimeTypeEnum = new EnumOptionData(null, null, chargeTimeTypeId);
}
return chargeTimeTypeEnum;
}
public static EnumOptionData getChargeAmountTypeEnum(final String chargeAmountType) {
EnumOptionData chargeAmountTypeEnum = null;
if (chargeAmountType != null) {
String chargeAmountTypeId = "";
if (chargeAmountType.equalsIgnoreCase("Flat")) {
chargeAmountTypeId = "1";
} else if (chargeAmountType.equalsIgnoreCase("% Amount")) {
chargeAmountTypeId = "2";
} else {
chargeAmountTypeId = chargeAmountType;
}
chargeAmountTypeEnum = new EnumOptionData(null, null, chargeAmountTypeId);
}
return chargeAmountTypeEnum;
}
public static String getCodeByName(Sheet sheet, String name) {
String sheetName = sheet.getSheetName();
if (sheetName.equals(TemplatePopulateImportConstants.EXTRAS_SHEET_NAME)) {
@@ -45,6 +45,7 @@ import org.apache.fineract.portfolio.loanaccount.data.LoanApprovalData;
import org.apache.fineract.portfolio.loanaccount.data.LoanChargeData;
import org.apache.fineract.portfolio.loanaccount.data.LoanCollateralManagementData;
import org.apache.fineract.portfolio.loanaccount.data.LoanTransactionData;
import org.apache.fineract.portfolio.loanaccount.domain.LoanCharge;
import org.apache.fineract.portfolio.loanaccount.exception.InvalidAmountOfCollateralQuantity;
import org.apache.poi.ss.usermodel.Cell;
import org.apache.poi.ss.usermodel.IndexedColors;
@@ -174,19 +175,21 @@ public class LoanImportHandler implements ImportHandler {
repaidEveryFrequencyId = "1";
} else if (repaidEveryFrequency.equalsIgnoreCase("Months")) {
repaidEveryFrequencyId = "2";
} else if (repaidEveryFrequency.equalsIgnoreCase("Semi Month")) {
repaidEveryFrequencyId = "5";
}
repaidEveryFrequencyEnums = new EnumOptionData(null, null, repaidEveryFrequencyId);
}
Integer loanTerm = ImportHandlerUtils.readAsInt(LoanConstants.LOAN_TERM_COL, row);
String loanTermFrequency = ImportHandlerUtils.readAsString(LoanConstants.LOAN_TERM_FREQUENCY_COL, row);
String loanTermFrequencyType = ImportHandlerUtils.readAsString(LoanConstants.LOAN_TERM_FREQUENCY_COL, row);
EnumOptionData loanTermFrequencyEnum = null;
if (loanTermFrequency != null) {
if (loanTermFrequencyType != null) {
String loanTermFrequencyId = "";
if (loanTermFrequency.equalsIgnoreCase("Days")) {
if (loanTermFrequencyType.equalsIgnoreCase("Days")) {
loanTermFrequencyId = "0";
} else if (loanTermFrequency.equalsIgnoreCase("Weeks")) {
} else if (loanTermFrequencyType.equalsIgnoreCase("Weeks")) {
loanTermFrequencyId = "1";
} else if (loanTermFrequency.equalsIgnoreCase("Months")) {
} else if (loanTermFrequencyType.equalsIgnoreCase("Months")) {
loanTermFrequencyId = "2";
}
loanTermFrequencyEnum = new EnumOptionData(null, null, loanTermFrequencyId);
@@ -269,8 +272,19 @@ public class LoanImportHandler implements ImportHandler {
List<LoanChargeData> charges = new ArrayList<>();
Long charge1 = ImportHandlerUtils.readAsLong(LoanConstants.CHARGE_ID_1, row);
Long charge2 = ImportHandlerUtils.readAsLong(LoanConstants.CHARGE_ID_2, row);
String chargeOneName = ImportHandlerUtils.readAsString(LoanConstants.CHARGE_NAME_1, row);
String chargeTwoName = ImportHandlerUtils.readAsString(LoanConstants.CHARGE_NAME_2, row);
Long chargeOneId = null;
if (chargeOneName != null) {
chargeOneId = ImportHandlerUtils.getIdByName(workbook.getSheet(TemplatePopulateImportConstants.CHARGE_SHEET_NAME),
chargeOneName);
}
Long chargeTwoId = null;
if (chargeTwoName != null) {
chargeTwoId = ImportHandlerUtils.getIdByName(workbook.getSheet(TemplatePopulateImportConstants.CHARGE_SHEET_NAME),
chargeTwoName);
}
Long collateralId = ImportHandlerUtils.readAsLong(LoanConstants.LOAN_COLLATERAL_ID, row);
@@ -278,25 +292,47 @@ public class LoanImportHandler implements ImportHandler {
String linkAccountId = ImportHandlerUtils.readAsString(LoanConstants.LINK_ACCOUNT_ID, row);
if (charge1 != null) {
if (chargeOneId != null) {
if (ImportHandlerUtils.readAsDouble(LoanConstants.CHARGE_AMOUNT_1, row) != null) {
charges.add(new LoanChargeData(ImportHandlerUtils.readAsLong(LoanConstants.CHARGE_ID_1, row),
ImportHandlerUtils.readAsDate(LoanConstants.CHARGE_DUE_DATE_1, row),
BigDecimal.valueOf(ImportHandlerUtils.readAsDouble(LoanConstants.CHARGE_AMOUNT_1, row))));
EnumOptionData chargeOneTimeTypeEnum = ImportHandlerUtils
.getChargeTimeTypeEmun(workbook.getSheet(TemplatePopulateImportConstants.CHARGE_SHEET_NAME), chargeOneName);
EnumOptionData chargeOneAmountTypeEnum = ImportHandlerUtils
.getChargeAmountTypeEnum(ImportHandlerUtils.readAsString(LoanConstants.CHARGE_AMOUNT_TYPE_1, row));
BigDecimal chargeAmount;
BigDecimal amountOrPercentage = BigDecimal.valueOf(ImportHandlerUtils.readAsDouble(LoanConstants.CHARGE_AMOUNT_1, row));
if (chargeOneAmountTypeEnum.getValue().equalsIgnoreCase("1")) {
chargeAmount = amountOrPercentage;
} else {
chargeAmount = LoanCharge.percentageOf(principal, amountOrPercentage);
}
charges.add(new LoanChargeData(chargeOneId, ImportHandlerUtils.readAsDate(LoanConstants.CHARGE_DUE_DATE_1, row),
chargeAmount, chargeOneAmountTypeEnum, chargeOneTimeTypeEnum));
} else {
charges.add(new LoanChargeData(ImportHandlerUtils.readAsLong(LoanConstants.CHARGE_ID_1, row),
ImportHandlerUtils.readAsDate(LoanConstants.CHARGE_DUE_DATE_1, row), null));
charges.add(new LoanChargeData(chargeOneId, ImportHandlerUtils.readAsDate(LoanConstants.CHARGE_DUE_DATE_1, row), null));
}
}
if (charge2 != null) {
if (chargeTwoId != null) {
if (ImportHandlerUtils.readAsDouble(LoanConstants.CHARGE_AMOUNT_2, row) != null) {
charges.add(new LoanChargeData(ImportHandlerUtils.readAsLong(LoanConstants.CHARGE_ID_2, row),
ImportHandlerUtils.readAsDate(LoanConstants.CHARGE_DUE_DATE_2, row),
BigDecimal.valueOf(ImportHandlerUtils.readAsDouble(LoanConstants.CHARGE_AMOUNT_2, row))));
EnumOptionData chargeTwoTimeTypeEnum = ImportHandlerUtils
.getChargeTimeTypeEmun(workbook.getSheet(TemplatePopulateImportConstants.CHARGE_SHEET_NAME), chargeTwoName);
EnumOptionData chargeTwoAmountTypeEnum = ImportHandlerUtils
.getChargeAmountTypeEnum(ImportHandlerUtils.readAsString(LoanConstants.CHARGE_AMOUNT_TYPE_2, row));
BigDecimal chargeAmount;
BigDecimal amountOrPercentage = BigDecimal.valueOf(ImportHandlerUtils.readAsDouble(LoanConstants.CHARGE_AMOUNT_2, row));
if (chargeTwoTimeTypeEnum.getValue().equalsIgnoreCase("1")) {
chargeAmount = amountOrPercentage;
} else {
chargeAmount = LoanCharge.percentageOf(principal, amountOrPercentage);
}
charges.add(new LoanChargeData(chargeTwoId, ImportHandlerUtils.readAsDate(LoanConstants.CHARGE_DUE_DATE_2, row),
chargeAmount, chargeTwoAmountTypeEnum, chargeTwoTimeTypeEnum));
} else {
charges.add(new LoanChargeData(ImportHandlerUtils.readAsLong(LoanConstants.CHARGE_ID_2, row),
ImportHandlerUtils.readAsDate(LoanConstants.CHARGE_DUE_DATE_2, row), null));
charges.add(new LoanChargeData(chargeTwoId, ImportHandlerUtils.readAsDate(LoanConstants.CHARGE_DUE_DATE_2, row), null));
}
}
@@ -313,6 +349,7 @@ public class LoanImportHandler implements ImportHandler {
}
statuses.add(status);
if (loanType != null) {
if (loanType.equals("individual")) {
Long clientId = ImportHandlerUtils.getIdByName(workbook.getSheet(TemplatePopulateImportConstants.CLIENT_SHEET_NAME),
@@ -0,0 +1,86 @@
/**
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
package org.apache.fineract.infrastructure.bulkimport.populator;
import java.util.List;
import org.apache.fineract.infrastructure.bulkimport.constants.ChargeConstants;
import org.apache.fineract.infrastructure.bulkimport.constants.TemplatePopulateImportConstants;
import org.apache.fineract.portfolio.charge.data.ChargeData;
import org.apache.poi.ss.usermodel.Row;
import org.apache.poi.ss.usermodel.Sheet;
import org.apache.poi.ss.usermodel.Workbook;
public class ChargeSheetPopulator extends AbstractWorkbookPopulator {
private List<ChargeData> charges;
private static final int ID_COL = 0;
public ChargeSheetPopulator(final List<ChargeData> charges) {
this.charges = charges;
}
@Override
public void populate(final Workbook workbook, String dateFormat) {
int rowIndex = 1;
Sheet chargeSheet = workbook.createSheet(TemplatePopulateImportConstants.CHARGE_SHEET_NAME);
setLayout(chargeSheet);
populateCharges(chargeSheet, rowIndex);
chargeSheet.protectSheet("");
}
private void populateCharges(Sheet chargeSheet, int rowIndex) {
for (ChargeData charge : charges) {
Row row = chargeSheet.createRow(rowIndex);
writeLong(ID_COL, row, charge.getId());
writeString(ChargeConstants.CHARGE_NAME_COL, row, charge.getName().trim().replaceAll("[ )(]", "_"));
writeBigDecimal(ChargeConstants.CHARGE_AMOUNT_COL, row, charge.getAmount());
writeString(ChargeConstants.CHARGE_CALCULATION_TYPE_COL, row, charge.getChargeCalculationType().getValue());
writeString(ChargeConstants.CHARGE_TIME_TYPE_COL, row, charge.getChargeTimeType().getValue());
rowIndex++;
}
}
private void setLayout(Sheet worksheet) {
worksheet.setColumnWidth(ID_COL, TemplatePopulateImportConstants.SMALL_COL_SIZE);
worksheet.setColumnWidth(ChargeConstants.CHARGE_NAME_COL, TemplatePopulateImportConstants.MEDIUM_COL_SIZE);
worksheet.setColumnWidth(ChargeConstants.CHARGE_AMOUNT_COL, TemplatePopulateImportConstants.SMALL_COL_SIZE);
worksheet.setColumnWidth(ChargeConstants.CHARGE_CALCULATION_TYPE_COL, TemplatePopulateImportConstants.MEDIUM_COL_SIZE);
worksheet.setColumnWidth(ChargeConstants.CHARGE_TIME_TYPE_COL, TemplatePopulateImportConstants.MEDIUM_COL_SIZE);
Row rowHeader = worksheet.createRow(TemplatePopulateImportConstants.ROWHEADER_INDEX);
rowHeader.setHeight(TemplatePopulateImportConstants.ROW_HEADER_HEIGHT);
writeString(ID_COL, rowHeader, "ID");
writeString(ChargeConstants.CHARGE_NAME_COL, rowHeader, "Name");
writeString(ChargeConstants.CHARGE_AMOUNT_COL, rowHeader, "Charge Amount");
writeString(ChargeConstants.CHARGE_CALCULATION_TYPE_COL, rowHeader, "Charge Calculation Type");
writeString(ChargeConstants.CHARGE_TIME_TYPE_COL, rowHeader, "Charge Time Type");
}
public Integer getChargesSize() {
return charges.size();
}
public List<ChargeData> getCharges() {
return charges;
}
}
@@ -86,7 +86,12 @@ public class LoanProductSheetPopulator extends AbstractWorkbookPopulator {
} else {
writeInt(MAX_PRINCIPAL_COL, row, 999999999);
}
writeInt(NO_OF_REPAYMENTS_COL, row, product.getNumberOfRepayments());
int numberOfRepayments = product.getNumberOfRepayments();
if (product.getRepaymentFrequencyType().getValue().equalsIgnoreCase("Semi Month")) {
numberOfRepayments = numberOfRepayments * product.getRepaymentEvery();
}
writeInt(NO_OF_REPAYMENTS_COL, row, numberOfRepayments);
if (product.getMinNumberOfRepayments() != null) {
writeInt(MIN_REPAYMENTS_COL, row, product.getMinNumberOfRepayments());
} else {
@@ -0,0 +1,74 @@
/**
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
package org.apache.fineract.infrastructure.bulkimport.populator.charge;
import org.apache.fineract.infrastructure.bulkimport.constants.ChargeConstants;
import org.apache.fineract.infrastructure.bulkimport.constants.TemplatePopulateImportConstants;
import org.apache.fineract.infrastructure.bulkimport.populator.AbstractWorkbookPopulator;
import org.apache.poi.ss.usermodel.Row;
import org.apache.poi.ss.usermodel.Sheet;
import org.apache.poi.ss.usermodel.Workbook;
public class ChargeWorkbookPopulator extends AbstractWorkbookPopulator {
public ChargeWorkbookPopulator() {
//
}
@Override
public void populate(Workbook workbook, String dateFormat) {
Sheet chargeSheet = workbook.createSheet(TemplatePopulateImportConstants.CHARGE_SHEET_NAME);
setLayout(chargeSheet);
// setRules(chargeSheet, dateFormat);
}
private void setLayout(final Sheet worksheet) {
Row rowHeader = worksheet.createRow(TemplatePopulateImportConstants.ROWHEADER_INDEX);
worksheet.setColumnWidth(0, TemplatePopulateImportConstants.SMALL_COL_SIZE);
worksheet.setColumnWidth(ChargeConstants.CHARGE_NAME_COL, TemplatePopulateImportConstants.SMALL_COL_SIZE);
worksheet.setColumnWidth(ChargeConstants.CHARGE_AMOUNT_COL, TemplatePopulateImportConstants.MEDIUM_COL_SIZE);
worksheet.setColumnWidth(ChargeConstants.CHARGE_CALCULATION_TYPE_COL, TemplatePopulateImportConstants.MEDIUM_COL_SIZE);
// worksheet.setColumnWidth(ChargeConstants.CHARGE_DUE_DATE_COL,
// TemplatePopulateImportConstants.MEDIUM_COL_SIZE);
worksheet.setColumnWidth(ChargeConstants.CHARGE_TIME_TYPE_COL, TemplatePopulateImportConstants.MEDIUM_COL_SIZE);
writeString(0, rowHeader, "ID");
writeString(ChargeConstants.CHARGE_NAME_COL, rowHeader, "Charge Name*");
writeString(ChargeConstants.CHARGE_AMOUNT_COL, rowHeader, "Charge Amount*");
writeString(ChargeConstants.CHARGE_CALCULATION_TYPE_COL, rowHeader, "Charge Calculation Type*");
// writeString(ChargeConstants.CHARGE_DUE_DATE_COL, rowHeader, "Charge Due Date*");
writeString(ChargeConstants.CHARGE_TIME_TYPE_COL, rowHeader, "Charge Time Type*");
}
@SuppressWarnings("unused")
private void setRules(Sheet workSheet, final String dateFormat) {
// CellRangeAddressList dueDateRange = new CellRangeAddressList(1, SpreadsheetVersion.EXCEL97.getLastRowIndex(),
// ChargeConstants.CHARGE_DUE_DATE_COL, ChargeConstants.CHARGE_DUE_DATE_COL);
// DataValidationHelper validationHelper = new HSSFDataValidationHelper((HSSFSheet) workSheet);
// DataValidationConstraint dueDateConstraint = validationHelper
// .createDateConstraint(DataValidationConstraint.OperatorType.GREATER_OR_EQUAL, "=TODAY()", null, dateFormat);
// DataValidation dueDateValidation = validationHelper.createValidation(dueDateConstraint, dueDateRange);
// workSheet.addValidationData(dueDateValidation);
}
}
@@ -22,12 +22,14 @@ import java.util.List;
import org.apache.fineract.infrastructure.bulkimport.constants.LoanConstants;
import org.apache.fineract.infrastructure.bulkimport.constants.TemplatePopulateImportConstants;
import org.apache.fineract.infrastructure.bulkimport.populator.AbstractWorkbookPopulator;
import org.apache.fineract.infrastructure.bulkimport.populator.ChargeSheetPopulator;
import org.apache.fineract.infrastructure.bulkimport.populator.ClientSheetPopulator;
import org.apache.fineract.infrastructure.bulkimport.populator.ExtrasSheetPopulator;
import org.apache.fineract.infrastructure.bulkimport.populator.GroupSheetPopulator;
import org.apache.fineract.infrastructure.bulkimport.populator.LoanProductSheetPopulator;
import org.apache.fineract.infrastructure.bulkimport.populator.OfficeSheetPopulator;
import org.apache.fineract.infrastructure.bulkimport.populator.PersonnelSheetPopulator;
import org.apache.fineract.portfolio.charge.data.ChargeData;
import org.apache.fineract.portfolio.loanproduct.data.LoanProductData;
import org.apache.poi.hssf.usermodel.HSSFDataValidationHelper;
import org.apache.poi.hssf.usermodel.HSSFSheet;
@@ -46,22 +48,25 @@ import org.apache.poi.ss.util.CellRangeAddressList;
public class LoanWorkbookPopulator extends AbstractWorkbookPopulator {
private final OfficeSheetPopulator officeSheetPopulator;
private final ClientSheetPopulator clientSheetPopulator;
private final GroupSheetPopulator groupSheetPopulator;
private final PersonnelSheetPopulator personnelSheetPopulator;
private final LoanProductSheetPopulator productSheetPopulator;
private final ExtrasSheetPopulator extrasSheetPopulator;
private OfficeSheetPopulator officeSheetPopulator;
private ClientSheetPopulator clientSheetPopulator;
private GroupSheetPopulator groupSheetPopulator;
private PersonnelSheetPopulator personnelSheetPopulator;
private LoanProductSheetPopulator productSheetPopulator;
private ChargeSheetPopulator chargeSheetPopulator;
private ExtrasSheetPopulator extrasSheetPopulator;
public LoanWorkbookPopulator(OfficeSheetPopulator officeSheetPopulator, ClientSheetPopulator clientSheetPopulator,
GroupSheetPopulator groupSheetPopulator, PersonnelSheetPopulator personnelSheetPopulator,
LoanProductSheetPopulator productSheetPopulator, ExtrasSheetPopulator extrasSheetPopulator) {
LoanProductSheetPopulator productSheetPopulator, ChargeSheetPopulator chargeSheetPopulator,
ExtrasSheetPopulator extrasSheetPopulator) {
this.officeSheetPopulator = officeSheetPopulator;
this.clientSheetPopulator = clientSheetPopulator;
this.groupSheetPopulator = groupSheetPopulator;
this.personnelSheetPopulator = personnelSheetPopulator;
this.productSheetPopulator = productSheetPopulator;
this.extrasSheetPopulator = extrasSheetPopulator;
this.chargeSheetPopulator = chargeSheetPopulator;
}
@Override
@@ -72,6 +77,7 @@ public class LoanWorkbookPopulator extends AbstractWorkbookPopulator {
groupSheetPopulator.populate(workbook, dateFormat);
personnelSheetPopulator.populate(workbook, dateFormat);
productSheetPopulator.populate(workbook, dateFormat);
chargeSheetPopulator.populate(workbook, dateFormat);
extrasSheetPopulator.populate(workbook, dateFormat);
setLayout(loanSheet);
setRules(loanSheet, dateFormat);
@@ -138,6 +144,16 @@ public class LoanWorkbookPopulator extends AbstractWorkbookPopulator {
LoanConstants.LAST_REPAYMENT_DATE_COL, LoanConstants.LAST_REPAYMENT_DATE_COL);
DataValidationHelper validationHelper = new HSSFDataValidationHelper((HSSFSheet) worksheet);
CellRangeAddressList chargeOneNameRange = new CellRangeAddressList(1, SpreadsheetVersion.EXCEL97.getLastRowIndex(),
LoanConstants.CHARGE_NAME_1, LoanConstants.CHARGE_NAME_1);
CellRangeAddressList chargeOneAmountTypeRange = new CellRangeAddressList(1, SpreadsheetVersion.EXCEL97.getLastRowIndex(),
LoanConstants.CHARGE_AMOUNT_TYPE_1, LoanConstants.CHARGE_AMOUNT_TYPE_1);
CellRangeAddressList chargeTwoNameRange = new CellRangeAddressList(1, SpreadsheetVersion.EXCEL97.getLastRowIndex(),
LoanConstants.CHARGE_NAME_2, LoanConstants.CHARGE_NAME_2);
CellRangeAddressList chargeTwoAmountTypeRange = new CellRangeAddressList(1, SpreadsheetVersion.EXCEL97.getLastRowIndex(),
LoanConstants.CHARGE_AMOUNT_TYPE_2, LoanConstants.CHARGE_AMOUNT_TYPE_2);
setNames(worksheet);
DataValidationConstraint officeNameConstraint = validationHelper.createFormulaListConstraint("Office");
@@ -168,9 +184,11 @@ public class LoanWorkbookPopulator extends AbstractWorkbookPopulator {
DataValidationConstraint.OperatorType.BETWEEN, "=INDIRECT(CONCATENATE(\"MIN_REPAYMENT_\",$E1))",
"=INDIRECT(CONCATENATE(\"MAX_REPAYMENT_\",$E1))");
DataValidationConstraint frequencyConstraint = validationHelper
.createExplicitListConstraint(new String[] { "Days", "Weeks", "Months", "Semi Month" });
DataValidationConstraint loanTermFrequencyConstraint = validationHelper
.createExplicitListConstraint(new String[] { "Days", "Weeks", "Months" });
DataValidationConstraint loanTermConstraint = validationHelper
.createIntegerConstraint(DataValidationConstraint.OperatorType.GREATER_OR_EQUAL, "=$M1*$N1", null);
.createIntegerConstraint(DataValidationConstraint.OperatorType.GREATER_OR_EQUAL, "=$M1/$N1", "=$M1*$N1");
DataValidationConstraint interestFrequencyConstraint = validationHelper
.createFormulaListConstraint("INDIRECT(CONCATENATE(\"INTEREST_FREQUENCY_\",$E1))");
DataValidationConstraint interestConstraint = validationHelper.createDecimalConstraint(
@@ -196,6 +214,14 @@ public class LoanWorkbookPopulator extends AbstractWorkbookPopulator {
DataValidationConstraint lastRepaymentDateConstraint = validationHelper
.createDateConstraint(DataValidationConstraint.OperatorType.BETWEEN, "=$I1", "=TODAY()", dateFormat);
DataValidationConstraint chargeOneNameConstraint = validationHelper.createFormulaListConstraint("Charges");
DataValidationConstraint chargeOneAmountTypeConstraint = validationHelper
.createExplicitListConstraint(new String[] { "Flat", "% Amount" });
DataValidationConstraint chargeTwoNameConstraint = validationHelper.createFormulaListConstraint("Charges");
DataValidationConstraint chargeTwoAmountTypeConstraint = validationHelper
.createExplicitListConstraint(new String[] { "Flat", "% Amount" });
DataValidation officeValidation = validationHelper.createValidation(officeNameConstraint, officeNameRange);
DataValidation loanTypeValidation = validationHelper.createValidation(loanTypeConstraint, loanTypeRange);
DataValidation clientValidation = validationHelper.createValidation(clientNameConstraint, clientNameRange);
@@ -203,7 +229,7 @@ public class LoanWorkbookPopulator extends AbstractWorkbookPopulator {
DataValidation loanOfficerValidation = validationHelper.createValidation(loanOfficerNameConstraint, loanOfficerRange);
DataValidation fundNameValidation = validationHelper.createValidation(fundNameConstraint, fundNameRange);
DataValidation repaidFrequencyValidation = validationHelper.createValidation(frequencyConstraint, repaidFrequencyRange);
DataValidation loanTermFrequencyValidation = validationHelper.createValidation(frequencyConstraint, loanTermFrequencyRange);
DataValidation loanTermFrequencyValidation = validationHelper.createValidation(loanTermFrequencyConstraint, loanTermFrequencyRange);
DataValidation amortizationValidation = validationHelper.createValidation(amortizationConstraint, amortizationRange);
DataValidation interestMethodValidation = validationHelper.createValidation(interestMethodConstraint, interestMethodRange);
DataValidation interestCalculationPeriodValidation = validationHelper.createValidation(interestCalculationPeriodConstraint,
@@ -228,6 +254,14 @@ public class LoanWorkbookPopulator extends AbstractWorkbookPopulator {
graceOnInterestChargedRange);
DataValidation interestFrequencyValidation = validationHelper.createValidation(interestFrequencyConstraint, interestFrequencyRange);
DataValidation chargeOneNameValidation = validationHelper.createValidation(chargeOneNameConstraint, chargeOneNameRange);
DataValidation chargeOneAmountTypeValidation = validationHelper.createValidation(chargeOneAmountTypeConstraint,
chargeOneAmountTypeRange);
DataValidation chargeTwoNameValidation = validationHelper.createValidation(chargeTwoNameConstraint, chargeTwoNameRange);
DataValidation chargeTwoAmountTypeValidation = validationHelper.createValidation(chargeTwoAmountTypeConstraint,
chargeTwoAmountTypeRange);
interestFrequencyValidation.setSuppressDropDownArrow(true);
worksheet.addValidationData(officeValidation);
@@ -258,6 +292,14 @@ public class LoanWorkbookPopulator extends AbstractWorkbookPopulator {
worksheet.addValidationData(lastRepaymentDateValidation);
worksheet.addValidationData(repaymentTypeValidation);
worksheet.addValidationData(chargeOneNameValidation);
// worksheet.addValidationData(chargeOneAmountValidation);
worksheet.addValidationData(chargeOneAmountTypeValidation);
worksheet.addValidationData(chargeTwoNameValidation);
// worksheet.addValidationData(chargeTwoAmountValidation);
worksheet.addValidationData(chargeTwoAmountTypeValidation);
}
private void setLayout(Sheet worksheet) {
@@ -299,11 +341,13 @@ public class LoanWorkbookPopulator extends AbstractWorkbookPopulator {
worksheet.setColumnWidth(LoanConstants.LOOKUP_CLIENT_EXTERNAL_ID, TemplatePopulateImportConstants.MEDIUM_COL_SIZE);
worksheet.setColumnWidth(LoanConstants.LOOKUP_ACTIVATION_DATE_COL, TemplatePopulateImportConstants.MEDIUM_COL_SIZE);
worksheet.setColumnWidth(LoanConstants.EXTERNAL_ID_COL, TemplatePopulateImportConstants.MEDIUM_COL_SIZE);
worksheet.setColumnWidth(LoanConstants.CHARGE_ID_1, TemplatePopulateImportConstants.MEDIUM_COL_SIZE);
worksheet.setColumnWidth(LoanConstants.CHARGE_NAME_1, TemplatePopulateImportConstants.MEDIUM_COL_SIZE);
worksheet.setColumnWidth(LoanConstants.CHARGE_AMOUNT_1, TemplatePopulateImportConstants.MEDIUM_COL_SIZE);
worksheet.setColumnWidth(LoanConstants.CHARGE_AMOUNT_TYPE_1, TemplatePopulateImportConstants.MEDIUM_COL_SIZE);
worksheet.setColumnWidth(LoanConstants.CHARGE_DUE_DATE_1, TemplatePopulateImportConstants.MEDIUM_COL_SIZE);
worksheet.setColumnWidth(LoanConstants.CHARGE_ID_2, TemplatePopulateImportConstants.MEDIUM_COL_SIZE);
worksheet.setColumnWidth(LoanConstants.CHARGE_NAME_2, TemplatePopulateImportConstants.MEDIUM_COL_SIZE);
worksheet.setColumnWidth(LoanConstants.CHARGE_AMOUNT_2, TemplatePopulateImportConstants.MEDIUM_COL_SIZE);
worksheet.setColumnWidth(LoanConstants.CHARGE_AMOUNT_TYPE_2, TemplatePopulateImportConstants.MEDIUM_COL_SIZE);
worksheet.setColumnWidth(LoanConstants.CHARGE_DUE_DATE_2, TemplatePopulateImportConstants.MEDIUM_COL_SIZE);
worksheet.setColumnWidth(LoanConstants.GROUP_ID, TemplatePopulateImportConstants.MEDIUM_COL_SIZE);
worksheet.setColumnWidth(LoanConstants.LINK_ACCOUNT_ID, TemplatePopulateImportConstants.MEDIUM_COL_SIZE);
@@ -341,11 +385,13 @@ public class LoanWorkbookPopulator extends AbstractWorkbookPopulator {
writeString(LoanConstants.LOOKUP_CLIENT_EXTERNAL_ID, rowHeader, "Lookup Client ExternalID");
writeString(LoanConstants.LOOKUP_ACTIVATION_DATE_COL, rowHeader, "Client Activation Date");
writeString(LoanConstants.EXTERNAL_ID_COL, rowHeader, "External Id");
writeString(LoanConstants.CHARGE_ID_1, rowHeader, "Charge Id");
writeString(LoanConstants.CHARGE_NAME_1, rowHeader, "Charge Name*");
writeString(LoanConstants.CHARGE_AMOUNT_1, rowHeader, "Charged Amount");
writeString(LoanConstants.CHARGE_AMOUNT_TYPE_1, rowHeader, "Charged Amount Type");
writeString(LoanConstants.CHARGE_DUE_DATE_1, rowHeader, "Charged On Date");
writeString(LoanConstants.CHARGE_ID_2, rowHeader, "Charge Id");
writeString(LoanConstants.CHARGE_NAME_2, rowHeader, "Charge Name*");
writeString(LoanConstants.CHARGE_AMOUNT_2, rowHeader, "Charged Amount");
writeString(LoanConstants.CHARGE_AMOUNT_TYPE_2, rowHeader, "Charged Amount Type");
writeString(LoanConstants.CHARGE_DUE_DATE_2, rowHeader, "Charged On Date");
writeString(LoanConstants.GROUP_ID, rowHeader, "GROUP ID");
writeString(LoanConstants.LINK_ACCOUNT_ID, rowHeader, "Linked Account No.");
@@ -385,8 +431,11 @@ public class LoanWorkbookPopulator extends AbstractWorkbookPopulator {
writeFormula(LoanConstants.NO_OF_REPAYMENTS_COL, row, "IF(ISERROR(INDIRECT(CONCATENATE(\"NO_REPAYMENT_\",$E" + (rowNo + 1)
+ "))),\"\",INDIRECT(CONCATENATE(\"NO_REPAYMENT_\",$E" + (rowNo + 1) + ")))");
writeFormula(LoanConstants.LOAN_TERM_COL, row,
"IF(ISERROR($M" + (rowNo + 1) + "*$N" + (rowNo + 1) + "),\"\",$M" + (rowNo + 1) + "*$N" + (rowNo + 1) + ")");
writeFormula(LoanConstants.LOAN_TERM_FREQUENCY_COL, row, "$O" + (rowNo + 1));
"IF(($O" + (rowNo + 1) + "=\"Semi Month\"), " + "(IF(ISERROR($M" + (rowNo + 1) + "/$N" + (rowNo + 1) + "),\"\",$M"
+ (rowNo + 1) + "/$N" + (rowNo + 1) + ")), " + "(IF(ISERROR($M" + (rowNo + 1) + "*$N" + (rowNo + 1)
+ "),\"\",$M" + (rowNo + 1) + "*$N" + (rowNo + 1) + "))" + ")");
writeFormula(LoanConstants.LOAN_TERM_FREQUENCY_COL, row,
"IF(($O" + (rowNo + 1) + "=\"Semi Month\"), \"Months\", $O" + (rowNo + 1) + ")");
writeFormula(LoanConstants.NOMINAL_INTEREST_RATE_FREQUENCY_COL, row,
"IF(ISERROR(INDIRECT(CONCATENATE(\"INTEREST_FREQUENCY_\",$E" + (rowNo + 1)
+ "))),\"\",INDIRECT(CONCATENATE(\"INTEREST_FREQUENCY_\",$E" + (rowNo + 1) + ")))");
@@ -408,13 +457,13 @@ public class LoanWorkbookPopulator extends AbstractWorkbookPopulator {
+ (rowNo + 1) + "))),\"\",INDIRECT(CONCATENATE(\"GRACE_INTEREST_PAYMENT_\",$E" + (rowNo + 1) + ")))");
writeFormula(LoanConstants.GRACE_ON_INTEREST_CHARGED_COL, row, "IF(ISERROR(INDIRECT(CONCATENATE(\"GRACE_INTEREST_CHARGED_\",$E"
+ (rowNo + 1) + "))),\"\",INDIRECT(CONCATENATE(\"GRACE_INTEREST_CHARGED_\",$E" + (rowNo + 1) + ")))");
}
}
private void setNames(Sheet worksheet) {
Workbook loanWorkbook = worksheet.getWorkbook();
List<String> officeNames = officeSheetPopulator.getOfficeNames();
List<ChargeData> charges = chargeSheetPopulator.getCharges();
List<LoanProductData> products = productSheetPopulator.getProducts();
// Office Names
@@ -460,6 +509,31 @@ public class LoanWorkbookPopulator extends AbstractWorkbookPopulator {
fundGroup.setRefersToFormula(
TemplatePopulateImportConstants.EXTRAS_SHEET_NAME + "!$B$2:$B$" + (extrasSheetPopulator.getFundsSize() + 1));
// Charge Name
Name chargeGroup = loanWorkbook.createName();
chargeGroup.setNameName("Charges");
chargeGroup.setRefersToFormula(
TemplatePopulateImportConstants.CHARGE_SHEET_NAME + "!$B$2:$B$" + (chargeSheetPopulator.getChargesSize() + 1));
// Default Charge Name, Charge Amount, Charge Amount Type, Charge Due Date
for (Integer i = 0; i < charges.size(); i++) {
Name chargeColName = loanWorkbook.createName();
Name chargeAmount = loanWorkbook.createName();
Name chargeAmountType = loanWorkbook.createName();
String chargeName = charges.get(i).getName().trim().replaceAll("[ )(]", "_");
chargeColName.setNameName("CHARGE_NAME_" + chargeName);
chargeColName.setRefersToFormula(TemplatePopulateImportConstants.CHARGE_SHEET_NAME + "!$B$" + (i + 2));
chargeAmount.setNameName("CHARGE_AMOUNT_" + chargeName);
chargeAmount.setRefersToFormula(TemplatePopulateImportConstants.CHARGE_SHEET_NAME + "!$C$" + (i + 2));
chargeAmountType.setNameName("CHARGE_AMOUNT_TYPE_" + chargeName);
chargeAmountType.setRefersToFormula(TemplatePopulateImportConstants.CHARGE_SHEET_NAME + "!$D$" + (i + 2));
}
// Payment Type Name
Name paymentTypeGroup = loanWorkbook.createName();
paymentTypeGroup.setNameName("PaymentTypes");
@@ -29,6 +29,7 @@ import org.apache.fineract.accounting.glaccount.service.GLAccountReadPlatformSer
import org.apache.fineract.infrastructure.bulkimport.constants.TemplatePopulateImportConstants;
import org.apache.fineract.infrastructure.bulkimport.data.GlobalEntityType;
import org.apache.fineract.infrastructure.bulkimport.populator.CenterSheetPopulator;
import org.apache.fineract.infrastructure.bulkimport.populator.ChargeSheetPopulator;
import org.apache.fineract.infrastructure.bulkimport.populator.ClientSheetPopulator;
import org.apache.fineract.infrastructure.bulkimport.populator.ExtrasSheetPopulator;
import org.apache.fineract.infrastructure.bulkimport.populator.FixedDepositProductSheetPopulator;
@@ -277,6 +278,11 @@ public class BulkImportWorkbookPopulatorServiceImpl implements BulkImportWorkboo
return offices;
}
@SuppressWarnings("unchecked")
private List<ChargeData> fetchCharges() {
return (List) this.chargeReadPlatformService.retrieveAllCharges();
}
@SuppressWarnings("unchecked")
private List<StaffData> fetchStaff(final Long staffId) {
List<StaffData> staff = null;
@@ -376,13 +382,15 @@ public class BulkImportWorkbookPopulatorServiceImpl implements BulkImportWorkboo
List<StaffData> staff = fetchStaff(staffId);
List<ClientData> clients = fetchClients(officeId);
List<GroupGeneralData> groups = fetchGroups(officeId);
List<ChargeData> charges = fetchCharges();
List<LoanProductData> loanproducts = fetchLoanProducts();
List<FundData> funds = fetchFunds();
List<PaymentTypeData> paymentTypes = fetchPaymentTypes();
List<CurrencyData> currencies = fetchCurrencies();
return new LoanWorkbookPopulator(new OfficeSheetPopulator(offices), new ClientSheetPopulator(clients, offices),
new GroupSheetPopulator(groups, offices), new PersonnelSheetPopulator(staff, offices),
new LoanProductSheetPopulator(loanproducts), new ExtrasSheetPopulator(funds, paymentTypes, currencies));
new LoanProductSheetPopulator(loanproducts), new ChargeSheetPopulator(charges),
new ExtrasSheetPopulator(funds, paymentTypes, currencies));
}
private List<CurrencyData> fetchCurrencies() {
@@ -321,6 +321,18 @@ public final class ChargeData implements Comparable<ChargeData>, Serializable {
return name;
}
public EnumOptionData getChargeCalculationType() {
return chargeCalculationType;
}
public EnumOptionData getChargeTimeType() {
return chargeTimeType;
}
public BigDecimal getAmount() {
return this.amount;
}
public CurrencyData getCurrency() {
return currency;
}
@@ -308,6 +308,37 @@ public class LoanChargeData {
this.amountUnrecognized = chargeData.amountUnrecognized;
}
public LoanChargeData(final Long id, final LocalDate dueAsOfDate, final BigDecimal amount, final EnumOptionData chargeCalculationType,
final EnumOptionData chargeTimeType) {
this.id = null;
this.chargeId = id;
this.name = null;
this.currency = null;
this.amount = amount;
this.amountPaid = null;
this.amountWaived = null;
this.amountWrittenOff = null;
this.amountOutstanding = null;
this.chargeTimeType = chargeTimeType;
this.dueDate = dueAsOfDate;
this.chargeCalculationType = chargeCalculationType;
this.percentage = null;
this.amountPercentageAppliedTo = null;
this.penalty = false;
this.chargePaymentMode = null;
this.paid = false;
this.waived = false;
this.amountOrPercentage = null;
this.chargeOptions = null;
this.chargePayable = false;
this.loanId = null;
this.minCap = null;
this.maxCap = null;
this.installmentChargeData = null;
this.amountAccrued = null;
this.amountUnrecognized = null;
}
public LoanChargeData(final Long id, final LocalDate dueAsOfDate, final BigDecimal amountOrPercentage) {
this.id = id;
this.chargeId = null;
@@ -370,6 +401,10 @@ public class LoanChargeData {
return isInstalmentFee;
}
public EnumOptionData getChargeCalculationType() {
return chargeCalculationType;
}
public BigDecimal amountOrPercentage() {
return this.amountOrPercentage;
}
@@ -47,6 +47,7 @@ import org.apache.fineract.integrationtests.common.OfficeDomain;
import org.apache.fineract.integrationtests.common.OfficeHelper;
import org.apache.fineract.integrationtests.common.PaymentTypeHelper;
import org.apache.fineract.integrationtests.common.Utils;
import org.apache.fineract.integrationtests.common.charges.ChargesHelper;
import org.apache.fineract.integrationtests.common.funds.FundsHelper;
import org.apache.fineract.integrationtests.common.funds.FundsResourceHandler;
import org.apache.fineract.integrationtests.common.loans.LoanProductTestBuilder;
@@ -66,6 +67,7 @@ public class LoanImportHandlerTest {
private static final Logger LOG = LoggerFactory.getLogger(LoanImportHandlerTest.class);
private static final String CREATE_CLIENT_URL = "/fineract-provider/api/v1/clients?" + Utils.TENANT_IDENTIFIER;
private static final String CREATE_CHARGE_URL = "/fineract-provider/api/v1/charges?" + Utils.TENANT_IDENTIFIER;
public static final String DATE_FORMAT = "dd MMMM yyyy";
private ResponseSpecification responseSpec;
@@ -120,6 +122,14 @@ public class LoanImportHandlerTest {
collateralHashMap.put("quantity", "1");
collaterals.add(collateralHashMap);
final String disbursementChargeJsonString = ChargesHelper.getLoanDisbursementJSON();
final Integer disbursementChargeId = ChargesHelper.createCharges(this.requestSpec, this.responseSpec, disbursementChargeJsonString);
final JsonPath disbursementChargeJSON = JsonPath.from(disbursementChargeJsonString);
Assertions.assertNotNull(disbursementChargeId, "Could not create charge");
// in order to populate helper sheets
Integer outcome_group_creation = GroupHelper.createGroup(requestSpec, responseSpec, true);
Assertions.assertNotNull(outcome_group_creation, "Could not create group");
@@ -200,6 +210,10 @@ public class LoanImportHandlerTest {
firstLoanRow.createCell(LoanConstants.REPAYMENT_TYPE_COL).setCellValue(paymentTypeName);
firstLoanRow.createCell(LoanConstants.LOAN_COLLATERAL_ID).setCellValue(collaterals.get(0).get("clientCollateralId").toString());
firstLoanRow.createCell(LoanConstants.LOAN_COLLATERAL_QUANTITY).setCellValue(collaterals.get(0).get("quantity").toString());
firstLoanRow.createCell(LoanConstants.CHARGE_NAME_1).setCellValue(disbursementChargeJSON.getString("name"));
firstLoanRow.createCell(LoanConstants.CHARGE_AMOUNT_1).setCellValue(disbursementChargeJSON.getFloat("amount"));
firstLoanRow.createCell(LoanConstants.CHARGE_AMOUNT_TYPE_1)
.setCellValue(disbursementChargeJSON.getString("chargeCalculationType.value"));
String currentdirectory = new File("").getAbsolutePath();
File directory = new File(currentdirectory + File.separator + "src" + File.separator + "integrationTest" + File.separator