Search in sources :

Example 1 with CustomerAccountBO

use of org.mifos.customers.business.CustomerAccountBO in project head by mifos.

the class SaveCollectionSheetAssembler method customerAccountAssemblerFromDto.

public List<AccountBO> customerAccountAssemblerFromDto(final List<SaveCollectionSheetCustomerDto> saveCollectionSheetCustomers, final AccountPaymentEntity payment, final List<String> failedCustomerAccountPaymentNums) {
    final List<AccountBO> customerAccountList = new ArrayList<AccountBO>();
    for (SaveCollectionSheetCustomerDto saveCollectionSheetCustomer : saveCollectionSheetCustomers) {
        SaveCollectionSheetCustomerAccountDto saveCollectionSheetCustomerAccount = saveCollectionSheetCustomer.getSaveCollectionSheetCustomerAccount();
        if (null != saveCollectionSheetCustomerAccount) {
            final BigDecimal amount = saveCollectionSheetCustomerAccount.getTotalCustomerAccountCollectionFee();
            if (null != amount && amount.compareTo(BigDecimal.ZERO) > 0) {
                final PaymentData accountPaymentDataView = getCustomerAccountPaymentDataView(new Money(Money.getDefaultCurrency(), amount.toString()), payment);
                final Integer accountId = saveCollectionSheetCustomer.getSaveCollectionSheetCustomerAccount().getAccountId();
                CustomerAccountBO account = null;
                try {
                    account = findCustomerAccountById(accountId);
                    account.applyPayment(accountPaymentDataView);
                    customerAccountList.add(account);
                } catch (AccountException ae) {
                    logger.warn("Payment of collection/fee on account [" + accountId + "] failed. Account changes will not be persisted due to: " + ae.getMessage());
                    failedCustomerAccountPaymentNums.add(accountId.toString());
                    StaticHibernateUtil.getSessionTL().evict(account);
                }
            }
        }
    }
    return customerAccountList;
}
Also used : CustomerAccountBO(org.mifos.customers.business.CustomerAccountBO) AccountBO(org.mifos.accounts.business.AccountBO) PaymentData(org.mifos.accounts.util.helpers.PaymentData) Money(org.mifos.framework.util.helpers.Money) CustomerAccountBO(org.mifos.customers.business.CustomerAccountBO) AccountException(org.mifos.accounts.exceptions.AccountException) ArrayList(java.util.ArrayList) BigDecimal(java.math.BigDecimal)

Example 2 with CustomerAccountBO

use of org.mifos.customers.business.CustomerAccountBO in project head by mifos.

the class GenerateMeetingsForCustomerAndSavingsHelper method execute.

