View Javadoc

1   /**
2    * Copyright 2004-2013 The Kuali Foundation
3    *
4    * Licensed under the Educational Community License, Version 2.0 (the "License");
5    * you may not use this file except in compliance with the License.
6    * You may obtain a copy of the License at
7    *
8    * http://www.opensource.org/licenses/ecl2.php
9    *
10   * Unless required by applicable law or agreed to in writing, software
11   * distributed under the License is distributed on an "AS IS" BASIS,
12   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13   * See the License for the specific language governing permissions and
14   * limitations under the License.
15   */
16  package org.kuali.hr.lm.balancetransfer.service;
17  
18  import java.math.BigDecimal;
19  import java.util.ArrayList;
20  import java.util.List;
21  import java.util.Map;
22  
23  import org.apache.commons.collections.CollectionUtils;
24  import org.apache.commons.lang3.StringUtils;
25  import org.kuali.hr.lm.LMConstants;
26  import org.kuali.hr.lm.accrual.AccrualCategory;
27  import org.kuali.hr.lm.balancetransfer.BalanceTransfer;
28  import org.kuali.hr.lm.leaveblock.LeaveBlock;
29  import org.kuali.hr.time.HrBusinessObject;
30  import org.kuali.hr.time.service.base.TkServiceLocator;
31  import org.kuali.hr.time.util.HrBusinessObjectMaintainableImpl;
32  import org.kuali.hr.time.util.TKContext;
33  import org.kuali.hr.time.util.TKUtils;
34  import org.kuali.rice.kew.api.document.DocumentStatus;
35  import org.kuali.rice.kew.api.exception.WorkflowException;
36  import org.kuali.rice.kns.document.MaintenanceDocument;
37  import org.kuali.rice.krad.bo.DocumentHeader;
38  import org.kuali.rice.krad.service.DocumentService;
39  import org.kuali.rice.krad.service.KRADServiceLocatorWeb;
40  import org.kuali.rice.krad.util.ObjectUtils;
41  
42  @SuppressWarnings("deprecation")
43  public class BalanceTransferMaintainableImpl extends
44  		HrBusinessObjectMaintainableImpl {
45  
46  	private static final long serialVersionUID = -789218061798169466L;
47  
48  	@Override
49  	public void saveBusinessObject() {
50  		// TODO Auto-generated method stub
51  		super.saveBusinessObject();
52  	}
53  	
54  	@Override
55  	public HrBusinessObject getObjectById(String id) {
56  		return TkServiceLocator.getBalanceTransferService().getBalanceTransferById(id);
57  	}
58  
59  
60  	@Override
61      public void doRouteStatusChange(DocumentHeader documentHeader) {
62          //ProcessDocReport pdr = new ProcessDocReport(true, "");
63          String documentId = documentHeader.getDocumentNumber();
64          BalanceTransfer balanceTransfer = (BalanceTransfer)this.getDataObject();
65          DocumentService documentService = KRADServiceLocatorWeb.getDocumentService();
66  
67          DocumentStatus newDocumentStatus = documentHeader.getWorkflowDocument().getStatus();
68          String routedByPrincipalId = documentHeader.getWorkflowDocument().getRoutedByPrincipalId();
69          if (DocumentStatus.ENROUTE.equals(newDocumentStatus)
70                  && CollectionUtils.isEmpty(balanceTransfer.getLeaveBlocks())) {
71          	// this is a balance transfer on a system scheduled time off leave block
72          	if(StringUtils.isNotEmpty(balanceTransfer.getSstoId())) {
73          		try {
74  	                MaintenanceDocument md = (MaintenanceDocument)KRADServiceLocatorWeb.getDocumentService().getByDocumentHeaderId(documentId);
75  	                balanceTransfer = TkServiceLocator.getBalanceTransferService().transferSsto(balanceTransfer);
76  	                md.getNewMaintainableObject().setDataObject(balanceTransfer);
77  	                documentService.saveDocument(md);
78  	            }
79  	            catch (WorkflowException e) {
80  	                LOG.error("caught exception while handling doRouteStatusChange -> documentService.getByDocumentHeaderId(" + documentHeader.getDocumentNumber() + "). ", e);
81  	                throw new RuntimeException("caught exception while handling doRouteStatusChange -> documentService.getByDocumentHeaderId(" + documentHeader.getDocumentNumber() + "). ", e);
82  	            }	
83          	} else {
84                  //when transfer document is routed, initiate the balance transfer - creating the leave blocks
85  	            try {
86  	                MaintenanceDocument md = (MaintenanceDocument)KRADServiceLocatorWeb.getDocumentService().getByDocumentHeaderId(documentId);
87  	
88  	                balanceTransfer = TkServiceLocator.getBalanceTransferService().transfer(balanceTransfer);
89  	                md.getNewMaintainableObject().setDataObject(balanceTransfer);
90  	                documentService.saveDocument(md);
91  	            }
92  	            catch (WorkflowException e) {
93  	                LOG.error("caught exception while handling doRouteStatusChange -> documentService.getByDocumentHeaderId(" + documentHeader.getDocumentNumber() + "). ", e);
94  	                throw new RuntimeException("caught exception while handling doRouteStatusChange -> documentService.getByDocumentHeaderId(" + documentHeader.getDocumentNumber() + "). ", e);
95  	            }
96          	}
97          } else if (DocumentStatus.DISAPPROVED.equals(newDocumentStatus)) {
98          	/**
99          	 * TODO: Remove disapproval action
100         	 */
101         	// this is a balance transfer on a system scheduled time off leave block
102 
103             if(StringUtils.isNotEmpty(balanceTransfer.getSstoId())) {
104         		// put two accrual service generated leave blocks back, one accrued, one usage
105         		List<LeaveBlock> lbList = buildSstoLeaveBlockList(balanceTransfer);    			
106     			TkServiceLocator.getLeaveBlockService().saveLeaveBlocks(lbList);
107         	}
108             //When transfer document is disapproved, set all leave block's request statuses to disapproved.
109             for(LeaveBlock lb : balanceTransfer.getLeaveBlocks()) {
110                 if(ObjectUtils.isNotNull(lb)) {
111                     lb.setRequestStatus(LMConstants.REQUEST_STATUS.DISAPPROVED);
112                     TkServiceLocator.getLeaveBlockService().deleteLeaveBlock(lb.getLmLeaveBlockId(), routedByPrincipalId);
113                 }
114             }
115             //update status of document and associated leave blocks.
116         } else if (DocumentStatus.FINAL.equals(newDocumentStatus)) {
117             //When transfer document moves to final, set all leave block's request statuses to approved.
118             for(LeaveBlock lb : balanceTransfer.getLeaveBlocks()) {
119                 if(ObjectUtils.isNotNull(lb)) {
120                 	//TODO: What happens when an approver edits the fields in the transfer doc before approving?
121                     lb.setRequestStatus(LMConstants.REQUEST_STATUS.APPROVED);
122                     TkServiceLocator.getLeaveBlockService().updateLeaveBlock(lb, routedByPrincipalId);
123                 }
124             }
125             List<LeaveBlock> leaveBlocks = TkServiceLocator.getLeaveBlockService().getLeaveBlocksForDocumentId(balanceTransfer.getLeaveCalendarDocumentId());
126             //List<LeaveBlock> leaveBlocks = TkServiceLocator.getLeaveBlockService().getLeaveBlocksForDate(balanceTransfer.getPrincipalId(), balanceTransfer.getEffectiveDate());
127             for(LeaveBlock lb : leaveBlocks) {
128             	if(StringUtils.equals(lb.getAccrualCategory(),balanceTransfer.getFromAccrualCategory())
129             			&& StringUtils.equals(lb.getLeaveBlockType(),LMConstants.LEAVE_BLOCK_TYPE.CARRY_OVER_ADJUSTMENT)) {
130             		//KPME-2253
131                 	BigDecimal adjustment = new BigDecimal(0);
132                 	if(balanceTransfer.getTransferAmount() != null)
133                 		adjustment = adjustment.add(balanceTransfer.getTransferAmount().abs());
134                 	if(balanceTransfer.getForfeitedAmount() != null)
135                 		adjustment = adjustment.add(balanceTransfer.getForfeitedAmount().abs());
136                 	BigDecimal adjustedLeaveAmount = lb.getLeaveAmount().abs().subtract(adjustment);
137                 	lb.setLeaveAmount(adjustedLeaveAmount.negate());
138             		TkServiceLocator.getLeaveBlockService().updateLeaveBlock(lb, routedByPrincipalId);
139             	}
140             }
141         } else if (DocumentStatus.CANCELED.equals(newDocumentStatus)) {
142             //When transfer document is canceled, set all leave block's request statuses to deferred
143 
144             for(LeaveBlock lb : balanceTransfer.getLeaveBlocks()) {
145                 if(ObjectUtils.isNotNull(lb)) {
146                     lb.setRequestStatus(LMConstants.REQUEST_STATUS.DEFERRED);
147                     TkServiceLocator.getLeaveBlockService().updateLeaveBlock(lb, routedByPrincipalId);
148                 }
149             }
150         }
151     }
152 
153 	private List<LeaveBlock> buildSstoLeaveBlockList(BalanceTransfer bt) {
154 		String leaveDocId = CollectionUtils.isNotEmpty(bt.getLeaveBlocks())? bt.getLeaveBlocks().get(0).getDocumentId() : "";
155 		List<LeaveBlock> lbList = new ArrayList<LeaveBlock>();
156 		AccrualCategory fromAC = TkServiceLocator.getAccrualCategoryService().getAccrualCategory(bt.getFromAccrualCategory(), bt.getEffectiveDate());
157 		
158 		LeaveBlock accruedLeaveBlock = new LeaveBlock();
159 		accruedLeaveBlock.setAccrualCategory(bt.getFromAccrualCategory());
160 		accruedLeaveBlock.setLeaveDate(bt.getEffectiveDate());
161 		accruedLeaveBlock.setPrincipalId(bt.getPrincipalId());
162 		accruedLeaveBlock.setEarnCode(fromAC.getEarnCode());
163 		accruedLeaveBlock.setDateAndTime(TKUtils.getCurrentTimestamp());
164 		accruedLeaveBlock.setAccrualGenerated(true);
165 		accruedLeaveBlock.setBlockId(0L);
166 		accruedLeaveBlock.setScheduleTimeOffId(bt.getSstoId());
167 		accruedLeaveBlock.setLeaveAmount(bt.getTransferAmount());
168 		accruedLeaveBlock.setLeaveBlockType(LMConstants.LEAVE_BLOCK_TYPE.ACCRUAL_SERVICE);
169 		accruedLeaveBlock.setRequestStatus(LMConstants.REQUEST_STATUS.APPROVED);
170 		accruedLeaveBlock.setDocumentId(leaveDocId);
171 		accruedLeaveBlock.setPrincipalIdModified(TKContext.getPrincipalId());
172 		lbList.add(accruedLeaveBlock);
173 		
174 		LeaveBlock usageLeaveBlock = new LeaveBlock();
175 		usageLeaveBlock.setAccrualCategory(bt.getFromAccrualCategory());
176 		usageLeaveBlock.setLeaveDate(bt.getEffectiveDate());
177 		usageLeaveBlock.setPrincipalId(bt.getPrincipalId());
178 		usageLeaveBlock.setEarnCode(fromAC.getEarnCode());
179 		usageLeaveBlock.setDateAndTime(TKUtils.getCurrentTimestamp());
180 		usageLeaveBlock.setAccrualGenerated(true);
181 		usageLeaveBlock.setBlockId(0L);
182 		usageLeaveBlock.setScheduleTimeOffId(bt.getSstoId());
183 		usageLeaveBlock.setLeaveAmount(bt.getTransferAmount().negate());
184 		usageLeaveBlock.setLeaveBlockType(LMConstants.LEAVE_BLOCK_TYPE.ACCRUAL_SERVICE);
185 		usageLeaveBlock.setRequestStatus(LMConstants.REQUEST_STATUS.APPROVED);
186 		usageLeaveBlock.setDocumentId(leaveDocId);
187 		usageLeaveBlock.setPrincipalIdModified(TKContext.getPrincipalId());
188 		lbList.add(usageLeaveBlock);
189 		
190 		return lbList;
191 	}
192 }