/*********************************************************************************************************************** * Copyright (C) 2010-2013 by the Stratosphere project (http://stratosphere.eu) * * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with * the License. You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on * an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the * specific language governing permissions and limitations under the License. **********************************************************************************************************************/ package eu.stratosphere.nephele.executiongraph; import java.util.Iterator; import java.util.concurrent.CopyOnWriteArrayList; import eu.stratosphere.nephele.execution.ExecutionState; import eu.stratosphere.nephele.instance.AllocatedResource; import eu.stratosphere.nephele.util.UnmodifiableIterator; /** * An execution pipeline is a scheduling abstraction which defines a set of {@link ExecutionVertex} objects which must * be deployed together. An {@link ExecutionVertex} always belongs to exactly one execution pipeline. * <p> * This class is thread-safe. * */ public final class ExecutionPipeline { /** * The set of vertices belonging to this execution pipeline. */ private final CopyOnWriteArrayList<ExecutionVertex> vertices = new CopyOnWriteArrayList<ExecutionVertex>(); /** * Adds the given {@link ExecutionVertex} to this pipeline. * * @param vertex * the vertex to be added to this pipeline */ void addToPipeline(final ExecutionVertex vertex) { if (!this.vertices.addIfAbsent(vertex)) { throw new IllegalStateException("Vertex " + vertex + " has already been added to pipeline " + this); } } /** * Removes the given {@link ExecutionVertex} from this pipeline. * * @param vertex * the vertex to be removed from this pipeline. */ void removeFromPipeline(final ExecutionVertex vertex) { if (!this.vertices.remove(vertex)) { throw new IllegalStateException("Vertex " + vertex + " was not part of the pipeline " + this); } } /** * Returns an {@link Iterator} to the vertices which are part of this pipeline. * * @return an iterator to the vertices of this pipeline */ public Iterator<ExecutionVertex> iterator() { return new UnmodifiableIterator<ExecutionVertex>(this.vertices.iterator()); } /** * Checks if the pipeline is currently finishing its execution, i.e. all vertices contained in the pipeline have * switched to the <code>FINISHING</code> or <code>FINISHED</code> state. * * @return <code>true</code> if the pipeline is currently finishing, <code>false</code> otherwise */ public boolean isFinishing() { final Iterator<ExecutionVertex> it = this.vertices.iterator(); while (it.hasNext()) { final ExecutionState state = it.next().getExecutionState(); if (state != ExecutionState.FINISHING && state != ExecutionState.FINISHED) { return false; } } return true; } /** * Sets the given allocated resource for all vertices included in this pipeline. * * @param resource * the allocated resource to set for all vertices included in this pipeline */ public void setAllocatedResource(final AllocatedResource resource) { final Iterator<ExecutionVertex> it = this.vertices.iterator(); while (it.hasNext()) { final ExecutionVertex vertex = it.next(); vertex.setAllocatedResource(resource); } } /** * Updates the execution state for all vertices included in this pipeline. * * @param executionState * the execution state to set for all vertices included in this pipeline */ public void updateExecutionState(final ExecutionState executionState) { final Iterator<ExecutionVertex> it = this.vertices.iterator(); while (it.hasNext()) { final ExecutionVertex vertex = it.next(); vertex.updateExecutionState(executionState); } } }