@Override
public void execute(@SuppressWarnings("unused") final long timeInMillis) throws BatchJobException {
    workingDays = new FiscalCalendarRules().getWorkingDaysAsJodaTimeDays();
    officeCurrentAndFutureHolidays = new HashMap<Short, List<Holiday>>();
    long taskStartTime = new DateTimeService().getCurrentDateTime().getMillis();
    List<Integer> customerAndSavingsAccountIds = findActiveCustomerAndSavingsAccountIdsThatRequiredMeetingsToBeGenerated();
    int accountCount = customerAndSavingsAccountIds.size();
    if (accountCount == 0) {
        return;
    }
    List<String> errorList = new ArrayList<String>();
    int currentRecordNumber = 0;
    int outputIntervalForBatchJobs = GeneralConfig.getOutputIntervalForBatchJobs();
    int batchSize = GeneralConfig.getBatchSizeForBatchJobs();
    // jpw - hardcoded recordCommittingSize to 500 because now only accounts that need more schedules are returned
    int recordCommittingSize = 500;
    infoLogBatchParameters(accountCount, outputIntervalForBatchJobs, batchSize, recordCommittingSize);
    long startTime = new DateTimeService().getCurrentDateTime().getMillis();
    Integer currentAccountId = null;
    int updatedRecordCount = 0;
    try {
        StaticHibernateUtil.getSessionTL();
        StaticHibernateUtil.startTransaction();
        for (Integer accountId : customerAndSavingsAccountIds) {
            currentRecordNumber++;
            currentAccountId = accountId;
            AccountBO accountBO = legacyAccountDao.getAccount(accountId);
            List<Holiday> currentAndFutureHolidays = getOfficeCurrentAndFutureHolidays(accountBO.getOffice().getOfficeId());
            ScheduledDateGeneration scheduleGenerationStrategy = new HolidayAndWorkingDaysAndMoratoriaScheduledDateGeneration(workingDays, currentAndFutureHolidays);
            if (accountBO instanceof CustomerAccountBO) {
                ((CustomerAccountBO) accountBO).generateNextSetOfMeetingDates(scheduleGenerationStrategy);
                updatedRecordCount++;
            } else if (accountBO instanceof SavingsBO) {
                ((SavingsBO) accountBO).generateNextSetOfMeetingDates(workingDays, currentAndFutureHolidays);
                updatedRecordCount++;
            }
            if (currentRecordNumber % batchSize == 0) {
                StaticHibernateUtil.flushAndClearSession();
                getLogger().debug("completed HibernateUtil.flushAndClearSession()");
            }
            if (updatedRecordCount > 0) {
                if (updatedRecordCount % recordCommittingSize == 0) {
                    StaticHibernateUtil.commitTransaction();
                    StaticHibernateUtil.getSessionTL();
                    StaticHibernateUtil.startTransaction();
                }
            }
            if (currentRecordNumber % outputIntervalForBatchJobs == 0) {
                long time = System.currentTimeMillis();
                String message = "" + currentRecordNumber + " processed, " + (accountCount - currentRecordNumber) + " remaining, " + updatedRecordCount + " updated, batch time: " + (time - startTime) + " ms";
                logMessage(message);
                startTime = time;
            }
        }
        StaticHibernateUtil.commitTransaction();
        long time = System.currentTimeMillis();
        String message = "" + currentRecordNumber + " processed, " + (accountCount - currentRecordNumber) + " remaining, " + updatedRecordCount + " updated, batch time: " + (time - startTime) + " ms";
        logMessage(message);
    } catch (Exception e) {
        logMessage("account " + currentAccountId.intValue() + " exception " + e.getMessage());
        StaticHibernateUtil.rollbackTransaction();
        errorList.add(currentAccountId.toString());
        getLogger().error("Unable to generate schedules for account with ID " + currentAccountId, e);
    } finally {
        StaticHibernateUtil.closeSession();
    }
    if (errorList.size() > 0) {
        throw new BatchJobException(SchedulerConstants.FAILURE, errorList);
    }
    logMessage("GenerateMeetingsForCustomerAndSavings ran in " + (new DateTimeService().getCurrentDateTime().getMillis() - taskStartTime));
}
Also used : CustomerAccountBO(org.mifos.customers.business.CustomerAccountBO) ArrayList(java.util.ArrayList) SavingsBO(org.mifos.accounts.savings.business.SavingsBO) BatchJobException(org.mifos.framework.components.batchjobs.exceptions.BatchJobException) PersistenceException(org.mifos.framework.exceptions.PersistenceException) CustomerAccountBO(org.mifos.customers.business.CustomerAccountBO) AccountBO(org.mifos.accounts.business.AccountBO) HolidayAndWorkingDaysAndMoratoriaScheduledDateGeneration(org.mifos.schedule.internal.HolidayAndWorkingDaysAndMoratoriaScheduledDateGeneration) ScheduledDateGeneration(org.mifos.schedule.ScheduledDateGeneration) BatchJobException(org.mifos.framework.components.batchjobs.exceptions.BatchJobException) Holiday(org.mifos.application.holiday.business.Holiday) ArrayList(java.util.ArrayList) List(java.util.List) DateTimeService(org.mifos.framework.util.DateTimeService) FiscalCalendarRules(org.mifos.config.FiscalCalendarRules) HolidayAndWorkingDaysAndMoratoriaScheduledDateGeneration(org.mifos.schedule.internal.HolidayAndWorkingDaysAndMoratoriaScheduledDateGeneration)

Example 3 with CustomerAccountBO

use of org.mifos.customers.business.CustomerAccountBO in project head by mifos.

the class AccountBusinessService method getAppllicableFees.

