/* * The Kuali Financial System, a comprehensive financial management system for higher education. * * Copyright 2005-2014 The Kuali Foundation * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as * published by the Free Software Foundation, either version 3 of the * License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU Affero General Public License for more details. * * You should have received a copy of the GNU Affero General Public License * along with this program. If not, see <http://www.gnu.org/licenses/>. */ package org.kuali.kfs.coa.document; import java.util.ArrayList; import java.util.HashMap; import java.util.HashSet; import java.util.List; import java.util.Map; import java.util.Set; import org.apache.commons.lang.StringUtils; import org.kuali.kfs.coa.businessobject.AccountDelegate; import org.kuali.kfs.coa.businessobject.AccountDelegateGlobal; import org.kuali.kfs.coa.businessobject.AccountDelegateGlobalDetail; import org.kuali.kfs.coa.businessobject.AccountDelegateModel; import org.kuali.kfs.coa.businessobject.AccountDelegateModelDetail; import org.kuali.kfs.coa.businessobject.AccountGlobalDetail; import org.kuali.kfs.coa.service.AccountDelegateService; import org.kuali.kfs.sys.KFSConstants; import org.kuali.kfs.sys.KFSKeyConstants; import org.kuali.kfs.sys.context.SpringContext; import org.kuali.kfs.sys.document.FinancialSystemGlobalMaintainable; import org.kuali.rice.coreservice.framework.parameter.ParameterService; import org.kuali.rice.kns.document.MaintenanceDocument; import org.kuali.rice.krad.bo.PersistableBusinessObject; import org.kuali.rice.krad.maintenance.MaintenanceLock; import org.kuali.rice.krad.service.BusinessObjectService; import org.kuali.rice.krad.util.GlobalVariables; import org.kuali.rice.krad.util.ObjectUtils; /** * This class overrides the base {@link FinancialSystemGlobalMaintainable} to generate the specific maintenance locks for Global delegates * and to help with using delegate models * * @see OrganizationRoutingModelName */ public class AccountDelegateGlobalMaintainableImpl extends FinancialSystemGlobalMaintainable { private static final org.apache.log4j.Logger LOG = org.apache.log4j.Logger.getLogger(AccountDelegateGlobalMaintainableImpl.class); @Override /** * show the max account delegates info message * @see org.kuali.rice.kns.maintenance.KualiMaintainableImpl#processAfterNew(org.kuali.rice.kns.document.MaintenanceDocument, java.util.Map) */ public void processAfterNew(MaintenanceDocument document, Map<String, String[]> requestParameters) { super.processAfterNew(document, requestParameters); this.displayMaxAccountDelegatesInfoMessage(); } /** * Informational message about max account delegates */ protected void displayMaxAccountDelegatesInfoMessage() { String maxAccountDelegatesString = SpringContext.getBean(ParameterService.class).getParameterValueAsString(AccountDelegateGlobal.class, KFSConstants.ChartApcParms.MAXIMUM_ACCOUNT_DELEGATES); if(maxAccountDelegatesString != null && !maxAccountDelegatesString.isEmpty()){ GlobalVariables.getMessageMap().putInfo(KFSConstants.GLOBAL_ERRORS, KFSKeyConstants.INFO_DOCUMENT_DELEGATE_MAXIMUM_ACCOUNT_DELEGATES, maxAccountDelegatesString); } } /** * This method is used for the creation of a delegate from a {@link OrganizationRoutingModelName} * * @see org.kuali.rice.kns.maintenance.KualiMaintainableImpl#setupNewFromExisting() */ @Override public void setupNewFromExisting( MaintenanceDocument document, Map<String,String[]> parameters ) { super.setupNewFromExisting( document, parameters ); AccountDelegateGlobal globalDelegate = (AccountDelegateGlobal) this.getBusinessObject(); globalDelegate.setVersionNumber(1L); this.setBusinessObject(globalDelegate); // 1. if model name, chart of accounts, and org code are all present // then let's see if we've actually got a model record if (!StringUtils.isBlank(globalDelegate.getModelName()) && !StringUtils.isBlank(globalDelegate.getModelChartOfAccountsCode()) && !StringUtils.isBlank(globalDelegate.getModelOrganizationCode())) { Map pkMap = new HashMap(); pkMap.put("accountDelegateModelName", globalDelegate.getModelName()); pkMap.put("chartOfAccountsCode", globalDelegate.getModelChartOfAccountsCode()); pkMap.put("organizationCode", globalDelegate.getModelOrganizationCode()); AccountDelegateModel globalDelegateTemplate = (AccountDelegateModel) SpringContext.getBean(BusinessObjectService.class).findByPrimaryKey(AccountDelegateModel.class, pkMap); if (globalDelegateTemplate != null) { // 2. if there is a model record, then let's populate the global delegate // based on that for (AccountDelegateModelDetail model : globalDelegateTemplate.getAccountDelegateModelDetails()) { if (model.isActive()) { // only populate with active models AccountDelegateGlobalDetail newDelegate = new AccountDelegateGlobalDetail(model); // allow deletion of the new delegate from the global delegate newDelegate.setNewCollectionRecord(true); globalDelegate.getDelegateGlobals().add(newDelegate); } } } } } @Override public String getLockingDocumentId() { String lock = super.getLockingDocumentId(); if (StringUtils.isNotBlank(lock)) return lock; else { AccountDelegateService accountDelegateService = SpringContext.getBean(AccountDelegateService.class); lock = accountDelegateService.getLockingDocumentId(this, getDocumentNumber()); return lock; } } /** * This creates the particular locking representation for this global document. * * @see org.kuali.rice.kns.maintenance.Maintainable#generateMaintenanceLocks() */ @Override public List<MaintenanceLock> generateMaintenanceLocks() { // create locking rep for each combination of account and object code List<MaintenanceLock> maintenanceLocks = new ArrayList(); AccountDelegateGlobal delegateGlobal = (AccountDelegateGlobal) getBusinessObject(); // hold all the locking representations in a set to make sure we don't get any duplicates Set<String> lockingRepresentations = new HashSet<String>(); MaintenanceLock maintenanceLock; if (ObjectUtils.isNotNull(delegateGlobal)) { for (AccountGlobalDetail accountGlobalDetail : delegateGlobal.getAccountGlobalDetails()) { for (AccountDelegateGlobalDetail delegateGlobalDetail : delegateGlobal.getDelegateGlobals()) { StringBuilder lockRep = new StringBuilder(); lockRep.append(AccountDelegate.class.getName()); lockRep.append(KFSConstants.Maintenance.AFTER_CLASS_DELIM); lockRep.append("chartOfAccountsCode"); lockRep.append(KFSConstants.Maintenance.AFTER_FIELDNAME_DELIM); lockRep.append(accountGlobalDetail.getChartOfAccountsCode()); lockRep.append(KFSConstants.Maintenance.AFTER_VALUE_DELIM); lockRep.append("accountNumber"); lockRep.append(KFSConstants.Maintenance.AFTER_FIELDNAME_DELIM); lockRep.append(accountGlobalDetail.getAccountNumber()); lockRep.append(KFSConstants.Maintenance.AFTER_VALUE_DELIM); lockRep.append("financialDocumentTypeCode"); lockRep.append(KFSConstants.Maintenance.AFTER_FIELDNAME_DELIM); lockRep.append(delegateGlobalDetail.getFinancialDocumentTypeCode()); lockRep.append(KFSConstants.Maintenance.AFTER_VALUE_DELIM); lockRep.append("accountDelegateSystemId"); lockRep.append(KFSConstants.Maintenance.AFTER_FIELDNAME_DELIM); lockRep.append(delegateGlobalDetail.getAccountDelegateUniversalId()); // FIXME above is a bit dangerous b/c it hard codes the attribute names, which could change (particularly // accountDelegateSystemId) - guess they should either be constants or obtained by looping through Delegate keys; // however, I copied this from elsewhere which had them hard-coded, so I'm leaving it for now if (!lockingRepresentations.contains(lockRep.toString())) { maintenanceLock = new MaintenanceLock(); maintenanceLock.setDocumentNumber(delegateGlobal.getDocumentNumber()); maintenanceLock.setLockingRepresentation(lockRep.toString()); maintenanceLocks.add(maintenanceLock); lockingRepresentations.add(lockRep.toString()); } lockRep = new StringBuilder(); lockRep.append(AccountDelegate.class.getName()); lockRep.append(KFSConstants.Maintenance.AFTER_CLASS_DELIM); lockRep.append("chartOfAccountsCode"); lockRep.append(KFSConstants.Maintenance.AFTER_FIELDNAME_DELIM); lockRep.append(accountGlobalDetail.getChartOfAccountsCode()); lockRep.append(KFSConstants.Maintenance.AFTER_VALUE_DELIM); lockRep.append("accountNumber"); lockRep.append(KFSConstants.Maintenance.AFTER_FIELDNAME_DELIM); lockRep.append(accountGlobalDetail.getAccountNumber()); lockRep.append(KFSConstants.Maintenance.AFTER_VALUE_DELIM); lockRep.append("financialDocumentTypeCode"); lockRep.append(KFSConstants.Maintenance.AFTER_FIELDNAME_DELIM); lockRep.append(delegateGlobalDetail.getFinancialDocumentTypeCode()); lockRep.append(KFSConstants.Maintenance.AFTER_VALUE_DELIM); lockRep.append("accountsDelegatePrmrtIndicator"); lockRep.append(KFSConstants.Maintenance.AFTER_FIELDNAME_DELIM); lockRep.append("true"); if (!lockingRepresentations.contains(lockRep.toString())) { maintenanceLock = new MaintenanceLock(); maintenanceLock.setDocumentNumber(delegateGlobal.getDocumentNumber()); maintenanceLock.setLockingRepresentation(lockRep.toString()); maintenanceLocks.add(maintenanceLock); lockingRepresentations.add(lockRep.toString()); } lockRep = new StringBuilder(); lockRep.append(AccountDelegateGlobal.class.getName()); lockRep.append(KFSConstants.Maintenance.AFTER_CLASS_DELIM); lockRep.append("chartOfAccountsCode"); lockRep.append(KFSConstants.Maintenance.AFTER_FIELDNAME_DELIM); lockRep.append(accountGlobalDetail.getChartOfAccountsCode()); lockRep.append(KFSConstants.Maintenance.AFTER_VALUE_DELIM); lockRep.append("accountNumber"); lockRep.append(KFSConstants.Maintenance.AFTER_FIELDNAME_DELIM); lockRep.append(accountGlobalDetail.getAccountNumber()); if (!lockingRepresentations.contains(lockRep.toString())) { maintenanceLock = new MaintenanceLock(); maintenanceLock.setDocumentNumber(delegateGlobal.getDocumentNumber()); maintenanceLock.setLockingRepresentation(lockRep.toString()); maintenanceLocks.add(maintenanceLock); lockingRepresentations.add(lockRep.toString()); } } } } return maintenanceLocks; } @Override public Class<? extends PersistableBusinessObject> getPrimaryEditedBusinessObjectClass() { return AccountDelegate.class; } /** * Overridden to update the delegations for currently routing documents; this also guarantees that the business * objects to change will be saved in a separate transaction * @see org.kuali.rice.kns.maintenance.KualiGlobalMaintainableImpl#saveBusinessObject() */ @Override public void saveBusinessObject() { final AccountDelegateGlobal accountDelegateGlobal = (AccountDelegateGlobal)this.getBusinessObject(); final AccountDelegateService accountDelegateService = SpringContext.getBean(AccountDelegateService.class); accountDelegateService.saveInactivationsForGlobalMaintenanceDocument(accountDelegateGlobal.generateDeactivationsToPersist()); accountDelegateService.saveChangesForGlobalMaintenanceDocument(accountDelegateGlobal.generateGlobalChangesToPersist()); accountDelegateService.updateDelegationRole(); } }