/*
* Copyright (c) 2005-2011 Grameen Foundation USA
* All rights reserved.
*
* Licensed 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.
*
* See also http://www.apache.org/licenses/LICENSE-2.0.html for an
* explanation of the license and how it is applied.
*/
package org.mifos.accounts.loan.struts.action;
import static org.apache.commons.lang.StringUtils.isNotEmpty;
import static org.mifos.accounts.loan.util.helpers.LoanConstants.ADMINISTRATIVE_DOCUMENT_IS_ENABLED;
import static org.mifos.accounts.loan.util.helpers.LoanConstants.CLIENT_LIST;
import static org.mifos.accounts.loan.util.helpers.LoanConstants.CUSTOM_FIELDS;
import static org.mifos.accounts.loan.util.helpers.LoanConstants.LOANFUNDS;
import static org.mifos.accounts.loan.util.helpers.LoanConstants.LOANOFFERING;
import static org.mifos.accounts.loan.util.helpers.LoanConstants.LOAN_ACCOUNT_OWNER_IS_A_GROUP;
import static org.mifos.accounts.loan.util.helpers.LoanConstants.LOAN_ALL_ACTIVITY_VIEW;
import static org.mifos.accounts.loan.util.helpers.LoanConstants.LOAN_INDIVIDUAL_MONITORING_IS_ENABLED;
import static org.mifos.accounts.loan.util.helpers.LoanConstants.METHODCALLED;
import static org.mifos.accounts.loan.util.helpers.LoanConstants.MIN_DAYS_BETWEEN_DISBURSAL_AND_FIRST_REPAYMENT_DAY;
import static org.mifos.accounts.loan.util.helpers.LoanConstants.NEXTMEETING_DATE;
import static org.mifos.accounts.loan.util.helpers.LoanConstants.PROPOSED_DISBURSAL_DATE;
import static org.mifos.accounts.loan.util.helpers.LoanConstants.RECENTACCOUNTACTIVITIES;
import static org.mifos.accounts.loan.util.helpers.LoanConstants.RECURRENCEID;
import static org.mifos.accounts.loan.util.helpers.LoanConstants.RECURRENCENAME;
import static org.mifos.accounts.loan.util.helpers.LoanConstants.STATUS_HISTORY;
import static org.mifos.accounts.loan.util.helpers.LoanConstants.TOTAL_AMOUNT_OVERDUE;
import static org.mifos.accounts.loan.util.helpers.LoanConstants.VIEWINSTALLMENTDETAILS_SUCCESS;
import static org.mifos.accounts.loan.util.helpers.LoanConstants.VIEW_OVERDUE_INSTALLMENT_DETAILS;
import static org.mifos.accounts.loan.util.helpers.LoanConstants.VIEW_UPCOMING_INSTALLMENT_DETAILS;
import static org.mifos.accounts.loan.util.helpers.RequestConstants.PERSPECTIVE;
import static org.mifos.framework.util.helpers.Constants.BUSINESS_KEY;
import java.io.Serializable;
import java.io.UnsupportedEncodingException;
import java.math.BigDecimal;
import java.math.RoundingMode;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.Collection;
import java.util.Collections;
import java.util.Date;
import java.util.GregorianCalendar;
import java.util.HashSet;
import java.util.List;
import java.util.Locale;
import java.util.Set;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.commons.collections.CollectionUtils;
import org.apache.commons.collections.Predicate;
import org.apache.commons.lang.StringUtils;
import org.apache.struts.action.ActionErrors;
import org.apache.struts.action.ActionForm;
import org.apache.struts.action.ActionForward;
import org.apache.struts.action.ActionMapping;
import org.apache.struts.action.ActionMessage;
import org.mifos.accounts.business.AccountOverpaymentEntity;
import org.mifos.accounts.business.AccountStatusChangeHistoryEntity;
import org.mifos.accounts.business.service.AccountBusinessService;
import org.mifos.accounts.exceptions.AccountException;
import org.mifos.accounts.fund.business.FundBO;
import org.mifos.accounts.loan.business.LoanBO;
import org.mifos.accounts.loan.business.MaxMinInterestRate;
import org.mifos.accounts.loan.business.service.LoanBusinessService;
import org.mifos.accounts.loan.business.service.OriginalScheduleInfoDto;
import org.mifos.accounts.loan.persistance.LoanDaoHibernate;
import org.mifos.accounts.loan.struts.actionforms.LoanAccountActionForm;
import org.mifos.accounts.loan.util.helpers.LoanConstants;
import org.mifos.accounts.loan.util.helpers.RepaymentScheduleInstallment;
import org.mifos.accounts.productdefinition.business.LoanOfferingBO;
import org.mifos.accounts.productdefinition.business.LoanOfferingFundEntity;
import org.mifos.accounts.productdefinition.business.service.LoanPrdBusinessService;
import org.mifos.accounts.savings.persistence.GenericDaoHibernate;
import org.mifos.accounts.struts.action.AccountAppAction;
import org.mifos.accounts.util.helpers.AccountConstants;
import org.mifos.accounts.util.helpers.AccountState;
import org.mifos.application.admin.servicefacade.InvalidDateException;
import org.mifos.application.master.MessageLookup;
import org.mifos.application.master.business.CustomFieldDefinitionEntity;
import org.mifos.application.master.util.helpers.MasterConstants;
import org.mifos.application.meeting.business.MeetingBO;
import org.mifos.application.meeting.business.MeetingDetailsEntity;
import org.mifos.application.meeting.exceptions.MeetingException;
import org.mifos.application.meeting.util.helpers.MeetingConstants;
import org.mifos.application.meeting.util.helpers.MeetingType;
import org.mifos.application.meeting.util.helpers.RankOfDay;
import org.mifos.application.meeting.util.helpers.RecurrenceType;
import org.mifos.application.meeting.util.helpers.WeekDay;
import org.mifos.application.questionnaire.struts.DefaultQuestionnaireServiceFacadeLocator;
import org.mifos.application.questionnaire.struts.QuestionnaireAction;
import org.mifos.application.questionnaire.struts.QuestionnaireFlowAdapter;
import org.mifos.application.questionnaire.struts.QuestionnaireServiceFacadeLocator;
import org.mifos.application.servicefacade.ApplicationContextProvider;
import org.mifos.application.servicefacade.GroupLoanAccountServiceFacade;
import org.mifos.application.util.helpers.ActionForwards;
import org.mifos.application.util.helpers.Methods;
import org.mifos.application.util.helpers.OriginalScheduleInfoHelper;
import org.mifos.config.AccountingRules;
import org.mifos.config.FiscalCalendarRules;
import org.mifos.config.business.service.ConfigurationBusinessService;
import org.mifos.config.persistence.ConfigurationPersistence;
import org.mifos.core.MifosRuntimeException;
import org.mifos.customers.business.CustomerBO;
import org.mifos.customers.client.business.ClientBO;
import org.mifos.customers.persistence.CustomerDao;
import org.mifos.customers.util.helpers.CustomerConstants;
import org.mifos.dto.domain.CustomFieldDto;
import org.mifos.dto.domain.LoanAccountDetailsDto;
import org.mifos.dto.domain.LoanActivityDto;
import org.mifos.dto.domain.LoanInstallmentDetailsDto;
import org.mifos.dto.domain.ValueListElement;
import org.mifos.dto.screen.LoanInformationDto;
import org.mifos.framework.business.util.helpers.MethodNameConstants;
import org.mifos.framework.exceptions.ApplicationException;
import org.mifos.framework.exceptions.PageExpiredException;
import org.mifos.framework.exceptions.PersistenceException;
import org.mifos.framework.exceptions.ServiceException;
import org.mifos.framework.util.helpers.Constants;
import org.mifos.framework.util.helpers.DateUtils;
import org.mifos.framework.util.helpers.Money;
import org.mifos.framework.util.helpers.SessionUtils;
import org.mifos.framework.util.helpers.TransactionDemarcate;
import org.mifos.platform.questionnaire.domain.InformationOrderService;
import org.mifos.platform.questionnaire.service.InformationOrderServiceFacade;
import org.mifos.platform.questionnaire.service.QuestionGroupInstanceDetail;
import org.mifos.platform.questionnaire.service.QuestionnaireServiceFacade;
import org.mifos.platform.validations.ErrorEntry;
import org.mifos.platform.validations.Errors;
import org.mifos.reports.admindocuments.util.helpers.AdminDocumentsContants;
import org.mifos.security.util.UserContext;
/**
* management of loan accounts.
*/
public class LoanAccountAction extends AccountAppAction implements QuestionnaireAction {
private final LoanBusinessService loanBusinessService;
private final LoanPrdBusinessService loanPrdBusinessService;
private final ConfigurationPersistence configurationPersistence;
private final ConfigurationBusinessService configService;
private final GlimLoanUpdater glimLoanUpdater;
public static final String CUSTOMER_ID = "customerId";
public static final String ACCOUNT_ID = "accountId";
public static final String GLOBAL_ACCOUNT_NUM = "globalAccountNum";
private QuestionnaireServiceFacadeLocator questionnaireServiceFacadeLocator;
private QuestionGroupFilterForLoan questionGroupFilter;
private QuestionnaireFlowAdapter createLoanQuestionnaire;
private GroupLoanAccountServiceFacade groupLoanAccountServiceFacade;
private InformationOrderServiceFacade informationOrderServiceFacade;
public LoanAccountAction() {
this(new ConfigurationBusinessService(), ApplicationContextProvider.getBean(LoanBusinessService.class), new GlimLoanUpdater(),
new LoanPrdBusinessService(),
new ConfigurationPersistence(), new AccountBusinessService(), ApplicationContextProvider.getBean(GroupLoanAccountServiceFacade.class),
ApplicationContextProvider.getBean(InformationOrderServiceFacade.class));
}
public LoanAccountAction(final ConfigurationBusinessService configService,
final LoanBusinessService loanBusinessService, final GlimLoanUpdater glimLoanUpdater,
final LoanPrdBusinessService loanPrdBusinessService,
final ConfigurationPersistence configurationPersistence,
final AccountBusinessService accountBusinessService,
final GroupLoanAccountServiceFacade groupLoanAccountServiceFacade,
final InformationOrderServiceFacade informationOrderServiceFacade) {
super(accountBusinessService);
this.configService = configService;
this.loanBusinessService = loanBusinessService;
this.glimLoanUpdater = glimLoanUpdater;
this.loanPrdBusinessService = loanPrdBusinessService;
this.configurationPersistence = configurationPersistence;
this.questionGroupFilter = new QuestionGroupFilterForLoan();
this.questionnaireServiceFacadeLocator = new DefaultQuestionnaireServiceFacadeLocator();
this.createLoanQuestionnaire = getCreateLoanQuestionnaire();
this.groupLoanAccountServiceFacade = groupLoanAccountServiceFacade;
this.informationOrderServiceFacade = informationOrderServiceFacade;
}
QuestionnaireFlowAdapter getCreateLoanQuestionnaire() {
return new QuestionnaireFlowAdapter("Create", "Loan", ActionForwards.schedulePreview_success,
"clientsAndAccounts.ftl", questionnaireServiceFacadeLocator, questionGroupFilter);
}
/**
* @deprecated - test only
*/
@Deprecated
LoanAccountAction(final LoanBusinessService loanBusinessService, final ConfigurationBusinessService configService,
final GlimLoanUpdater glimLoanUpdater) {
this(configService, loanBusinessService, glimLoanUpdater);
}
/**
* test only constructor
*/
@Deprecated
private LoanAccountAction(final ConfigurationBusinessService configService,
final LoanBusinessService loanBusinessService, final GlimLoanUpdater glimLoanUpdater) {
this(configService, loanBusinessService, glimLoanUpdater, new LoanPrdBusinessService(), new ConfigurationPersistence(),
new AccountBusinessService(), null, ApplicationContextProvider.getBean(InformationOrderServiceFacade.class));
}
private List<FundBO> getFunds(final LoanOfferingBO loanOffering) {
List<FundBO> funds = new ArrayList<FundBO>();
if (loanOffering.getLoanOfferingFunds() != null && loanOffering.getLoanOfferingFunds().size() > 0) {
for (LoanOfferingFundEntity loanOfferingFund : loanOffering.getLoanOfferingFunds()) {
funds.add(loanOfferingFund.getFund());
}
}
return funds;
}
public ActionForward viewAndEditAdditionalInformation(final ActionMapping mapping, @SuppressWarnings("unused") final ActionForm form, final HttpServletRequest request, @SuppressWarnings("unused") final HttpServletResponse response)
throws Exception {
Integer entityId = Integer.valueOf(request.getParameter("entityId"));
questionGroupFilter.setLoanOfferingBO(getLoan(entityId).getLoanOffering());
List<QuestionGroupInstanceDetail> questionGroupInstances = createLoanQuestionnaire.
getQuestionGroupInstances(request, entityId);
request.getSession().setAttribute(LoanConstants.QUESTION_GROUP_INSTANCES, questionGroupInstances);
ActionForward forward = mapping.findForward(ActionForwards.viewAndEditAdditionalInformation.toString());
return new ActionForward(forward.getPath(), forward.getRedirect());
}
private void setPerspective(HttpServletRequest request, String perspective) {
if (perspective != null) {
request.setAttribute(PERSPECTIVE, perspective);
}
}
@TransactionDemarcate(joinToken = true)
public ActionForward getInstallmentDetails(final ActionMapping mapping,
@SuppressWarnings("unused") final ActionForm form, final HttpServletRequest request,
@SuppressWarnings("unused") final HttpServletResponse response) throws Exception {
Integer accountId = Integer.valueOf(request.getParameter(ACCOUNT_ID));
LoanInstallmentDetailsDto loanInstallmentDetailsDto = this.loanAccountServiceFacade.retrieveInstallmentDetails(accountId);
SessionUtils.setAttribute(VIEW_UPCOMING_INSTALLMENT_DETAILS, loanInstallmentDetailsDto.getUpcomingInstallmentDetails(), request);
SessionUtils.setAttribute(VIEW_OVERDUE_INSTALLMENT_DETAILS, loanInstallmentDetailsDto.getOverDueInstallmentDetails(), request);
SessionUtils.setAttribute(TOTAL_AMOUNT_OVERDUE, loanInstallmentDetailsDto.getTotalAmountDue(), request);
SessionUtils.setAttribute(NEXTMEETING_DATE, loanInstallmentDetailsDto.getNextMeetingDate(), request);
if (null == this.loanDao.findById(accountId).getParentAccount() && this.loanDao.findById(accountId).isGroupLoanAccount()) {
SessionUtils.setAttribute("isNewGlim", "isNewGlim", request);
}
return mapping.findForward(VIEWINSTALLMENTDETAILS_SUCCESS);
}
@TransactionDemarcate(joinToken = true)
public ActionForward getAllActivity(final ActionMapping mapping, @SuppressWarnings("unused") final ActionForm form,
final HttpServletRequest request, @SuppressWarnings("unused") final HttpServletResponse response)
throws Exception {
String globalAccountNum = request.getParameter(GLOBAL_ACCOUNT_NUM);
List<LoanActivityDto> allLoanAccountActivities = this.loanAccountServiceFacade.retrieveAllLoanAccountActivities(globalAccountNum);
SessionUtils.setCollectionAttribute(LOAN_ALL_ACTIVITY_VIEW, allLoanAccountActivities, request);
return mapping.findForward(MethodNameConstants.GETALLACTIVITY_SUCCESS);
}
@TransactionDemarcate(joinToken = true)
public ActionForward forwardWaiveCharge(final ActionMapping mapping,
@SuppressWarnings("unused") final ActionForm form, final HttpServletRequest request,
@SuppressWarnings("unused") final HttpServletResponse response) throws Exception {
return mapping.findForward("waive" + request.getParameter("type") + "Charges_Success");
}
@TransactionDemarcate(saveToken = true)
public ActionForward get(final ActionMapping mapping, final ActionForm form, final HttpServletRequest request,
@SuppressWarnings("unused") final HttpServletResponse response) throws Exception {
LoanAccountActionForm loanAccountActionForm = (LoanAccountActionForm) form;
loanAccountActionForm.clearDetailsForLoan();
String globalAccountNum = request.getParameter(GLOBAL_ACCOUNT_NUM);
UserContext userContext = getUserContext(request);
LoanInformationDto loanInformationDto;
try {
loanInformationDto = this.loanAccountServiceFacade.retrieveLoanInformation(globalAccountNum);
}
catch (MifosRuntimeException e) {
if (e.getCause() instanceof ApplicationException) {
throw (ApplicationException) e.getCause();
}
throw e;
}
request.getSession().setAttribute("guarantyInformation" , loanAccountServiceFacade.handleGuaranties(loanInformationDto));
final String accountStateNameLocalised = ApplicationContextProvider.getBean(MessageLookup.class).lookup(loanInformationDto.getAccountStateName());
SessionUtils.removeThenSetAttribute("accountStateNameLocalised", accountStateNameLocalised, request);
final String gracePeriodTypeNameLocalised = ApplicationContextProvider.getBean(MessageLookup.class).lookup(loanInformationDto.getGracePeriodTypeName());
SessionUtils.removeThenSetAttribute("gracePeriodTypeNameLocalised", gracePeriodTypeNameLocalised, request);
final String interestTypeNameLocalised = ApplicationContextProvider.getBean(MessageLookup.class).lookup(loanInformationDto.getInterestTypeName());
SessionUtils.removeThenSetAttribute("interestTypeNameLocalised", interestTypeNameLocalised, request);
final Set<String> accountFlagStateEntityNamesLocalised = new HashSet<String>();
for (String name : loanInformationDto.getAccountFlagNames()) {
accountFlagStateEntityNamesLocalised.add(ApplicationContextProvider.getBean(MessageLookup.class).lookup(name));
}
SessionUtils.setCollectionAttribute("accountFlagNamesLocalised", accountFlagStateEntityNamesLocalised, request);
SessionUtils.removeAttribute(BUSINESS_KEY, request);
Integer loanIndividualMonitoringIsEnabled = configurationPersistence.getConfigurationValueInteger(LOAN_INDIVIDUAL_MONITORING_IS_ENABLED);
if (null != loanIndividualMonitoringIsEnabled && loanIndividualMonitoringIsEnabled.intValue() != 0) {
SessionUtils.setAttribute(LOAN_INDIVIDUAL_MONITORING_IS_ENABLED, loanIndividualMonitoringIsEnabled.intValue(), request);
}
Boolean GroupLoanWithMembers = AccountingRules.isGroupLoanWithMembers();
if (null != GroupLoanWithMembers && GroupLoanWithMembers != false) {
SessionUtils.setAttribute("GroupLoanWithMembers", GroupLoanWithMembers.booleanValue(), request);
}
List<ValueListElement> allLoanPurposes = this.loanProductDao.findAllLoanPurposes();
// List<BusinessActivityEntity> loanPurposes = (List<BusinessActivityEntity>)masterDataService.retrieveMasterEntities(MasterConstants.LOAN_PURPOSES, getUserContext(request).getLocaleId());
SessionUtils.setCollectionAttribute(MasterConstants.BUSINESS_ACTIVITIES, allLoanPurposes, request);
if ((null != loanIndividualMonitoringIsEnabled && 0 != loanIndividualMonitoringIsEnabled.intValue() || (null != GroupLoanWithMembers && GroupLoanWithMembers != false))
&& loanInformationDto.isGroup()) {
List<LoanAccountDetailsDto> loanAccountDetails = this.loanAccountServiceFacade.retrieveLoanAccountDetails(loanInformationDto);
addEmptyBuisnessActivities(loanAccountDetails);
SessionUtils.setCollectionAttribute("loanAccountDetailsView", loanAccountDetails, request);
}
SessionUtils.setCollectionAttribute(CUSTOM_FIELDS, new ArrayList<CustomFieldDefinitionEntity>(), request);
// Retrieve and set into the session all collateral types from the
// lookup_value_locale table associated with the current user context
// locale
SessionUtils.setCollectionAttribute(MasterConstants.COLLATERAL_TYPES, legacyMasterDao.getLookUpEntity(
MasterConstants.COLLATERAL_TYPES).getCustomValueListElements(), request);
SessionUtils.setAttribute(AccountConstants.LAST_PAYMENT_ACTION, loanBusinessService.getLastPaymentAction(loanInformationDto.getAccountId()), request);
SessionUtils.removeThenSetAttribute("loanInformationDto", loanInformationDto, request);
// inject preferred date
List<LoanActivityDto> activities = loanInformationDto.getRecentAccountActivity();
for (LoanActivityDto activity : activities) {
activity.setUserPrefferedDate(DateUtils.getUserLocaleDate(userContext.getPreferredLocale(), activity.getActionDate().toString()));
}
SessionUtils.setCollectionAttribute(RECENTACCOUNTACTIVITIES, activities, request);
request.setAttribute(CustomerConstants.SURVEY_KEY, loanInformationDto.getAccountSurveys());
request.setAttribute(CustomerConstants.SURVEY_COUNT, loanInformationDto.getActiveSurveys());
request.setAttribute(AccountConstants.SURVEY_KEY, loanInformationDto.getAccountSurveys());
Integer administrativeDocumentsIsEnabled = configurationPersistence.getConfigurationValueInteger(ADMINISTRATIVE_DOCUMENT_IS_ENABLED);
if (null != administrativeDocumentsIsEnabled && administrativeDocumentsIsEnabled.intValue() == 1) {
SessionUtils.setCollectionAttribute(AdminDocumentsContants.ADMINISTRATIVEDOCUMENTSLIST,
legacyAdminDocumentDao.getAllActiveAdminDocuments(), request);
SessionUtils.setCollectionAttribute(AdminDocumentsContants.ADMINISTRATIVEDOCUMENTSACCSTATEMIXLIST,
legacyAdminDocAccStateMixDao.getAllMixedAdminDocuments(), request);
}
List<QuestionGroupInstanceDetail> questions = new ArrayList<QuestionGroupInstanceDetail>();
QuestionnaireServiceFacade questionnaireServiceFacade = ApplicationContextProvider.getBean(QuestionnaireServiceFacade.class);
questions.addAll(questionnaireServiceFacade.getQuestionGroupInstancesWithUnansweredQuestionGroups(loanInformationDto.getAccountId(), "Create", "Loan"));
questions.addAll(questionnaireServiceFacade.getQuestionGroupInstancesWithUnansweredQuestionGroups(loanInformationDto.getAccountId(), "Approve", "Loan"));
questions.addAll(questionnaireServiceFacade.getQuestionGroupInstancesWithUnansweredQuestionGroups(loanInformationDto.getAccountId(), "View", "Loan"));
questions.addAll(questionnaireServiceFacade.getQuestionGroupInstancesWithUnansweredQuestionGroups(loanInformationDto.getAccountId(), "Disburse", "Loan"));
questions.addAll(questionnaireServiceFacade.getQuestionGroupInstancesWithUnansweredQuestionGroups(loanInformationDto.getAccountId(), "Close", "Loan"));
SessionUtils.setCollectionAttribute("questionGroups", questions, request);
SessionUtils.setCollectionAttribute("personalInformationOrder", informationOrderServiceFacade.getInformationOrder("Loan"), request);
// John W - temporarily put back because needed in applychargeaction - update
// keithW - and for recentAccountNotes
LoanBO loan = getLoan(loanInformationDto.getAccountId());
SessionUtils.setAttribute(Constants.BUSINESS_KEY, loan, request);
LoanAccountAction.setSessionAtributeForGLIM(request, loan);
setCurrentPageUrl(request, loan);
setQuestionGroupInstances(request, loan);
setOverpayments(request, loan);
List<RepaymentScheduleInstallment> installments = loan.toRepaymentScheduleDto(userContext.getPreferredLocale());
loanAccountActionForm.initializeInstallments(installments);
return mapping.findForward(ActionForwards.get_success.toString());
}
private void setOverpayments(HttpServletRequest request, LoanBO loan) throws PageExpiredException {
List<AccountOverpaymentEntity> overpayments = new ArrayList<AccountOverpaymentEntity>();
// filter cleared overpayments
for (AccountOverpaymentEntity overpayment : loan.getAccountOverpayments()) {
if (overpayment.isNotCleared()) {
overpayments.add(overpayment);
}
}
SessionUtils.setCollectionAttribute("overpayments", overpayments, request);
}
private void addEmptyBuisnessActivities(List<LoanAccountDetailsDto> loanAccountDetails) {
for (LoanAccountDetailsDto details : loanAccountDetails) {
if (details.getBusinessActivity() == null || details.getBusinessActivity().equals("")) {
details.setBusinessActivity("-");
details.setBusinessActivityName("-");
}
}
}
private void setQuestionGroupInstances(HttpServletRequest request, LoanBO loanBO) throws PageExpiredException {
QuestionnaireServiceFacade questionnaireServiceFacade = questionnaireServiceFacadeLocator.getService(request);
boolean containsQGForCloseLoan = false;
if (questionnaireServiceFacade != null) {
setQuestionGroupInstances(questionnaireServiceFacade, request, loanBO.getAccountId());
if (loanBO.getAccountState().getId().equals(AccountState.LOAN_CLOSED_RESCHEDULED.getValue()) ||
loanBO.getAccountState().getId().equals(AccountState.LOAN_CLOSED_WRITTEN_OFF.getValue())) {
containsQGForCloseLoan = questionnaireServiceFacade.getQuestionGroupInstances(loanBO.getAccountId(), "Close", "Loan").size() > 0;
}
}
SessionUtils.removeThenSetAttribute("containsQGForCloseLoan", containsQGForCloseLoan, request);
}
// Intentionally made public to aid testing !
public void setQuestionGroupInstances(QuestionnaireServiceFacade questionnaireServiceFacade, HttpServletRequest request, Integer loanAccountId) throws PageExpiredException {
List<QuestionGroupInstanceDetail> instanceDetails = questionnaireServiceFacade.getQuestionGroupInstances(loanAccountId, "View", "Loan");
SessionUtils.setCollectionAttribute("questionGroupInstances", instanceDetails, request);
}
private void setCurrentPageUrl(HttpServletRequest request, LoanBO loanBO) throws PageExpiredException, UnsupportedEncodingException {
SessionUtils.removeThenSetAttribute("currentPageUrl", constructCurrentPageUrl(request, loanBO), request);
}
private String constructCurrentPageUrl(HttpServletRequest request, LoanBO loanBO) throws UnsupportedEncodingException {
String globalAccountNum = request.getParameter("globalAccountNum");
String officerId = request.getParameter("recordOfficeId");
String loanOfficerId = request.getParameter("recordLoanOfficerId");
String url = String.format("loanAccountAction.do?globalAccountNum=%s&customerId=%s&recordOfficeId=%s&recordLoanOfficerId=%s",
globalAccountNum, Integer.toString(loanBO.getAccountId()), officerId, loanOfficerId);
return url;
}
@TransactionDemarcate(saveToken = true)
public ActionForward getLoanRepaymentSchedule(final ActionMapping mapping,
final ActionForm form, final HttpServletRequest request,
@SuppressWarnings("unused") final HttpServletResponse response) throws Exception {
LoanAccountActionForm loanAccountActionForm = (LoanAccountActionForm) form;
UserContext userContext = getUserContext(request);
Integer loanId = Integer.valueOf(request.getParameter(ACCOUNT_ID));
Locale locale = userContext.getPreferredLocale();
Date viewDate = loanAccountActionForm.getScheduleViewDateValue(locale);
LoanBO loan = getLoan(loanId);
setSessionAtributeForGLIM(request, loan);
loan.updateDetails(userContext);
Errors errors = loanBusinessService.computeExtraInterest(loan, viewDate);
if (errors.hasErrors()) {
loanAccountActionForm.resetScheduleViewDate();
}
OriginalScheduleInfoDto originalSchedule = this.loanServiceFacade.retrieveOriginalLoanSchedule(loanId);
String memberAccountIdParam = request.getParameter("memberAccountId");
if (StringUtils.isNotBlank(memberAccountIdParam)) {
Integer memberId = Integer.valueOf(memberAccountIdParam);
LoanBO member = loan.findMemberById(memberId);
if (member != null) {
SessionUtils.setAttribute(CustomerConstants.CUSTOMER_NAME, member.getCustomer().getDisplayName(), request);
SessionUtils.setAttribute(CustomerConstants.GLOBAL_CUST_NUM, member.getCustomer().getGlobalCustNum(), request);
}
}
SessionUtils.setAttribute(Constants.BUSINESS_KEY, loan, request);
SessionUtils.setAttribute(Constants.ORIGINAL_SCHEDULE_AVAILABLE, originalSchedule.hasOriginalInstallments(), request);
SessionUtils.setAttribute(Constants.VIEW_DATE, viewDate, request);
String forward = errors.hasErrors() ? ActionForwards.getLoanRepaymentScheduleFailure.toString() : ActionForwards.getLoanRepaymentSchedule.toString();
addErrors(request, getActionErrors(errors));
return mapping.findForward(forward);
}
// Method exists to support unit testing
LoanBO getLoan(Integer loanId) {
return loanDao.findById(loanId);
}
@TransactionDemarcate(joinToken = true)
public ActionForward viewOriginalSchedule(final ActionMapping mapping,
@SuppressWarnings("unused") final ActionForm form, final HttpServletRequest request,
@SuppressWarnings("unused") final HttpServletResponse response) throws Exception {
UserContext userContext = getUserContext(request);
Integer loanId = Integer.valueOf(request.getParameter(ACCOUNT_ID));
LoanBO loan = (LoanBO) SessionUtils.getAttribute(BUSINESS_KEY, request);
boolean originalSchedule = ( request.getParameter("individual") == null ? true : false);
OriginalScheduleInfoDto dto = loanServiceFacade.retrieveOriginalLoanSchedule(loanId);
SessionUtils.setAttribute("originalSchedule", originalSchedule, request);
SessionUtils.setAttribute(CustomerConstants.DISBURSEMENT_DATE, dto.getDisbursementDate(), request);
SessionUtils.setAttribute(CustomerConstants.LOAN_AMOUNT, dto.getLoanAmount(), request);
SessionUtils.setCollectionAttribute(LoanConstants.ORIGINAL_INSTALLMENTS, dto.getOriginalLoanScheduleInstallment(), request);
return mapping.findForward(ActionForwards.viewOriginalSchedule.name());
}
@TransactionDemarcate(joinToken = true)
public ActionForward viewStatusHistory(final ActionMapping mapping,
@SuppressWarnings("unused") final ActionForm form, final HttpServletRequest request,
@SuppressWarnings("unused") final HttpServletResponse response) throws Exception {
UserContext userContext = getUserContext(request);
String globalAccountNum = request.getParameter(GLOBAL_ACCOUNT_NUM);
LoanBO loan = this.loanDao.findByGlobalAccountNum(globalAccountNum);
loan.updateDetails(userContext);
List<AccountStatusChangeHistoryEntity> accStatusChangeHistory = new ArrayList<AccountStatusChangeHistoryEntity>(loan.getAccountStatusChangeHistory());
SessionUtils.setCollectionAttribute(STATUS_HISTORY, accStatusChangeHistory, request);
return mapping.findForward(ActionForwards.viewStatusHistory.toString());
}
@TransactionDemarcate(joinToken = true)
public ActionForward validate(final ActionMapping mapping, final ActionForm form, final HttpServletRequest request,
@SuppressWarnings("unused") final HttpServletResponse response) throws Exception {
LoanAccountActionForm loanAccountForm = (LoanAccountActionForm) form;
String perspective = loanAccountForm.getPerspective();
if (perspective != null) {
setPerspective(request, perspective);
}
ActionForwards actionForward = null;
String method = (String) request.getAttribute(METHODCALLED);
if (method.equals(Methods.getPrdOfferings.toString())) {
actionForward = ActionForwards.getPrdOfferigs_failure;
} else if (method.equals(Methods.load.toString())) {
actionForward = ActionForwards.getPrdOfferigs_success;
} else if (method.equals(Methods.schedulePreview.toString())) {
actionForward = ActionForwards.load_success;
} else if (method.equals(Methods.managePreview.toString())) {
actionForward = ActionForwards.managepreview_failure;
} else if (method.equals(Methods.preview.toString())) {
actionForward = ActionForwards.preview_failure;
}
return mapping.findForward(actionForward.toString());
}
private void setMonthlySchedule(final LoanAccountActionForm loanActionForm,
final MeetingDetailsEntity meetingDetails) {
// 2 is signaled as the schedule is monthly on jsp page (Monthradio
// button is clicked)
loanActionForm.setFrequency("2");
loanActionForm.setRecurMonth(meetingDetails.getRecurAfter().toString());
loanActionForm.setDayRecurMonth(meetingDetails.getRecurAfter().toString());
if (meetingDetails.getWeekRank() != null) {
// 2 is signaled as the day of week is chosen on jsp page. For ex,
// First Monday of every 2 months
loanActionForm.setMonthType("2");
loanActionForm.setMonthRank(meetingDetails.getWeekRank().getValue().toString());
loanActionForm.setMonthWeek(meetingDetails.getWeekDay().getValue().toString());
} else {
// 1 is signaled as the day of month is chosen on jsp page. For ex,
// 12 th day of every 1 month
loanActionForm.setMonthType("1");
loanActionForm.setMonthDay(meetingDetails.getDayNumber().toString());
}
}
private void setWeeklySchedule(final LoanAccountActionForm loanActionForm, final MeetingDetailsEntity meetingDetail) {
// 1 is signaled as the schedule is weekly on jsp page. Week radio
// button is clicked
loanActionForm.setFrequency("1");
loanActionForm.setRecurWeek(meetingDetail.getRecurAfter().toString());
loanActionForm.setWeekDay(meetingDetail.getWeekDay().getValue().toString());
}
public ActionForward redoLoanBegin(final ActionMapping mapping, @SuppressWarnings("unused") final ActionForm form,
@SuppressWarnings("unused") final HttpServletRequest request,
@SuppressWarnings("unused") final HttpServletResponse response) throws Exception {
return mapping.findForward(ActionForwards.beginRedoLoanDisbursal_success.toString());
}
/**
* Resolve repayment start date according to given disbursement date
* <p/>
* The resulting date equates to the disbursement date plus MIN_DAYS_BETWEEN_DISBURSAL_AND_FIRST_REPAYMENT_DAY: e.g.
* If disbursement date is 18 June 2008, and MIN_DAYS_BETWEEN_DISBURSAL_AND_FIRST_REPAYMENT_DAY is 1 then the
* repayment start date would be 19 June 2008
*
* @return Date repaymentStartDate
* @throws PersistenceException
*/
private Date resolveRepaymentStartDate(final Date disbursementDate) {
int minDaysInterval = configurationPersistence.getConfigurationValueInteger(
MIN_DAYS_BETWEEN_DISBURSAL_AND_FIRST_REPAYMENT_DAY);
final GregorianCalendar repaymentStartDate = new GregorianCalendar();
repaymentStartDate.setTime(disbursementDate);
repaymentStartDate.add(Calendar.DAY_OF_WEEK, minDaysInterval);
return repaymentStartDate.getTime();
}
@SuppressWarnings("unchecked")
private List<LoanAccountDetailsDto> getLoanAccountDetailsFromSession(final HttpServletRequest request)
throws PageExpiredException {
return (List<LoanAccountDetailsDto>) SessionUtils.getAttribute("loanAccountDetailsView", request);
}
@TransactionDemarcate(joinToken = true)
public ActionForward manage(final ActionMapping mapping, final ActionForm form, final HttpServletRequest request,
@SuppressWarnings("unused") final HttpServletResponse response) throws Exception {
LoanAccountActionForm loanActionForm = (LoanAccountActionForm) form;
String globalAccountNum = request.getParameter(GLOBAL_ACCOUNT_NUM);
CustomerBO customer = getCustomerFromRequest(request);
if (isGlimEnabled() || isNewGlimEnabled()) {
populateGlimAttributes(request, loanActionForm, globalAccountNum, customer);
}
String recurMonth = customer.getCustomerMeeting().getMeeting().getMeetingDetails().getRecurAfter().toString();
handleRepaymentsIndependentOfMeetingIfConfigured(request, loanActionForm, recurMonth);
LoanBO loanBO = new LoanDaoHibernate(new GenericDaoHibernate()).findByGlobalAccountNum(globalAccountNum);
UserContext userContext = getUserContext(request);
loanBO.setUserContext(userContext);
SessionUtils.setAttribute(PROPOSED_DISBURSAL_DATE, loanBO.getDisbursementDate(), request);
SessionUtils.removeAttribute(LOANOFFERING, request);
LoanOfferingBO loanOffering = getLoanOffering(loanBO.getLoanOffering().getPrdOfferingId(), userContext.getLocaleId());
loanActionForm.setInstallmentRange(loanBO.getMaxMinNoOfInstall());
loanActionForm.setLoanAmountRange(loanBO.getMaxMinLoanAmount());
MaxMinInterestRate interestRateRange = loanBO.getMaxMinInterestRate();
loanActionForm.setMaxInterestRate(interestRateRange.getMaxLoanAmount());
loanActionForm.setMinInterestRate(interestRateRange.getMinLoanAmount());
loanActionForm.setExternalId(loanBO.getExternalId());
if (null != loanBO.getFund()) {
loanActionForm.setLoanOfferingFund(loanBO.getFund().getFundId().toString());
}
if (configService.isRepaymentIndepOfMeetingEnabled()) {
MeetingDetailsEntity meetingDetail = loanBO.getLoanMeeting().getMeetingDetails();
loanActionForm.setMonthDay("");
loanActionForm.setMonthWeek("0");
loanActionForm.setMonthRank("0");
if (meetingDetail.getRecurrenceTypeEnum() == RecurrenceType.MONTHLY) {
setMonthlySchedule(loanActionForm, meetingDetail);
} else {
setWeeklySchedule(loanActionForm, meetingDetail);
}
}
setSessionAtributeForGLIM(request, loanBO);
SessionUtils.setAttribute(LOANOFFERING, loanOffering, request);
// Retrieve and set into the session all collateral types from the
// lookup_value_locale table associated with the current user context
// locale
SessionUtils.setCollectionAttribute(MasterConstants.COLLATERAL_TYPES, legacyMasterDao.getLookUpEntity(
MasterConstants.COLLATERAL_TYPES).getCustomValueListElements(),
request);
SessionUtils.setCollectionAttribute(MasterConstants.BUSINESS_ACTIVITIES,
legacyMasterDao.findValueListElements(MasterConstants.LOAN_PURPOSES), request);
SessionUtils.setCollectionAttribute(CUSTOM_FIELDS, new ArrayList<CustomFieldDefinitionEntity>(), request);
SessionUtils.setAttribute(RECURRENCEID, loanBO.getLoanMeeting().getMeetingDetails().getRecurrenceTypeEnum()
.getValue(), request);
SessionUtils.setAttribute(RECURRENCENAME, loanBO.getLoanMeeting().getMeetingDetails().getRecurrenceType()
.getRecurrenceName(), request);
SessionUtils.setCollectionAttribute(LOANFUNDS, getFunds(loanOffering), request);
setRequestAttributesForEditPage(request, loanBO);
InformationOrderServiceFacade informationOrderServiceFacade = ApplicationContextProvider.getBean(InformationOrderServiceFacade.class);
SessionUtils.setCollectionAttribute("detailsInformationOrder", informationOrderServiceFacade.getInformationOrder("CreateLoan"), request);
setFormAttributes(loanBO, form, request);
return mapping.findForward(ActionForwards.manage_success.toString());
}
public static void setSessionAtributeForGLIM(final HttpServletRequest request, LoanBO loanBO)
throws PageExpiredException {
if (loanBO.isGroupLoanAccount() && loanBO.getParentAccount() == null) {
SessionUtils.setAttribute("isGroupLoan", Boolean.TRUE, request);
} else {
SessionUtils.setAttribute("isGroupLoan", Boolean.FALSE, request);
}
}
private LoanBO getLoanBO(final HttpServletRequest request) throws PageExpiredException, ServiceException {
LoanBO loanBOInSession = (LoanBO) SessionUtils.getAttribute(Constants.BUSINESS_KEY, request);
return loanBusinessService.getAccount(loanBOInSession.getAccountId());
}
private void setRequestAttributesForEditPage(final HttpServletRequest request, final LoanBO loanBO) {
request.setAttribute("accountState", loanBO.getState());
request.setAttribute(MasterConstants.COLLATERAL_TYPES, legacyMasterDao.getLookUpEntity(
MasterConstants.COLLATERAL_TYPES).getCustomValueListElements());
request.setAttribute("collateralTypeId", loanBO.getCollateralTypeId());
}
private CustomerBO getCustomerFromRequest(final HttpServletRequest request) {
String customerId = request.getParameter(CUSTOMER_ID);
if (isNotEmpty(customerId)) {
return getCustomer(Integer.valueOf(customerId));
}
return null;
}
private void populateGlimAttributes(final HttpServletRequest request, final LoanAccountActionForm loanActionForm,
final String globalAccountNum, final CustomerBO customer) throws PageExpiredException, ServiceException {
GlimSessionAttributes glimSessionAttributes = getGlimSpecificPropertiesToSet(loanActionForm, globalAccountNum,
customer, legacyMasterDao.findValueListElements(MasterConstants.LOAN_PURPOSES));
glimSessionAttributes.putIntoSession(request);
}
GlimSessionAttributes getGlimSpecificPropertiesToSet(final LoanAccountActionForm loanActionForm,
final String globalAccountNum, final CustomerBO customer, final List<ValueListElement> businessActivities)
throws ServiceException {
if ((configService.isGlimEnabled() || configService.isNewGlimEnabled()) && customer.isGroup()) {
List<LoanBO> individualLoans = loanBusinessService.getAllChildrenForParentGlobalAccountNum(globalAccountNum);
List<ClientBO> activeClientsUnderGroup = this.customerDao.findActiveClientsUnderGroup(customer);
List<LoanAccountDetailsDto> clientDetails = populateClientDetailsFromLoan(activeClientsUnderGroup, individualLoans, businessActivities);
loanActionForm.setClientDetails(clientDetails);
loanActionForm.setClients(fetchClientIdsWithMatchingLoans(individualLoans, clientDetails));
return new GlimSessionAttributes(LoanConstants.GLIM_ENABLED_VALUE, activeClientsUnderGroup, LoanConstants.LOAN_ACCOUNT_OWNER_IS_GROUP_YES);
}
return new GlimSessionAttributes(LoanConstants.GLIM_DISABLED_VALUE);
}
private List<String> fetchClientIdsWithMatchingLoans(final List<LoanBO> individualLoans,
final List<LoanAccountDetailsDto> clientDetails) {
List<String> clientIds = new ArrayList<String>();
for (final LoanAccountDetailsDto clientDetail : clientDetails) {
LoanBO loanMatchingClientDetail = (LoanBO) CollectionUtils.find(individualLoans, new Predicate() {
@Override
public boolean evaluate(final Object object) {
return ((LoanBO) object).getCustomer().getCustomerId().toString()
.equals(clientDetail.getClientId());
}
});
if (loanMatchingClientDetail != null) {
clientIds.add(clientDetail.getClientId());
} else {
clientIds.add("");
}
}
return clientIds;
}
List<LoanAccountDetailsDto> populateClientDetailsFromLoan(final List<ClientBO> activeClientsUnderGroup,
final List<LoanBO> individualLoans, final List<ValueListElement> businessActivities) {
List<LoanAccountDetailsDto> clientDetails = new ArrayList<LoanAccountDetailsDto>();
for (final ClientBO client : activeClientsUnderGroup) {
LoanAccountDetailsDto clientDetail = new LoanAccountDetailsDto();
clientDetail.setClientId(getStringValue(client.getCustomerId()));
clientDetail.setClientName(client.getDisplayName());
LoanBO loanAccount = (LoanBO) CollectionUtils.find(individualLoans, new Predicate() {
@Override
public boolean evaluate(final Object object) {
return client.getCustomerId().equals(((LoanBO) object).getCustomer().getCustomerId());
}
});
if (loanAccount != null) {
final Integer businessActivityId = loanAccount.getBusinessActivityId();
if (businessActivityId != null) {
clientDetail.setBusinessActivity(Integer.toString(businessActivityId));
ValueListElement businessActivityElement = (ValueListElement) CollectionUtils.find(
businessActivities, new Predicate() {
@Override
public boolean evaluate(final Object object) {
return ((ValueListElement) object).getId().equals(businessActivityId);
}
});
if (businessActivityElement != null) {
clientDetail.setBusinessActivityName(businessActivityElement.getName());
}
}
clientDetail.setLoanAmount(loanAccount.getLoanAmount() != null ? loanAccount.getLoanAmount().toString()
: "0.0");
}
clientDetails.add(clientDetail);
}
return clientDetails;
}
@TransactionDemarcate(joinToken = true)
public ActionForward managePrevious(final ActionMapping mapping, @SuppressWarnings("unused") final ActionForm form,
final HttpServletRequest request, @SuppressWarnings("unused") final HttpServletResponse response)
throws Exception {
setRequestAttributesForEditPage(request, getLoanBO(request));
return mapping.findForward(ActionForwards.manageprevious_success.toString());
}
@TransactionDemarcate(joinToken = true)
public ActionForward managePreview(final ActionMapping mapping, final ActionForm form,
final HttpServletRequest request, @SuppressWarnings("unused") final HttpServletResponse response)
throws Exception {
LoanAccountActionForm loanAccountForm = (LoanAccountActionForm) form;
if (isGlimEnabled() || isNewGlimEnabled()) {
performGlimSpecificOnManagePreview(request, loanAccountForm);
addEmptyBuisnessActivities(loanAccountForm.getClientDetails());
}
if (null != getFund(loanAccountForm)) {
request.setAttribute("sourceOfFunds", getFund(loanAccountForm).getFundName());
}
resetBusinessActivity(request, (LoanAccountActionForm) form);
return mapping.findForward(ActionForwards.managepreview_success.toString());
}
private FundBO getFund(LoanAccountActionForm loanAccountActionForm) {
FundBO fund = null;
if (!StringUtils.isBlank(loanAccountActionForm.getLoanOfferingFund())) {
Short fundId = loanAccountActionForm.getLoanOfferingFundValue();
if (fundId != 0) {
fund = this.fundDao.findById(fundId);
}
}
return fund;
}
private void performGlimSpecificOnManagePreview(final HttpServletRequest request,final LoanAccountActionForm loanAccountForm) throws PageExpiredException {
CustomerBO customer = getCustomer(loanAccountForm.getCustomerIdValue());
setGlimEnabledSessionAttributes(request, customer.isGroup());
if (customer.isGroup()) {
List<LoanAccountDetailsDto> loanAccountDetailsView = populateDetailsForSelectedClients(loanAccountForm.getClientDetails(), loanAccountForm.getClients());
SessionUtils.setCollectionAttribute("loanAccountDetailsView", loanAccountDetailsView, request);
}
}
private List<LoanAccountDetailsDto> populateDetailsForSelectedClients(final List<LoanAccountDetailsDto> clientDetails, final List<String> selectedClients) {
List<LoanAccountDetailsDto> loanAccountDetailsView = new ArrayList<LoanAccountDetailsDto>();
for (final String clientId : selectedClients) {
if (StringUtils.isNotEmpty(clientId)) {
LoanAccountDetailsDto matchingClientDetail = (LoanAccountDetailsDto) CollectionUtils.find(
clientDetails, new Predicate() {
@Override
public boolean evaluate(final Object object) {
return ((LoanAccountDetailsDto) object).getClientId().equals(clientId);
}
});
if (matchingClientDetail != null) {
setGovernmentIdAndPurpose(matchingClientDetail);
loanAccountDetailsView.add(matchingClientDetail);
}
}
}
return loanAccountDetailsView;
}
private void setGovernmentIdAndPurpose(final LoanAccountDetailsDto clientDetail) {
clientDetail.setBusinessActivityName(findBusinessActivityName(clientDetail.getBusinessActivity()));
clientDetail.setGovermentId(findGovernmentId(getIntegerValue(clientDetail.getClientId())));
}
private void resetBusinessActivity(final HttpServletRequest request,final LoanAccountActionForm loanAccountActionForm) throws PageExpiredException, Exception {
SessionUtils.removeAttribute(MasterConstants.BUSINESS_ACTIVITIE_NAME, request);
if (loanAccountActionForm.getBusinessActivityIdValue() != null) {
SessionUtils.setAttribute(MasterConstants.BUSINESS_ACTIVITIE_NAME, getNameForBusinessActivityEntity(
loanAccountActionForm.getBusinessActivityIdValue()), request);
}
}
private String findGovernmentId(final Integer clientId) {
ClientBO client = (ClientBO) this.customerDao.findCustomerById(clientId);
String governmentId = client.getGovernmentId();
return StringUtils.isBlank(governmentId) ? "-" : governmentId;
}
private String findBusinessActivityName(final String businessActivity) {
List<ValueListElement> businessActEntity = legacyMasterDao.findValueListElements(MasterConstants.LOAN_PURPOSES);
for (ValueListElement busact : businessActEntity) {
if (busact.getId().toString().equals(businessActivity)) {
return busact.getName();
}
}
return null;
}
@TransactionDemarcate(validateAndResetToken = true)
public ActionForward cancel(final ActionMapping mapping, @SuppressWarnings("unused") final ActionForm form,
@SuppressWarnings("unused") final HttpServletRequest request,
@SuppressWarnings("unused") final HttpServletResponse response) throws Exception {
return mapping.findForward(ActionForwards.loan_detail_page.toString());
}
@TransactionDemarcate(validateAndResetToken = true)
public ActionForward update(final ActionMapping mapping, final ActionForm form, final HttpServletRequest request,
@SuppressWarnings("unused") final HttpServletResponse response) throws Exception {
LoanBO loanBOInSession = (LoanBO) SessionUtils.getAttribute(Constants.BUSINESS_KEY, request);
LoanBO loanBO = loanBusinessService.findBySystemId(loanBOInSession.getGlobalAccountNum());
checkVersionMismatch(loanBOInSession.getVersionNo(), loanBO.getVersionNo());
loanBO.setVersionNo(loanBOInSession.getVersionNo());
loanBO.setUserContext(getUserContext(request));
setInitialObjectForAuditLogging(loanBO);
LoanAccountActionForm loanAccountActionForm = (LoanAccountActionForm) form;
CustomerBO customer = loanBO.getCustomer();
MeetingBO newMeetingForRepaymentDay = null;
boolean isRepaymentIndepOfMeetingEnabled = configService.isRepaymentIndepOfMeetingEnabled();
if (isRepaymentIndepOfMeetingEnabled) {
newMeetingForRepaymentDay = this.createNewMeetingForRepaymentDay(request, loanAccountActionForm, customer);
}
loanBO.setExternalId(loanAccountActionForm.getExternalId());
if ((configService.isGlimEnabled() || configService.isNewGlimEnabled()) && customer.isGroup()) {
List<LoanAccountDetailsDto> loanAccountDetailsList = getLoanAccountDetailsFromSession(request);
List<LoanBO> individualLoans = loanDao.findIndividualLoans(Integer.valueOf(
loanBO.getAccountId()));
handleIndividualLoans(loanBO, loanAccountActionForm, isRepaymentIndepOfMeetingEnabled,
loanAccountDetailsList, individualLoans, getUserContext(request).getPreferredLocale());
request.setAttribute(CUSTOMER_ID, loanBO.getCustomer().getCustomerId().toString());
}
loanBO.updateLoan(loanAccountActionForm.isInterestDedAtDisbValue(), new Money(loanBO.getCurrency(),
loanAccountActionForm.getLoanAmount()), loanAccountActionForm.getInterestDoubleValue(),
loanAccountActionForm.getNoOfInstallmentsValue(), loanAccountActionForm
.getDisbursementDateValue(getUserContext(request).getPreferredLocale()), loanAccountActionForm
.getGracePeriodDurationValue(), loanAccountActionForm.getBusinessActivityIdValue(),
loanAccountActionForm.getCollateralNote(), loanAccountActionForm.getCollateralTypeIdValue(),
loanAccountActionForm.getCustomFields(), isRepaymentIndepOfMeetingEnabled, newMeetingForRepaymentDay,
getFund(loanAccountActionForm));
loanBOInSession = null;
SessionUtils.removeAttribute(Constants.BUSINESS_KEY, request);
SessionUtils.setAttribute(Constants.BUSINESS_KEY, loanBO, request);
return mapping.findForward(ActionForwards.update_success.toString());
}
void handleIndividualLoans(final LoanBO loanBO, final LoanAccountActionForm loanAccountActionForm,
final boolean isRepaymentIndepOfMeetingEnabled, final List<LoanAccountDetailsDto> loanAccountDetailsList,
final List<LoanBO> individualLoans, final Locale locale) throws AccountException, ServiceException {
List<Integer> foundLoans = new ArrayList<Integer>();
for (final LoanAccountDetailsDto loanAccountDetail : loanAccountDetailsList) {
Predicate predicateOldGlim = new Predicate() {
@Override
public boolean evaluate(final Object object) {
return ((LoanBO) object).getCustomer().getCustomerId().toString().equals(
loanAccountDetail.getClientId());
}
};
LoanBO individualLoan = (LoanBO) CollectionUtils.find(individualLoans, predicateOldGlim);
if (individualLoan == null) {
// glimLoanUpdater.createIndividualLoan(loanAccountActionForm, loanBO, isRepaymentIndepOfMeetingEnabled,
// loanAccountDetail);
} else {
foundLoans.add(individualLoan.getAccountId());
try {
if (!AccountingRules.isGroupLoanWithMembers() && loanAccountActionForm.getLoanAmount() != null) {
loanAccountDetail.setLoanAmount(loanAccountActionForm.getLoanAmountAsBigDecimal().divide(individualLoan.calcFactorOfEntireLoan(), 10, RoundingMode.HALF_UP).toString());
}
glimLoanUpdater.updateIndividualLoan(
loanAccountActionForm.getDisbursementDateValue(locale), loanAccountActionForm.getInterestDoubleValue(), loanAccountActionForm.getNoOfInstallmentsValue(),loanAccountDetail, individualLoan);
} catch (InvalidDateException e) {
e.printStackTrace();
}
}
}
for (LoanBO loan : individualLoans) {
if (!foundLoans.contains(loan.getAccountId())) {
glimLoanUpdater.delete(loan);
}
}
}
/**
* Create new meeting for the repayment day.
* <p/>
* Depending on the recurrence id (WEEKLY or MONTHLY) a MeetingBO will be created and returned
*
* @throws InvalidDateException
*/
private MeetingBO createNewMeetingForRepaymentDay(final HttpServletRequest request,
final LoanAccountActionForm loanAccountActionForm, final CustomerBO customer) throws MeetingException,
InvalidDateException {
MeetingBO newMeetingForRepaymentDay = null;
Short recurrenceId = Short.valueOf(loanAccountActionForm.getRecurrenceId());
final Date repaymentStartDate = this.resolveRepaymentStartDate(loanAccountActionForm
.getDisbursementDateValue(getUserContext(request).getPreferredLocale()));
if (RecurrenceType.WEEKLY.getValue().equals(recurrenceId)) {
newMeetingForRepaymentDay = new MeetingBO(WeekDay.getWeekDay(Short.valueOf(loanAccountActionForm
.getWeekDay())), Short.valueOf(loanAccountActionForm.getRecurWeek()), repaymentStartDate,
MeetingType.LOAN_INSTALLMENT, customer.getCustomerMeeting().getMeeting().getMeetingPlace());
} else if (RecurrenceType.MONTHLY.getValue().equals(recurrenceId)) {
if (loanAccountActionForm.getMonthType().equals("1")) {
newMeetingForRepaymentDay = new MeetingBO(Short.valueOf(loanAccountActionForm.getMonthDay()), Short
.valueOf(loanAccountActionForm.getDayRecurMonth()), repaymentStartDate,
MeetingType.LOAN_INSTALLMENT, customer.getCustomerMeeting().getMeeting().getMeetingPlace());
} else {
newMeetingForRepaymentDay = new MeetingBO(Short.valueOf(loanAccountActionForm.getMonthWeek()), Short
.valueOf(loanAccountActionForm.getRecurMonth()), repaymentStartDate,
MeetingType.LOAN_INSTALLMENT, customer.getCustomerMeeting().getMeeting().getMeetingPlace(),
Short.valueOf(loanAccountActionForm.getMonthRank()));
}
}
return newMeetingForRepaymentDay;
}
private LoanOfferingBO getLoanOffering(Short loanOfferingId, short localeId) throws Exception {
return loanPrdBusinessService.getLoanOffering(loanOfferingId, localeId);
}
private String getNameForBusinessActivityEntity(final Integer entityId) throws Exception {
if (entityId != null) {
return legacyMasterDao.getMessageForLookupEntity(entityId);
}
return "";
}
private void setFormAttributes(final LoanBO loan, final ActionForm form, final HttpServletRequest request)
throws Exception {
LoanAccountActionForm loanAccountActionForm = (LoanAccountActionForm) form;
loanAccountActionForm.setStateSelected(getStringValue(loan.getAccountState().getId()));
loanAccountActionForm.setLoanAmount(getStringValue(loan.getLoanAmount()));
java.util.Date proposedDisbursement = (Date) SessionUtils.getAttribute(PROPOSED_DISBURSAL_DATE, request);
loanAccountActionForm.setDisbursementDate(DateUtils.getUserLocaleDate(getUserContext(request)
.getPreferredLocale(), DateUtils.toDatabaseFormat(proposedDisbursement)));
loanAccountActionForm.setIntDedDisbursement(loan.isInterestDeductedAtDisbursement() ? "1" : "0");
loanAccountActionForm.setBusinessActivityId(getStringValue(loan.getBusinessActivityId()));
if (loan.getCollateralTypeId() != null) {
loanAccountActionForm.setCollateralTypeId(getStringValue(loan.getCollateralTypeId()));
}
loanAccountActionForm.setCollateralNote(loan.getCollateralNote());
loanAccountActionForm.setInterestRate(getDoubleStringForInterest(loan.getInterestRate()));
loanAccountActionForm.setNoOfInstallments(getStringValue(loan.getNoOfInstallments()));
loanAccountActionForm.setGracePeriodDuration(getStringValue(loan.getGracePeriodDuration()));
loanAccountActionForm.setCustomFields(new ArrayList<CustomFieldDto>());
loanAccountActionForm.setOriginalDisbursementDate(new java.sql.Date(loan.getDisbursementDate().getTime()));
}
static class GlimSessionAttributes {
private final Integer isGlimEnabled;
private final List<ClientBO> clients;
private final String loanAccountOwnerIsGroup;
GlimSessionAttributes(final int isGlimEnabled, final List<ClientBO> clients,
final String loanAccountOwnerIsGroup) {
this.isGlimEnabled = isGlimEnabled;
this.clients = clients;
this.loanAccountOwnerIsGroup = loanAccountOwnerIsGroup;
}
@SuppressWarnings("unchecked")
GlimSessionAttributes(final int isGlimEnabled) {
this(isGlimEnabled, Collections.EMPTY_LIST, "");
}
void putIntoSession(final HttpServletRequest request) throws PageExpiredException {
SessionUtils.setAttribute(LOAN_INDIVIDUAL_MONITORING_IS_ENABLED, isGlimEnabled, request);
Boolean GroupLoanWithMembers = AccountingRules.isGroupLoanWithMembers();
if (null != GroupLoanWithMembers && GroupLoanWithMembers != false) {
SessionUtils.setAttribute("GroupLoanWithMembers", GroupLoanWithMembers.booleanValue(), request);
}
SessionUtils.setCollectionAttribute(CLIENT_LIST, clients, request);
SessionUtils.setAttribute(LOAN_ACCOUNT_OWNER_IS_A_GROUP, loanAccountOwnerIsGroup, request);
}
@Override
public int hashCode() {
final int PRIME = 31;
int result = 1;
result = PRIME * result + (clients == null ? 0 : clients.hashCode());
result = PRIME * result + (isGlimEnabled == null ? 0 : isGlimEnabled.hashCode());
result = PRIME * result + (loanAccountOwnerIsGroup == null ? 0 : loanAccountOwnerIsGroup.hashCode());
return result;
}
@Override
public boolean equals(final Object obj) {
if (this == obj) {
return true;
}
if (obj == null) {
return false;
}
if (getClass() != obj.getClass()) {
return false;
}
final GlimSessionAttributes other = (GlimSessionAttributes) obj;
if (clients == null) {
if (other.clients != null) {
return false;
}
} else if (!clients.equals(other.clients)) {
return false;
}
if (isGlimEnabled == null) {
if (other.isGlimEnabled != null) {
return false;
}
} else if (!isGlimEnabled.equals(other.isGlimEnabled)) {
return false;
}
if (loanAccountOwnerIsGroup == null) {
if (other.loanAccountOwnerIsGroup != null) {
return false;
}
} else if (!loanAccountOwnerIsGroup.equals(other.loanAccountOwnerIsGroup)) {
return false;
}
return true;
}
@Override
public String toString() {
return "isGlimEnabled:" + isGlimEnabled + " loanAccountOwnerIsAGroup:" + loanAccountOwnerIsGroup
+ " clients:" + clients;
}
}
private void storeObjectOnSessionForUseInJspPage(final HttpServletRequest request, final String objectKey,
final Serializable value) throws PageExpiredException {
SessionUtils.setAttribute(objectKey, value, request);
}
private void storeCollectionOnSessionForUseInJspPage(final HttpServletRequest request, final String collectionKey,
final Collection<? extends Serializable> collectionValue) throws PageExpiredException {
SessionUtils.setCollectionAttribute(collectionKey, collectionValue, request);
}
private boolean isGlimEnabled() {
return new ConfigurationBusinessService().isGlimEnabled();
}
private boolean isNewGlimEnabled(){
return new ConfigurationBusinessService().isNewGlimEnabled();
}
private void setGlimEnabledSessionAttributes(final HttpServletRequest request, final boolean isGroup)
throws PageExpiredException {
storeObjectOnSessionForUseInJspPage(request, LoanConstants.LOAN_INDIVIDUAL_MONITORING_IS_ENABLED,
LoanConstants.GLIM_ENABLED_VALUE);
if (isGroup) {
storeObjectOnSessionForUseInJspPage(request, LoanConstants.LOAN_ACCOUNT_OWNER_IS_A_GROUP,
LoanConstants.LOAN_ACCOUNT_OWNER_IS_GROUP_YES);
}
}
private void handleRepaymentsIndependentOfMeetingIfConfigured(final HttpServletRequest request,
final LoanAccountActionForm loanActionForm, final String recurMonth) throws PageExpiredException, Exception {
if (configService.isRepaymentIndepOfMeetingEnabled()) {
storeObjectOnSessionForUseInJspPage(request, LoanConstants.REPAYMENT_SCHEDULES_INDEPENDENT_OF_MEETING_IS_ENABLED, Integer.valueOf(1));
storeObjectOnSessionForUseInJspPage(request, LoanConstants.LOANACCOUNTOWNERISACLIENT, LoanConstants.LOAN_ACCOUNT_OWNER_IS_GROUP_YES);
storeCollectionOnSessionForUseInJspPage(request, MeetingConstants.WEEKDAYSLIST, fillWeekDaysWithLocalizedName(new FiscalCalendarRules().getWorkingDays()));
storeCollectionOnSessionForUseInJspPage(request, MeetingConstants.WEEKRANKLIST, RankOfDay.getRankOfDayList());
loanActionForm.setRecurMonth(recurMonth);
}
}
private List<WeekDay> fillWeekDaysWithLocalizedName(List<WeekDay> weekDays) {
//FIXME localization from properties is being used
// When Application is started and LSIM is enabled then WeekDay.getName() remains empty causing the list of the weekdays on loan creation page to be 1,2,3..7 instead of names
// We have done localization of Months using Joda type in http://mifosforge.jira.com/browse/MIFOS-3970
// see the usage of WeekDay#setName and it initializes with empty name.
for (WeekDay weekDay : weekDays) {
if (StringUtils.isBlank(weekDay.getName())) {
weekDay.setWeekdayName(ApplicationContextProvider.getBean(MessageLookup.class).lookup(weekDay.getPropertiesKey()));
}
}
return weekDays;
}
@TransactionDemarcate(joinToken = true)
@Override
public ActionForward captureQuestionResponses(final ActionMapping mapping, final ActionForm form,
final HttpServletRequest request, @SuppressWarnings("unused") final HttpServletResponse response)
throws Exception {
request.setAttribute(METHODCALLED, "captureQuestionResponses");
LoanAccountActionForm actionForm = (LoanAccountActionForm) form;
setPerspective(request, actionForm.getPerspective());
ActionErrors errors = createLoanQuestionnaire.validateResponses(request, actionForm);
if (errors != null && !errors.isEmpty()) {
addErrors(request, errors);
return mapping.findForward(ActionForwards.captureQuestionResponses.toString());
}
return createLoanQuestionnaire.rejoinFlow(mapping);
}
@TransactionDemarcate(joinToken = true)
@Override
public ActionForward editQuestionResponses(
final ActionMapping mapping, final ActionForm form,
final HttpServletRequest request, @SuppressWarnings("unused") final HttpServletResponse response) throws Exception {
request.setAttribute(METHODCALLED, "editQuestionResponses");
return createLoanQuestionnaire.editResponses(mapping, request, (LoanAccountActionForm) form);
}
private ActionErrors getActionErrors(Errors errors) {
ActionErrors actionErrors = new ActionErrors();
if (errors.hasErrors()) {
for (ErrorEntry errorEntry : errors.getErrorEntries()) {
ActionMessage actionMessage;
if (errorEntry.hasErrorArgs()) {
actionMessage = new ActionMessage(errorEntry.getErrorCode(), errorEntry.getArgs().toArray());
} else {
actionMessage = new ActionMessage(errorEntry.getErrorCode(), errorEntry.getFieldName());
}
actionErrors.add(errorEntry.getErrorCode(), actionMessage);
}
}
return actionErrors;
}
public void setCustomerDao(CustomerDao customerDao) {
this.customerDao = customerDao;
}
@TransactionDemarcate(saveToken = true)
public ActionForward getGroupLoanAccountDetails(final ActionMapping mapping, final ActionForm form, final HttpServletRequest request,
@SuppressWarnings("unused") final HttpServletResponse response) throws Exception {
LoanAccountActionForm loanAccountActionForm = (LoanAccountActionForm) form;
loanAccountActionForm.clearDetailsForLoan();
String globalAccountNum = request.getParameter(GLOBAL_ACCOUNT_NUM);
UserContext userContext = getUserContext(request);
LoanInformationDto loanInformationDto;
List<LoanInformationDto> memberloanInformationDtos = new ArrayList<LoanInformationDto>();
try {
loanInformationDto = this.loanAccountServiceFacade.retrieveLoanInformation(globalAccountNum);
for (LoanBO member : loanDao.findByGlobalAccountNum(globalAccountNum).getMemberAccounts()) {
memberloanInformationDtos.add(this.loanAccountServiceFacade.retrieveLoanInformation(member.getGlobalAccountNum()));
request.getSession().setAttribute("guarantyInformation" , loanAccountServiceFacade.handleGuaranties(this.loanAccountServiceFacade.retrieveLoanInformation(member.getGlobalAccountNum())));
}
}
catch (MifosRuntimeException e) {
if (e.getCause() instanceof ApplicationException) {
throw (ApplicationException) e.getCause();
}
throw e;
}
final String accountStateNameLocalised = ApplicationContextProvider.getBean(MessageLookup.class).lookup(loanInformationDto.getAccountStateName());
SessionUtils.removeThenSetAttribute("accountStateNameLocalised", accountStateNameLocalised, request);
final String gracePeriodTypeNameLocalised = ApplicationContextProvider.getBean(MessageLookup.class).lookup(loanInformationDto.getGracePeriodTypeName());
SessionUtils.removeThenSetAttribute("gracePeriodTypeNameLocalised", gracePeriodTypeNameLocalised, request);
final String interestTypeNameLocalised = ApplicationContextProvider.getBean(MessageLookup.class).lookup(loanInformationDto.getInterestTypeName());
SessionUtils.removeThenSetAttribute("interestTypeNameLocalised", interestTypeNameLocalised, request);
final Set<String> accountFlagStateEntityNamesLocalised = new HashSet<String>();
for (String name : loanInformationDto.getAccountFlagNames()) {
accountFlagStateEntityNamesLocalised.add(ApplicationContextProvider.getBean(MessageLookup.class).lookup(name));
}
SessionUtils.setCollectionAttribute("accountFlagNamesLocalised", accountFlagStateEntityNamesLocalised, request);
SessionUtils.removeAttribute(BUSINESS_KEY, request);
Integer loanIndividualMonitoringIsEnabled = configurationPersistence.getConfigurationValueInteger(LOAN_INDIVIDUAL_MONITORING_IS_ENABLED);
if (null != loanIndividualMonitoringIsEnabled && loanIndividualMonitoringIsEnabled.intValue() != 0) {
SessionUtils.setAttribute(LOAN_INDIVIDUAL_MONITORING_IS_ENABLED, loanIndividualMonitoringIsEnabled.intValue(), request);
}
Boolean GroupLoanWithMembers = AccountingRules.isGroupLoanWithMembers();
if (null != GroupLoanWithMembers && GroupLoanWithMembers != false) {
SessionUtils.setAttribute("GroupLoanWithMembers", GroupLoanWithMembers.booleanValue(), request);
}
List<ValueListElement> allLoanPurposes = this.loanProductDao.findAllLoanPurposes();
SessionUtils.setCollectionAttribute(MasterConstants.BUSINESS_ACTIVITIES, allLoanPurposes, request);
if ((null != loanIndividualMonitoringIsEnabled && 0 != loanIndividualMonitoringIsEnabled.intValue()
&& loanInformationDto.isGroup() ) || loanInformationDto.isGroupLoanWithMembersEnabled() ||
(null != GroupLoanWithMembers && GroupLoanWithMembers!=false)) {
List<LoanAccountDetailsDto> loanAccountDetails = this.loanAccountServiceFacade.retrieveLoanAccountDetails(loanInformationDto);
addEmptyBuisnessActivities(loanAccountDetails);
SessionUtils.setCollectionAttribute("loanAccountDetailsView", loanAccountDetails, request);
}
SessionUtils.setCollectionAttribute(CUSTOM_FIELDS, new ArrayList<CustomFieldDefinitionEntity>(), request);
// Retrieve and set into the session all collateral types from the
// lookup_value_locale table associated with the current user context
// locale
SessionUtils.setCollectionAttribute(MasterConstants.COLLATERAL_TYPES, legacyMasterDao.getLookUpEntity(
MasterConstants.COLLATERAL_TYPES).getCustomValueListElements(), request);
SessionUtils.setAttribute(AccountConstants.LAST_PAYMENT_ACTION, loanBusinessService.getLastPaymentAction(loanInformationDto.getAccountId()), request);
SessionUtils.removeThenSetAttribute("loanInformationDto", loanInformationDto, request);
//loanAccountServiceFacade.putLoanBusinessKeyInSession(globalAccountNum, request);
List<LoanActivityDto> activities = loanInformationDto.getRecentAccountActivity();
for (LoanActivityDto activity : activities) {
activity.setUserPrefferedDate(DateUtils.getUserLocaleDate(userContext.getPreferredLocale(), activity.getActionDate().toString()));
}
SessionUtils.removeAttribute(RECENTACCOUNTACTIVITIES, request.getSession());
SessionUtils.setCollectionAttribute(RECENTACCOUNTACTIVITIES, activities, request);
request.setAttribute(CustomerConstants.SURVEY_KEY, loanInformationDto.getAccountSurveys());
request.setAttribute(CustomerConstants.SURVEY_COUNT, loanInformationDto.getActiveSurveys());
request.setAttribute(AccountConstants.SURVEY_KEY, loanInformationDto.getAccountSurveys());
Integer administrativeDocumentsIsEnabled = configurationPersistence.getConfigurationValueInteger(ADMINISTRATIVE_DOCUMENT_IS_ENABLED);
if (null != administrativeDocumentsIsEnabled && administrativeDocumentsIsEnabled.intValue() == 1) {
SessionUtils.setCollectionAttribute(AdminDocumentsContants.ADMINISTRATIVEDOCUMENTSLIST,
legacyAdminDocumentDao.getAllActiveAdminDocuments(), request);
SessionUtils.setCollectionAttribute(AdminDocumentsContants.ADMINISTRATIVEDOCUMENTSACCSTATEMIXLIST,
legacyAdminDocAccStateMixDao.getAllMixedAdminDocuments(), request);
}
List<QuestionGroupInstanceDetail> questions = new ArrayList<QuestionGroupInstanceDetail>();
QuestionnaireServiceFacade questionnaireServiceFacade = questionnaireServiceFacadeLocator.getService(request);
questions.addAll(questionnaireServiceFacade.getQuestionGroupInstancesWithUnansweredQuestionGroups(loanInformationDto.getAccountId(), "Create", "Loan"));
questions.addAll(questionnaireServiceFacade.getQuestionGroupInstancesWithUnansweredQuestionGroups(loanInformationDto.getAccountId(), "Approve", "Loan"));
questions.addAll(questionnaireServiceFacade.getQuestionGroupInstancesWithUnansweredQuestionGroups(loanInformationDto.getAccountId(), "View", "Loan"));
questions.addAll(questionnaireServiceFacade.getQuestionGroupInstancesWithUnansweredQuestionGroups(loanInformationDto.getAccountId(), "Disburse", "Loan"));
questions.addAll(questionnaireServiceFacade.getQuestionGroupInstancesWithUnansweredQuestionGroups(loanInformationDto.getAccountId(), "Close", "Loan"));
SessionUtils.setCollectionAttribute("questionGroups", questions, request);
SessionUtils.setCollectionAttribute("personalInformationOrder", informationOrderServiceFacade.getInformationOrder("Loan"), request);
LoanBO loan = getLoan(loanInformationDto.getAccountId());
SessionUtils.setAttribute(Constants.BUSINESS_KEY, loan, request);
LoanAccountAction.setSessionAtributeForGLIM(request, loan);
setCurrentPageUrl(request, loan);
setQuestionGroupInstances(request, loan);
setOverpayments(request, loan);
List<RepaymentScheduleInstallment> installments = loan.toRepaymentScheduleDto(userContext.getPreferredLocale());
loanAccountActionForm.initializeInstallments(installments);
return mapping.findForward(ActionForwards.get_success.toString());
}
@TransactionDemarcate(joinToken = true)
public ActionForward getGroupLoanRepaymentSchedule(final ActionMapping mapping,
final ActionForm form, final HttpServletRequest request,
@SuppressWarnings("unused") final HttpServletResponse response) throws Exception {
LoanAccountActionForm loanAccountActionForm = (LoanAccountActionForm) form;
UserContext userContext = getUserContext(request);
Integer grouploanId = Integer.valueOf(request.getParameter(ACCOUNT_ID));
Locale locale = userContext.getPreferredLocale();
Date viewDate = loanAccountActionForm.getScheduleViewDateValue(locale);
LoanBO groupLoan = getLoan(grouploanId);
LoanAccountAction.setSessionAtributeForGLIM(request, groupLoan);
groupLoan.updateDetails(userContext);
Errors errors = loanBusinessService.computeExtraInterest(groupLoan, viewDate);
if (errors.hasErrors()) {
loanAccountActionForm.resetScheduleViewDate();
}
List<LoanBO> membersAccount = this.loanDao.findIndividualLoans(grouploanId);
List<Integer> membersAccountIds = getMembersAccountId(membersAccount);
OriginalScheduleInfoDto generatedSchedule = OriginalScheduleInfoHelper.sumRepaymentSchedule(getMembersSchedule(membersAccountIds));
SessionUtils.setAttribute(Constants.BUSINESS_KEY, groupLoan, request);
SessionUtils.setAttribute(Constants.VIEW_DATE, viewDate, request);
SessionUtils.setAttribute(Constants.ORIGINAL_SCHEDULE_AVAILABLE, generatedSchedule.hasOriginalInstallments(), request);
SessionUtils.setAttribute("isNewGropLoan", Boolean.TRUE, request);
String forward = errors.hasErrors() ? ActionForwards.getLoanRepaymentScheduleFailure.toString() : ActionForwards.getLoanRepaymentSchedule.toString();
addErrors(request, getActionErrors(errors));
return mapping.findForward(forward);
}
private List<Integer> getMembersAccountId(List<LoanBO> membersAccount){
List<Integer> ids = new ArrayList<Integer>();
for (LoanBO member : membersAccount) {
ids.add(member.getAccountId());
}
return ids;
}
private List<OriginalScheduleInfoDto> getMembersSchedule(List<Integer> membersIds) {
List<OriginalScheduleInfoDto> membersSchedule = new ArrayList<OriginalScheduleInfoDto>();
membersSchedule.add(this.loanServiceFacade.retrieveOriginalLoanSchedule(membersIds.get(0)));
return membersSchedule;
}
public ActionForward getDetails(final ActionMapping mapping, final ActionForm form, final HttpServletRequest request,
@SuppressWarnings("unused") final HttpServletResponse response) throws Exception {
String globalAccountNum = request.getParameter(GLOBAL_ACCOUNT_NUM);
ActionForward forward = null;
if (loanDao.findByGlobalAccountNum(globalAccountNum).isParentGroupLoanAccount()) {
forward = mapping.findForward("getGroupLoanAccountDetails");
}
else {
forward = mapping.findForward("get");
}
return forward;
}
}