public List<ApplicableCharge> getAppllicableFees(Integer accountId, UserContext userContext) throws ServiceException {
    List<ApplicableCharge> applicableChargeList = null;
    try {
        AccountBO account = getlegacyAccountDao().getAccount(accountId);
        FeeCategory categoryType = getCategoryType(account.getCustomer());
        if (account.getType() == AccountTypes.LOAN_ACCOUNT || account.getType() == AccountTypes.GROUP_LOAN_ACCOUNT) {
            applicableChargeList = getLoanApplicableCharges(getlegacyAccountDao().getAllApplicableFees(accountId, FeeCategory.LOAN), userContext, (LoanBO) account);
        } else if (account.getType() == AccountTypes.CUSTOMER_ACCOUNT) {
            if (account.getCustomer().getCustomerMeeting() == null) {
                throw new ServiceException(AccountExceptionConstants.APPLY_CAHRGE_NO_CUSTOMER_MEETING_EXCEPTION);
            }
            applicableChargeList = getCustomerApplicableCharges(getlegacyAccountDao().getAllApplicableFees(accountId, categoryType), userContext, ((CustomerAccountBO) account).getCustomer().getCustomerMeeting().getMeeting().getMeetingDetails().getRecurrenceType().getRecurrenceId());
        }
        addMiscFeeAndPenalty(applicableChargeList);
    } catch (PersistenceException pe) {
        throw new ServiceException(pe);
    }
    return applicableChargeList;
}
Also used : CustomerAccountBO(org.mifos.customers.business.CustomerAccountBO) AccountBO(org.mifos.accounts.business.AccountBO) CustomerAccountBO(org.mifos.customers.business.CustomerAccountBO) ServiceException(org.mifos.framework.exceptions.ServiceException) LoanBO(org.mifos.accounts.loan.business.LoanBO) ApplicableCharge(org.mifos.dto.domain.ApplicableCharge) PersistenceException(org.mifos.framework.exceptions.PersistenceException) FeeCategory(org.mifos.accounts.fees.util.helpers.FeeCategory)

Example 4 with CustomerAccountBO

use of org.mifos.customers.business.CustomerAccountBO in project head by mifos.

the class ImportClientsServiceFacadeWebTier method save.

