001 /** 002 * Copyright 2004-2012 The Kuali Foundation 003 * 004 * Licensed under the Educational Community License, Version 2.0 (the "License"); 005 * you may not use this file except in compliance with the License. 006 * You may obtain a copy of the License at 007 * 008 * http://www.opensource.org/licenses/ecl2.php 009 * 010 * Unless required by applicable law or agreed to in writing, software 011 * distributed under the License is distributed on an "AS IS" BASIS, 012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013 * See the License for the specific language governing permissions and 014 * limitations under the License. 015 */ 016 package org.kuali.hr.time.clocklog.service; 017 018 import org.apache.commons.lang.StringUtils; 019 import org.kuali.hr.time.assignment.Assignment; 020 import org.kuali.hr.time.calendar.CalendarEntries; 021 import org.kuali.hr.time.clocklog.ClockLog; 022 import org.kuali.hr.time.clocklog.dao.ClockLogDao; 023 import org.kuali.hr.time.service.base.TkServiceLocator; 024 import org.kuali.hr.time.task.Task; 025 import org.kuali.hr.time.timeblock.TimeBlock; 026 import org.kuali.hr.time.timesheet.TimesheetDocument; 027 import org.kuali.hr.time.util.TKContext; 028 import org.kuali.hr.time.util.TkConstants; 029 030 import java.math.BigDecimal; 031 import java.sql.Timestamp; 032 import java.util.ArrayList; 033 import java.util.List; 034 035 public class ClockLogServiceImpl implements ClockLogService { 036 037 private ClockLogDao clockLogDao; 038 039 public ClockLogServiceImpl() { 040 } 041 042 public void saveClockLog(ClockLog clockLog) { 043 clockLogDao.saveOrUpdate(clockLog); 044 } 045 046 @Override 047 public ClockLog processClockLog(Timestamp clockTimeStamp, Assignment assignment,CalendarEntries pe, String ip, java.sql.Date asOfDate, TimesheetDocument td, String clockAction, String principalId) { 048 return processClockLog(clockTimeStamp, assignment, pe, ip, asOfDate, td, clockAction, principalId, TKContext.getPrincipalId()); 049 } 050 051 @Override 052 public ClockLog processClockLog(Timestamp clockTimeStamp, Assignment assignment,CalendarEntries pe, String ip, java.sql.Date asOfDate, TimesheetDocument td, String clockAction, String principalId, String userPrincipalId) { 053 // process rules 054 Timestamp roundedClockTimestamp = TkServiceLocator.getGracePeriodService().processGracePeriodRule(clockTimeStamp, new java.sql.Date(pe.getBeginPeriodDateTime().getTime())); 055 056 ClockLog clockLog = TkServiceLocator.getClockLogService().buildClockLog(roundedClockTimestamp, new Timestamp(System.currentTimeMillis()), assignment, td, clockAction, ip, userPrincipalId); 057 TkServiceLocator.getClockLocationRuleService().processClockLocationRule(clockLog, asOfDate); 058 059 // If the clock action is clock out or lunch out, create a time block besides the clock log 060 if (StringUtils.equals(clockAction, TkConstants.CLOCK_OUT) || StringUtils.equals(clockAction, TkConstants.LUNCH_OUT)) { 061 processTimeBlock(clockLog, assignment, pe, td, clockAction, principalId); 062 } else { 063 //Save current clock log to get id for timeblock building 064 TkServiceLocator.getClockLogService().saveClockLog(clockLog); 065 } 066 067 return clockLog; 068 } 069 070 private void processTimeBlock(ClockLog clockLog, Assignment assignment, CalendarEntries pe, TimesheetDocument td, String clockAction, String principalId) { 071 ClockLog lastLog = null; 072 Timestamp lastClockTimestamp = null; 073 String beginClockLogId = null; 074 String endClockLogId = null; 075 076 if (StringUtils.equals(clockAction, TkConstants.LUNCH_OUT)) { 077 lastLog = TkServiceLocator.getClockLogService().getLastClockLog(principalId, TkConstants.CLOCK_IN); 078 } else if (StringUtils.equals(clockAction, TkConstants.CLOCK_OUT)) { 079 lastLog = TkServiceLocator.getClockLogService().getLastClockLog(principalId); 080 } 081 if (lastLog != null) { 082 lastClockTimestamp = lastLog.getClockTimestamp(); 083 beginClockLogId = lastLog.getTkClockLogId(); 084 } 085 //Save current clock log to get id for timeblock building 086 TkServiceLocator.getClockLogService().saveClockLog(clockLog); 087 endClockLogId = clockLog.getTkClockLogId(); 088 089 long beginTime = lastClockTimestamp.getTime(); 090 Timestamp beginTimestamp = new Timestamp(beginTime); 091 Timestamp endTimestamp = clockLog.getClockTimestamp(); 092 093 // New Time Blocks, pointer reference 094 List<TimeBlock> newTimeBlocks = td.getTimeBlocks(); 095 List<TimeBlock> referenceTimeBlocks = new ArrayList<TimeBlock>(td.getTimeBlocks().size()); 096 for (TimeBlock tb : td.getTimeBlocks()) { 097 referenceTimeBlocks.add(tb.copy()); 098 } 099 100 // Add TimeBlocks after we store our reference object! 101 List<TimeBlock> aList = TkServiceLocator.getTimeBlockService().buildTimeBlocks(assignment, assignment.getJob().getPayTypeObj().getRegEarnCode(), td, beginTimestamp, endTimestamp, BigDecimal.ZERO, BigDecimal.ZERO, true, false); 102 for (TimeBlock tb : aList) { 103 tb.setClockLogBeginId(beginClockLogId); 104 tb.setClockLogEndId(endClockLogId); 105 } 106 newTimeBlocks.addAll(aList); 107 108 //reset time block 109 TkServiceLocator.getTimesheetService().resetTimeBlock(newTimeBlocks); 110 111 //apply any rules for this action 112 TkServiceLocator.getTkRuleControllerService().applyRules(TkConstants.ACTIONS.CLOCK_OUT, newTimeBlocks, pe, td, principalId); 113 114 //call persist method that only saves added/deleted/changed timeblocks 115 TkServiceLocator.getTimeBlockService().saveTimeBlocks(referenceTimeBlocks, newTimeBlocks); 116 } 117 118 @Override 119 public ClockLog buildClockLog(Timestamp clockTimestamp, Timestamp originalTimestamp, Assignment assignment, TimesheetDocument timesheetDocument, String clockAction, String ip) { 120 return buildClockLog(clockTimestamp, originalTimestamp, assignment, timesheetDocument, clockAction, ip, TKContext.getPrincipalId()); 121 } 122 123 @Override 124 public ClockLog buildClockLog(Timestamp clockTimestamp, Timestamp originalTimestamp, Assignment assignment, TimesheetDocument timesheetDocument, String clockAction, String ip, String userPrincipalId) { 125 String principalId = timesheetDocument.getPrincipalId(); 126 127 ClockLog clockLog = new ClockLog(); 128 clockLog.setPrincipalId(principalId); 129 // AssignmentDescriptionKey assignmentDesc = TkServiceLocator.getAssignmentService().getAssignmentDescriptionKey(selectedAssign); 130 // Assignment assignment = TkServiceLocator.getAssignmentService().getAssignment(timesheetDocument, selectedAssign); 131 clockLog.setJob(timesheetDocument.getJob(assignment.getJobNumber())); 132 clockLog.setJobNumber(assignment.getJobNumber()); 133 clockLog.setWorkArea(assignment.getWorkArea()); 134 clockLog.setTkWorkAreaId(assignment.getWorkAreaObj().getTkWorkAreaId()); 135 136 String tkTaskId = null; 137 for (Task task : assignment.getWorkAreaObj().getTasks()) { 138 if (task.getTask().compareTo(assignment.getTask()) == 0) { 139 tkTaskId = task.getTkTaskId(); 140 break; 141 } 142 } 143 clockLog.setTask(assignment.getTask()); 144 clockLog.setTkTaskId(tkTaskId); 145 clockLog.setClockTimestampTimezone(TkServiceLocator.getTimezoneService().getUserTimezone()); 146 clockLog.setClockTimestamp(clockTimestamp); 147 clockLog.setClockAction(clockAction); 148 clockLog.setIpAddress(ip); 149 clockLog.setHrJobId(assignment.getJob().getHrJobId()); 150 clockLog.setUserPrincipalId(userPrincipalId); 151 // timestamp should be the original time without Grace Period rule applied 152 clockLog.setTimestamp(originalTimestamp); 153 154 return clockLog; 155 } 156 157 public void setClockLogDao(ClockLogDao clockLogDao) { 158 this.clockLogDao = clockLogDao; 159 } 160 161 public ClockLog getLastClockLog(String principalId) { 162 return clockLogDao.getLastClockLog(principalId); 163 } 164 165 public ClockLog getLastClockLog(String principalId, String clockAction) { 166 return clockLogDao.getLastClockLog(principalId, clockAction); 167 } 168 169 public List<ClockLog> getOpenClockLogs( CalendarEntries payCalendarEntry) { 170 return clockLogDao.getOpenClockLogs(payCalendarEntry); 171 } 172 173 @Override 174 public ClockLog getClockLog(String tkClockLogId) { 175 return clockLogDao.getClockLog(tkClockLogId); 176 } 177 178 }