001 /** 002 * Copyright (c) 2010 Yahoo! Inc. All rights reserved. 003 * Licensed under the Apache License, Version 2.0 (the "License"); 004 * you may not use this file except in compliance with the License. 005 * You may obtain a copy of the License at 006 * 007 * http://www.apache.org/licenses/LICENSE-2.0 008 * 009 * Unless required by applicable law or agreed to in writing, software 010 * distributed under the License is distributed on an "AS IS" BASIS, 011 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 012 * See the License for the specific language governing permissions and 013 * limitations under the License. See accompanying LICENSE file. 014 */ 015 package org.apache.oozie.command.coord; 016 017 import java.sql.Timestamp; 018 019 import org.apache.oozie.CoordinatorActionBean; 020 import org.apache.oozie.WorkflowJobBean; 021 import org.apache.oozie.XException; 022 import org.apache.oozie.service.Services; 023 import org.apache.oozie.service.StoreService; 024 import org.apache.oozie.store.CoordinatorStore; 025 import org.apache.oozie.store.StoreException; 026 import org.apache.oozie.store.WorkflowStore; 027 import org.apache.oozie.util.XLog; 028 import org.apache.oozie.util.db.SLADbOperations; 029 import org.apache.oozie.client.CoordinatorAction; 030 import org.apache.oozie.client.WorkflowJob; 031 import org.apache.oozie.client.SLAEvent.SlaAppType; 032 import org.apache.oozie.client.SLAEvent.Status; 033 import org.apache.oozie.command.CommandException; 034 035 public class CoordActionCheckCommand extends CoordinatorCommand<Void> { 036 private String actionId; 037 private int actionCheckDelay; 038 private final XLog log = XLog.getLog(getClass()); 039 private CoordinatorActionBean coordAction = null; 040 041 public CoordActionCheckCommand(String actionId, int actionCheckDelay) { 042 super("coord_action_check", "coord_action_check", 0, XLog.OPS); 043 this.actionId = actionId; 044 this.actionCheckDelay = actionCheckDelay; 045 } 046 047 protected Void call(CoordinatorStore cstore) throws StoreException, CommandException { 048 try { 049 //if the action has been updated, quit this command 050 Timestamp actionCheckTs = new Timestamp(System.currentTimeMillis() - actionCheckDelay * 1000); 051 Timestamp cactionLmt = coordAction.getLastModifiedTimestamp(); 052 if (cactionLmt.after(actionCheckTs)) { 053 log.info("The coord action :" + actionId + " has been udated. Ignore CoordActionCheckCommand!"); 054 return null; 055 } 056 if (coordAction.getStatus().equals(CoordinatorAction.Status.SUCCEEDED) 057 || coordAction.getStatus().equals(CoordinatorAction.Status.FAILED) 058 || coordAction.getStatus().equals(CoordinatorAction.Status.KILLED)) { 059 // do nothing 060 } 061 else { 062 incrJobCounter(1); 063 WorkflowStore wstore = Services.get().get(StoreService.class).getStore(WorkflowStore.class, cstore); 064 WorkflowJobBean wf = wstore.getWorkflow(coordAction.getExternalId(), false); 065 066 Status slaStatus = null; 067 068 if (wf.getStatus() == WorkflowJob.Status.SUCCEEDED) { 069 coordAction.setStatus(CoordinatorAction.Status.SUCCEEDED); 070 slaStatus = Status.SUCCEEDED; 071 } 072 else { 073 if (wf.getStatus() == WorkflowJob.Status.FAILED) { 074 coordAction.setStatus(CoordinatorAction.Status.FAILED); 075 slaStatus = Status.FAILED; 076 } 077 else { 078 if (wf.getStatus() == WorkflowJob.Status.KILLED) { 079 coordAction.setStatus(CoordinatorAction.Status.KILLED); 080 slaStatus = Status.KILLED; 081 } 082 else { 083 log.warn("Unexpected workflow " + wf.getId() + " STATUS " + wf.getStatus()); 084 cstore.updateCoordinatorAction(coordAction); 085 return null; 086 } 087 } 088 } 089 090 log.debug("Updating Coordintaor actionId :" + coordAction.getId() + "status to =" + coordAction.getStatus()); 091 cstore.updateCoordinatorAction(coordAction); 092 if (slaStatus != null) { 093 SLADbOperations.writeStausEvent(coordAction.getSlaXml(), coordAction.getId(), cstore, slaStatus, 094 SlaAppType.COORDINATOR_ACTION); 095 } 096 } 097 098 } 099 catch (XException ex) { 100 log.warn("CoordActionCheckCommand Failed ", ex); 101 throw new CommandException(ex); 102 } 103 return null; 104 } 105 106 @Override 107 protected Void execute(CoordinatorStore store) throws StoreException, CommandException { 108 log.info("STARTED CoordActionCheckCommand for actionId = " + actionId); 109 try { 110 coordAction = store.getEntityManager().find(CoordinatorActionBean.class, actionId); 111 setLogInfo(coordAction); 112 if (lock(coordAction.getJobId())) { 113 call(store); 114 } 115 else { 116 queueCallable(new CoordActionCheckCommand(actionId, actionCheckDelay), LOCK_FAILURE_REQUEUE_INTERVAL); 117 log.warn("CoordActionCheckCommand lock was not acquired - failed jobId=" + coordAction.getJobId() 118 + ", actionId=" + actionId + ". Requeing the same."); 119 } 120 } 121 catch (InterruptedException e) { 122 queueCallable(new CoordActionCheckCommand(actionId, actionCheckDelay), LOCK_FAILURE_REQUEUE_INTERVAL); 123 log.warn("CoordActionCheckCommand lock acquiring failed with exception " + e.getMessage() + " for jobId=" 124 + coordAction.getJobId() + ", actionId=" + actionId + " Requeing the same."); 125 } 126 finally { 127 log.info("ENDED CoordActionCheckCommand for actionId:" + actionId); 128 } 129 return null; 130 } 131 }