@Override
public ParsedClientsDto save(ParsedClientsDto parsedClientsDto) {
    MifosUser user = (MifosUser) SecurityContextHolder.getContext().getAuthentication().getPrincipal();
    UserContext userContext = toUserContext(user);
    OfficeBO userOffice = this.officeDao.findOfficeById(userContext.getBranchId());
    userContext.setBranchGlobalNum(userOffice.getGlobalOfficeNum());
    DateTimeService dateTimeService = new DateTimeService();
    /* Construct ClientBO objects */
    List<NewClientDto> newClients = new ArrayList<NewClientDto>();
    for (ImportedClientDetail importedClient : parsedClientsDto.getSuccessfullyParsedRows()) {
        String secondMiddleName = null;
        ClientCreationDetail clientCreationDetail = importedClient.getClientCreationDetail();
        PersonnelBO formedBy = null;
        /* Client name details */
        ClientNameDetailDto clientNameDetails = clientCreationDetail.getClientNameDetailDto();
        ClientNameDetailEntity clientNameDetailEntity = new ClientNameDetailEntity(null, secondMiddleName, clientNameDetails);
        ClientDetailEntity clientDetailEntity = new ClientDetailEntity();
        clientDetailEntity.updateClientDetails(clientCreationDetail.getClientPersonalDetailDto());
        String clientFirstName = clientNameDetails.getFirstName();
        String clientLastName = clientNameDetails.getLastName();
        String secondLastName = clientNameDetails.getSecondLastName();
        /* Spouse/father name details */
        ClientNameDetailEntity spouseFatherNameDetailEntity = null;
        if (clientCreationDetail.getSpouseFatherName() != null) {
            spouseFatherNameDetailEntity = new ClientNameDetailEntity(null, secondMiddleName, clientCreationDetail.getSpouseFatherName());
        }
        /* Data conversion */
        DateTime dateOfBirth = new DateTime(clientCreationDetail.getDateOfBirth());
        DateTime mfiJoiningDate = new DateTime(clientCreationDetail.getMfiJoiningDate());
        DateTime trainedDateTime = null;
        if (clientCreationDetail.getTrainedDate() != null) {
            trainedDateTime = new DateTime(clientCreationDetail.getTrainedDate());
        }
        /* Status */
        CustomerStatus clientStatus = CustomerStatus.fromInt(clientCreationDetail.getClientStatus());
        CustomerStatus finalStatus = clientStatus;
        if (clientStatus == CustomerStatus.CLIENT_ACTIVE && clientCreationDetail.getActivationDate() == null) {
            clientStatus = CustomerStatus.CLIENT_PENDING;
        }
        /* Address */
        Address address = null;
        if (clientCreationDetail.getAddress() != null) {
            AddressDto dto = clientCreationDetail.getAddress();
            address = new Address(dto.getLine1(), dto.getLine2(), dto.getLine3(), dto.getCity(), dto.getState(), dto.getCountry(), dto.getZip(), dto.getPhoneNumber());
        }
        // empty list
        List<ClientInitialSavingsOfferingEntity> associatedOfferings = new ArrayList<ClientInitialSavingsOfferingEntity>();
        // client object
        ClientBO client;
        if (clientCreationDetail.getGroupFlag() == 1) {
            CustomerBO group = customerDao.findCustomerBySystemId(clientCreationDetail.getParentGroupId());
            if (clientCreationDetail.getFormedBy() != null) {
                formedBy = this.personnelDao.findPersonnelById(clientCreationDetail.getFormedBy());
            } else {
                formedBy = group.getPersonnel();
            }
            client = ClientBO.createNewInGroupHierarchy(userContext, clientCreationDetail.getClientName(), clientStatus, mfiJoiningDate, group, formedBy, clientNameDetailEntity, dateOfBirth, clientCreationDetail.getGovernmentId(), clientCreationDetail.isTrained(), trainedDateTime, clientCreationDetail.getGroupFlag(), clientFirstName, clientLastName, secondLastName, spouseFatherNameDetailEntity, clientDetailEntity, associatedOfferings, clientCreationDetail.getExternalId(), address, clientCreationDetail.getActivationDate());
        } else {
            Short officeId = clientCreationDetail.getOfficeId();
            Short officerId = clientCreationDetail.getLoanOfficerId();
            PersonnelBO loanOfficer = personnelDao.findPersonnelById(officerId);
            OfficeBO office = this.officeDao.findOfficeById(officeId);
            if (clientCreationDetail.getFormedBy() != null) {
                formedBy = this.personnelDao.findPersonnelById(clientCreationDetail.getFormedBy());
            } else {
                formedBy = loanOfficer;
            }
            int lastSearchIdCustomerValue = customerDao.retrieveLastSearchIdValueForNonParentCustomersInOffice(officeId);
            /* meeting */
            final MeetingDto meetingDto = importedClient.getMeeting();
            MeetingBO clientMeeting = null;
            if (meetingDto != null) {
                clientMeeting = new MeetingFactory().create(meetingDto);
                clientMeeting.setUserContext(userContext);
            }
            client = ClientBO.createNewOutOfGroupHierarchy(userContext, clientCreationDetail.getClientName(), clientStatus, mfiJoiningDate, office, loanOfficer, clientMeeting, formedBy, clientNameDetailEntity, dateOfBirth, clientCreationDetail.getGovernmentId(), clientCreationDetail.isTrained(), trainedDateTime, clientCreationDetail.getGroupFlag(), clientFirstName, clientLastName, secondLastName, spouseFatherNameDetailEntity, clientDetailEntity, associatedOfferings, clientCreationDetail.getExternalId(), address, lastSearchIdCustomerValue);
            if (clientCreationDetail.getActivationDate() != null) {
                client.setCustomerActivationDate(clientCreationDetail.getActivationDate().toDateMidnight().toDate());
            }
        }
        // global id
        if (importedClient.getClientGlobalNum() != null) {
            client.setGlobalCustNum(importedClient.getClientGlobalNum());
        }
        NewClientDto newClient = new NewClientDto(client, finalStatus);
        newClients.add(newClient);
    }
    /* Validate client data */
    for (NewClientDto newClient : newClients) {
        ClientBO client = newClient.getClientBO();
        try {
            client.validate();
            customerDao.validateClientForDuplicateNameOrGovtId(client.getDisplayName(), client.getDateOfBirth(), client.getGovernmentId());
        } catch (CustomerException ex) {
            throw new MifosRuntimeException(ex);
        }
    }
    /* Save clients */
    // empty list
    List<AccountFeesEntity> accountFees = new ArrayList<AccountFeesEntity>();
    try {
        hibernateTransactionHelper.startTransaction();
        for (NewClientDto newClient : newClients) {
            ClientBO client = newClient.getClientBO();
            CustomerStatus finalStatus = newClient.getCustomerStatus();
            // status to pending approval if active
            MeetingBO meeting = client.getCustomerMeetingValue();
            customerDao.save(client);
            hibernateTransactionHelper.flushSession();
            CalendarEvent applicableCalendarEvents = holidayDao.findCalendarEventsForThisYearAndNext(client.getOfficeId());
            CustomerAccountBO customerAccount = customerAccountFactory.create(client, accountFees, meeting, applicableCalendarEvents);
            client.addAccount(customerAccount);
            customerDao.save(client);
            hibernateTransactionHelper.flushSession();
            if (client.getParentCustomer() != null) {
                customerDao.save(client.getParentCustomer());
            }
            if (client.getGlobalCustNum() == null) {
                client.generateGlobalCustomerNumber();
            }
            client.generateSearchId();
            customerDao.save(client);
            hibernateTransactionHelper.flushSession();
            if (client.getParentCustomer() != null) {
                customerDao.save(client.getParentCustomer());
            }
            /* activate client */
            if (finalStatus == CustomerStatus.CLIENT_ACTIVE) {
                hibernateTransactionHelper.flushSession();
                hibernateTransactionHelper.beginAuditLoggingFor(client);
                client.clearCustomerFlagsIfApplicable(client.getStatus(), finalStatus);
                client.updateCustomerStatus(finalStatus);
                // changeStatus(client, oldStatus, newStatus);
                if (client.getParentCustomer() != null) {
                    CustomerHierarchyEntity hierarchy = new CustomerHierarchyEntity(client, client.getParentCustomer());
                    client.addCustomerHierarchy(hierarchy);
                }
                if (client.getCustomerActivationDate() != null) {
                    client.setCustomerActivationDate(client.getCustomerActivationDate());
                } else {
                    client.setCustomerActivationDate(dateTimeService.getCurrentJavaDateTime());
                }
                customerAccount.createSchedulesAndFeeSchedulesForFirstTimeActiveCustomer(client, accountFees, meeting, applicableCalendarEvents, new DateTime(client.getCustomerActivationDate()));
                customerDao.save(client);
            }
        }
        hibernateTransactionHelper.commitTransaction();
    } catch (Exception ex) {
        hibernateTransactionHelper.rollbackTransaction();
        throw new MifosRuntimeException(ex);
    }
    return parsedClientsDto;
}
Also used : CustomerAccountBO(org.mifos.customers.business.CustomerAccountBO) Address(org.mifos.framework.business.util.Address) NewClientDto(org.mifos.customers.client.util.helpers.NewClientDto) MeetingBO(org.mifos.application.meeting.business.MeetingBO) ClientBO(org.mifos.customers.client.business.ClientBO) ArrayList(java.util.ArrayList) ClientInitialSavingsOfferingEntity(org.mifos.customers.client.business.ClientInitialSavingsOfferingEntity) MeetingFactory(org.mifos.application.meeting.business.MeetingFactory) DateTime(org.joda.time.DateTime) ClientCreationDetail(org.mifos.dto.domain.ClientCreationDetail) OfficeBO(org.mifos.customers.office.business.OfficeBO) PersonnelBO(org.mifos.customers.personnel.business.PersonnelBO) ClientNameDetailDto(org.mifos.dto.screen.ClientNameDetailDto) ClientNameDetailEntity(org.mifos.customers.client.business.ClientNameDetailEntity) ClientDetailEntity(org.mifos.customers.client.business.ClientDetailEntity) CustomerBO(org.mifos.customers.business.CustomerBO) AccountFeesEntity(org.mifos.accounts.business.AccountFeesEntity) DateTimeService(org.mifos.framework.util.DateTimeService) CustomerException(org.mifos.customers.exceptions.CustomerException) CustomerHierarchyEntity(org.mifos.customers.business.CustomerHierarchyEntity) UserContext(org.mifos.security.util.UserContext) CalendarEvent(org.mifos.calendar.CalendarEvent) MifosUser(org.mifos.security.MifosUser) AddressDto(org.mifos.dto.domain.AddressDto) CustomerException(org.mifos.customers.exceptions.CustomerException) MifosRuntimeException(org.mifos.core.MifosRuntimeException) MeetingDto(org.mifos.dto.domain.MeetingDto) CustomerStatus(org.mifos.customers.util.helpers.CustomerStatus) ImportedClientDetail(org.mifos.dto.domain.ImportedClientDetail) MifosRuntimeException(org.mifos.core.MifosRuntimeException)

