in twill-yarn/src/main/java/org/apache/twill/internal/appmaster/RunningContainers.java [367:416]
void handleCompleted(YarnContainerStatus status, Multiset<String> restartRunnables) {
containerLock.lock();
String containerId = status.getContainerId();
int exitStatus = status.getExitStatus();
ContainerState state = status.getState();
try {
removeContainerInfo(containerId);
Map<String, TwillContainerController> lookup = containers.column(containerId);
if (lookup.isEmpty()) {
// It's OK because if a container is stopped through removeLast, this would be empty.
return;
}
if (lookup.size() != 1) {
LOG.warn("More than one controller found for container {}", containerId);
}
if (exitStatus != ContainerExitCodes.SUCCESS) {
LOG.warn("Container {} exited abnormally with state {}, exit code {}.",
containerId, state, exitStatus);
if (shouldRetry(exitStatus)) {
LOG.info("Re-request the container {} for exit code {}.", containerId, exitStatus);
restartRunnables.add(lookup.keySet().iterator().next());
}
} else {
LOG.info("Container {} exited normally with state {}", containerId, state);
}
for (Map.Entry<String, TwillContainerController> completedEntry : lookup.entrySet()) {
String runnableName = completedEntry.getKey();
TwillContainerController controller = completedEntry.getValue();
controller.completed(exitStatus);
if (exitStatus == ContainerExitCodes.SUCCESS) {
if (!completedContainerCount.containsKey(runnableName)) {
completedContainerCount.put(runnableName, 0);
}
completedContainerCount.put(runnableName, completedContainerCount.get(runnableName) + 1);
}
removeInstanceId(runnableName, getInstanceId(controller.getRunId()));
resourceReport.removeRunnableResources(runnableName, containerId);
}
lookup.clear();
containerChange.signalAll();
} finally {
containerLock.unlock();
}
}