Example 5 with CustomerAccountBO

use of org.mifos.customers.business.CustomerAccountBO in project head by mifos.

the class AccountServiceIntegrationTest method testGetAppllicableFeesForMeetingStartingOnCurrentDate.

@Test
public void testGetAppllicableFeesForMeetingStartingOnCurrentDate() throws Exception {
    // FIXME some test leaves database table (apart from CUSTOMER and
    // PRD_OFFERING) in dirty state Failures are noticed on windows xp
    // system, the execution order differs for surefire from OS to OS.
    AccountBusinessService accountBusinessService = new AccountBusinessService();
    CustomerAccountBO customerAccountBO = getCustomerAccountWithAllTypesOfFees();
    StaticHibernateUtil.flushSession();
    center = TestObjectFactory.getCustomer(center.getCustomerId());
    StaticHibernateUtil.flushAndClearSession();
    UserContext uc = TestUtils.makeUser();
    List<ApplicableCharge> applicableChargeList = accountBusinessService.getAppllicableFees(customerAccountBO.getAccountId(), uc);
    Assert.assertEquals(4, applicableChargeList.size());
    for (ApplicableCharge applicableCharge : applicableChargeList) {
        if (applicableCharge.getFeeName().equalsIgnoreCase("Upfront Fee")) {
            // this is a rate, so we shouldn't have a trailing ".0"
            Assert.assertEquals("20", applicableCharge.getAmountOrRate());
            Assert.assertNotNull(applicableCharge.getFormula());
            Assert.assertNull(applicableCharge.getPeriodicity());
        } else if (applicableCharge.getFeeName().equalsIgnoreCase("Misc Fee")) {
            Assert.assertNull(applicableCharge.getAmountOrRate());
            Assert.assertNull(applicableCharge.getFormula());
            Assert.assertNull(applicableCharge.getPeriodicity());
        } else if (applicableCharge.getFeeName().equalsIgnoreCase("Periodic Fee")) {
            Assert.assertEquals(new Money(getCurrency(), "200.0"), new Money(getCurrency(), applicableCharge.getAmountOrRate()));
            Assert.assertNull(applicableCharge.getFormula());
            Assert.assertNotNull(applicableCharge.getPeriodicity());
        } else if (applicableCharge.getFeeName().equalsIgnoreCase("Mainatnence Fee")) {
            Assert.assertFalse(true);
        }
    }
}
Also used : CustomerAccountBO(org.mifos.customers.business.CustomerAccountBO) Money(org.mifos.framework.util.helpers.Money) UserContext(org.mifos.security.util.UserContext) ApplicableCharge(org.mifos.dto.domain.ApplicableCharge) Test(org.junit.Test)

Aggregations

CustomerAccountBO (org.mifos.customers.business.CustomerAccountBO)36 ArrayList (java.util.ArrayList)15 Test (org.junit.Test)15 AccountFeesEntity (org.mifos.accounts.business.AccountFeesEntity)15 MeetingBO (org.mifos.application.meeting.business.MeetingBO)12 DateTime (org.joda.time.DateTime)11 LocalDate (org.joda.time.LocalDate)11 AccountBO (org.mifos.accounts.business.AccountBO)10 CenterBuilder (org.mifos.domain.builders.CenterBuilder)10 MeetingBuilder (org.mifos.domain.builders.MeetingBuilder)10 AccountActionDateEntity (org.mifos.accounts.business.AccountActionDateEntity)9 CenterBO (org.mifos.customers.center.business.CenterBO)8 CalendarEventBuilder (org.mifos.domain.builders.CalendarEventBuilder)8 MifosRuntimeException (org.mifos.core.MifosRuntimeException)7 GroupBO (org.mifos.customers.group.business.GroupBO)7 GroupBuilder (org.mifos.domain.builders.GroupBuilder)7 AccountException (org.mifos.accounts.exceptions.AccountException)6 LoanBO (org.mifos.accounts.loan.business.LoanBO)6 UserContext (org.mifos.security.util.UserContext)6 SavingsBO (org.mifos.accounts.savings.business.SavingsBO)5