Java Code Examples for org.apache.flink.runtime.concurrent.FutureUtils#waitForAll()

The following examples show how to use org.apache.flink.runtime.concurrent.FutureUtils#waitForAll() . You can vote up the ones you like or vote down the ones you don't like, and go to the original project or source file by following the links above each example. You may check out the related API usage on the sidebar.
Example 1
Source File: FailoverRegion.java    From Flink-CEPplus with Apache License 2.0 5 votes vote down vote up
@VisibleForTesting
protected CompletableFuture<Void> createTerminationFutureOverAllConnectedVertexes() {
	// we build a future that is complete once all vertices have reached a terminal state
	final ArrayList<CompletableFuture<?>> futures = new ArrayList<>(connectedExecutionVertexes.size());

	// cancel all tasks (that still need cancelling)
	for (ExecutionVertex vertex : connectedExecutionVertexes) {
		futures.add(vertex.cancel());
	}

	return FutureUtils.waitForAll(futures);
}
 
Example 2
Source File: ExecutionGraph.java    From flink with Apache License 2.0 5 votes vote down vote up
private ConjunctFuture<Void> cancelVerticesAsync() {
	final ArrayList<CompletableFuture<?>> futures = new ArrayList<>(verticesInCreationOrder.size());

	// cancel all tasks (that still need cancelling)
	for (ExecutionJobVertex ejv : verticesInCreationOrder) {
		futures.add(ejv.cancelWithFuture());
	}

	// we build a future that is complete once all vertices have reached a terminal state
	return FutureUtils.waitForAll(futures);
}
 
Example 3
Source File: SchedulingUtils.java    From flink with Apache License 2.0 5 votes vote down vote up
/**
 * Schedule vertices lazy. That means only vertices satisfying its input constraint will be scheduled.
 *
 * @param vertices Topologically sorted vertices to schedule.
 * @param executionGraph The graph the given vertices belong to.
 */
public static CompletableFuture<Void> scheduleLazy(
		final Iterable<ExecutionVertex> vertices,
		final ExecutionGraph executionGraph) {

	executionGraph.assertRunningInJobMasterMainThread();

	final SlotProviderStrategy slotProviderStrategy = executionGraph.getSlotProviderStrategy();
	final Set<AllocationID> previousAllocations = computePriorAllocationIdsIfRequiredByScheduling(
		vertices, slotProviderStrategy.asSlotProvider());

	final ArrayList<CompletableFuture<Void>> schedulingFutures = new ArrayList<>();
	for (ExecutionVertex executionVertex : vertices) {
		// only schedule vertex when its input constraint is satisfied
		if (executionVertex.getJobVertex().getJobVertex().isInputVertex() ||
			executionVertex.checkInputDependencyConstraints()) {

			final CompletableFuture<Void> schedulingVertexFuture = executionVertex.scheduleForExecution(
				slotProviderStrategy,
				LocationPreferenceConstraint.ANY,
				previousAllocations);

			schedulingFutures.add(schedulingVertexFuture);
		}
	}

	return FutureUtils.waitForAll(schedulingFutures);
}
 
Example 4
Source File: AkkaRpcService.java    From flink with Apache License 2.0 5 votes vote down vote up
@GuardedBy("lock")
@Nonnull
private CompletableFuture<Void> terminateAkkaRpcActors() {
	final Collection<CompletableFuture<Void>> akkaRpcActorTerminationFutures = new ArrayList<>(actors.size());

	for (Map.Entry<ActorRef, RpcEndpoint> actorRefRpcEndpointEntry : actors.entrySet()) {
		akkaRpcActorTerminationFutures.add(terminateAkkaRpcActor(actorRefRpcEndpointEntry.getKey(), actorRefRpcEndpointEntry.getValue()));
	}
	actors.clear();

	return FutureUtils.waitForAll(akkaRpcActorTerminationFutures);
}
 
Example 5
Source File: ConcurrentFailoverStrategyExecutionGraphTest.java    From Flink-CEPplus with Apache License 2.0 5 votes vote down vote up
@Override
protected FailoverRegion createFailoverRegion(ExecutionGraph eg, List<ExecutionVertex> connectedExecutions) {
	return new FailoverRegion(eg, connectedExecutions) {
		@Override
		protected CompletableFuture<Void> createTerminationFutureOverAllConnectedVertexes() {
			ArrayList<CompletableFuture<?>> terminationAndBlocker = new ArrayList<>(2);
			terminationAndBlocker.add(super.createTerminationFutureOverAllConnectedVertexes());
			terminationAndBlocker.add(blockerFuture);
			return FutureUtils.waitForAll(terminationAndBlocker);
		}
	};
}
 
Example 6
Source File: EmbeddedLeaderService.java    From Flink-CEPplus with Apache License 2.0 5 votes vote down vote up
private CompletableFuture<Void> notifyAllListeners(String address, UUID leaderSessionId) {
	final List<CompletableFuture<Void>> notifyListenerFutures = new ArrayList<>(listeners.size());

	for (EmbeddedLeaderRetrievalService listener : listeners) {
		notifyListenerFutures.add(notifyListener(address, leaderSessionId, listener.listener));
	}

	return FutureUtils.waitForAll(notifyListenerFutures);
}
 
Example 7
Source File: AkkaRpcService.java    From Flink-CEPplus with Apache License 2.0 5 votes vote down vote up
@GuardedBy("lock")
@Nonnull
private CompletableFuture<Void> terminateAkkaRpcActors() {
	final Collection<CompletableFuture<Void>> akkaRpcActorTerminationFutures = new ArrayList<>(actors.size());

	for (Map.Entry<ActorRef, RpcEndpoint> actorRefRpcEndpointEntry : actors.entrySet()) {
		akkaRpcActorTerminationFutures.add(terminateAkkaRpcActor(actorRefRpcEndpointEntry.getKey(), actorRefRpcEndpointEntry.getValue()));
	}
	actors.clear();

	return FutureUtils.waitForAll(akkaRpcActorTerminationFutures);
}
 
Example 8
Source File: AkkaRpcService.java    From flink with Apache License 2.0 5 votes vote down vote up
@GuardedBy("lock")
@Nonnull
private CompletableFuture<Void> terminateAkkaRpcActors() {
	final Collection<CompletableFuture<Void>> akkaRpcActorTerminationFutures = new ArrayList<>(actors.size());

	for (Map.Entry<ActorRef, RpcEndpoint> actorRefRpcEndpointEntry : actors.entrySet()) {
		akkaRpcActorTerminationFutures.add(terminateAkkaRpcActor(actorRefRpcEndpointEntry.getKey(), actorRefRpcEndpointEntry.getValue()));
	}
	actors.clear();

	return FutureUtils.waitForAll(akkaRpcActorTerminationFutures);
}
 
Example 9
Source File: SingleLogicalSlotTest.java    From flink with Apache License 2.0 5 votes vote down vote up
/**
 * Tests that concurrent release operations only trigger the failing of the payload and
 * the return of the slot once.
 */
@Test
public void testConcurrentReleaseOperations() throws Exception {
	final CountingSlotOwner countingSlotOwner = new CountingSlotOwner();
	final CountingFailPayload countingFailPayload = new CountingFailPayload();
	final SingleLogicalSlot singleLogicalSlot = createSingleLogicalSlot(countingSlotOwner);

	singleLogicalSlot.tryAssignPayload(countingFailPayload);

	final ExecutorService executorService = Executors.newFixedThreadPool(4);

	try {
		final int numberConcurrentOperations = 10;
		final Collection<CompletableFuture<?>> releaseOperationFutures = new ArrayList<>(numberConcurrentOperations);

		for (int i = 0; i < numberConcurrentOperations; i++) {
			final CompletableFuture<Void> releaseOperationFuture = CompletableFuture.runAsync(
				() -> {
					try {
						singleLogicalSlot.releaseSlot(new FlinkException("Test exception")).get();
					} catch (InterruptedException | ExecutionException e) {
						ExceptionUtils.checkInterrupted(e);
						throw new CompletionException(e);
					}
				});

			releaseOperationFutures.add(releaseOperationFuture);
		}

		final FutureUtils.ConjunctFuture<Void> releaseOperationsFuture = FutureUtils.waitForAll(releaseOperationFutures);

		releaseOperationsFuture.get();

		assertThat(countingSlotOwner.getReleaseCount(), is(1));
		assertThat(countingFailPayload.getFailCount(), is(1));
	} finally {
		executorService.shutdownNow();
	}
}
 
Example 10
Source File: FailoverRegion.java    From flink with Apache License 2.0 5 votes vote down vote up
@VisibleForTesting
protected CompletableFuture<Void> createTerminationFutureOverAllConnectedVertexes() {
	// we build a future that is complete once all vertices have reached a terminal state
	final ArrayList<CompletableFuture<?>> futures = new ArrayList<>(connectedExecutionVertexes.size());

	// cancel all tasks (that still need cancelling)
	for (ExecutionVertex vertex : connectedExecutionVertexes) {
		futures.add(vertex.cancel());
	}

	return FutureUtils.waitForAll(futures);
}
 
Example 11
Source File: EmbeddedLeaderService.java    From flink with Apache License 2.0 5 votes vote down vote up
private CompletableFuture<Void> notifyAllListeners(String address, UUID leaderSessionId) {
	final List<CompletableFuture<Void>> notifyListenerFutures = new ArrayList<>(listeners.size());

	for (EmbeddedLeaderRetrievalService listener : listeners) {
		notifyListenerFutures.add(notifyListener(address, leaderSessionId, listener.listener));
	}

	return FutureUtils.waitForAll(notifyListenerFutures);
}
 
Example 12
Source File: ConcurrentFailoverStrategyExecutionGraphTest.java    From flink with Apache License 2.0 5 votes vote down vote up
@Override
protected FailoverRegion createFailoverRegion(ExecutionGraph eg, List<ExecutionVertex> connectedExecutions) {
	Map<JobVertexID, ExecutionJobVertex> tasks = initTasks(connectedExecutions);
	return new FailoverRegion(eg, connectedExecutions, tasks) {
		@Override
		protected CompletableFuture<Void> createTerminationFutureOverAllConnectedVertexes() {
			ArrayList<CompletableFuture<?>> terminationAndBlocker = new ArrayList<>(2);
			terminationAndBlocker.add(super.createTerminationFutureOverAllConnectedVertexes());
			terminationAndBlocker.add(blockerFuture);
			return FutureUtils.waitForAll(terminationAndBlocker);
		}
	};
}
 
Example 13
Source File: ExecutionGraph.java    From flink with Apache License 2.0 4 votes vote down vote up
/**
 * Suspends the current ExecutionGraph.
 *
 * <p>The JobStatus will be directly set to {@link JobStatus#SUSPENDED} iff the current state is not a terminal
 * state. All ExecutionJobVertices will be canceled and the onTerminalState() is executed.
 *
 * <p>The {@link JobStatus#SUSPENDED} state is a local terminal state which stops the execution of the job but does
 * not remove the job from the HA job store so that it can be recovered by another JobManager.
 *
 * @param suspensionCause Cause of the suspension
 */
public void suspend(Throwable suspensionCause) {

	assertRunningInJobMasterMainThread();

	if (state.isTerminalState()) {
		// stay in a terminal state
		return;
	} else if (transitionState(state, JobStatus.SUSPENDED, suspensionCause)) {
		initFailureCause(suspensionCause);

		// make sure no concurrent local actions interfere with the cancellation
		incrementGlobalModVersion();

		// cancel ongoing scheduling action
		if (schedulingFuture != null) {
			schedulingFuture.cancel(false);
		}
		final ArrayList<CompletableFuture<Void>> executionJobVertexTerminationFutures = new ArrayList<>(verticesInCreationOrder.size());

		for (ExecutionJobVertex ejv: verticesInCreationOrder) {
			executionJobVertexTerminationFutures.add(ejv.suspend());
		}

		final ConjunctFuture<Void> jobVerticesTerminationFuture = FutureUtils.waitForAll(executionJobVertexTerminationFutures);

		checkState(jobVerticesTerminationFuture.isDone(), "Suspend needs to happen atomically");

		jobVerticesTerminationFuture.whenComplete(
			(Void ignored, Throwable throwable) -> {
				if (throwable != null) {
					LOG.debug("Could not properly suspend the execution graph.", throwable);
				}

				onTerminalState(state);
				LOG.info("Job {} has been suspended.", getJobID());
			});
	} else {
		throw new IllegalStateException(String.format("Could not suspend because transition from %s to %s failed.", state, JobStatus.SUSPENDED));
	}
}
 
Example 14
Source File: ExecutionGraph.java    From Flink-CEPplus with Apache License 2.0 4 votes vote down vote up
/**
 * Fails the execution graph globally. This failure will not be recovered by a specific
 * failover strategy, but results in a full restart of all tasks.
 *
 * <p>This global failure is meant to be triggered in cases where the consistency of the
 * execution graph' state cannot be guaranteed any more (for example when catching unexpected
 * exceptions that indicate a bug or an unexpected call race), and where a full restart is the
 * safe way to get consistency back.
 *
 * @param t The exception that caused the failure.
 */
public void failGlobal(Throwable t) {

	assertRunningInJobMasterMainThread();

	while (true) {
		JobStatus current = state;
		// stay in these states
		if (current == JobStatus.FAILING ||
			current == JobStatus.SUSPENDED ||
			current.isGloballyTerminalState()) {
			return;
		} else if (transitionState(current, JobStatus.FAILING, t)) {
			initFailureCause(t);

			// make sure no concurrent local or global actions interfere with the failover
			final long globalVersionForRestart = incrementGlobalModVersion();

			final CompletableFuture<Void> ongoingSchedulingFuture = schedulingFuture;

			// cancel ongoing scheduling action
			if (ongoingSchedulingFuture != null) {
				ongoingSchedulingFuture.cancel(false);
			}

			// we build a future that is complete once all vertices have reached a terminal state
			final ArrayList<CompletableFuture<?>> futures = new ArrayList<>(verticesInCreationOrder.size());

			// cancel all tasks (that still need cancelling)
			for (ExecutionJobVertex ejv : verticesInCreationOrder) {
				futures.add(ejv.cancelWithFuture());
			}

			final ConjunctFuture<Void> allTerminal = FutureUtils.waitForAll(futures);
			allTerminal.whenComplete(
				(Void ignored, Throwable throwable) -> {
					if (throwable != null) {
						transitionState(
							JobStatus.FAILING,
							JobStatus.FAILED,
							new FlinkException("Could not cancel all execution job vertices properly.", throwable));
					} else {
						allVerticesInTerminalState(globalVersionForRestart);
					}
				});

			return;
		}

		// else: concurrent change to execution state, retry
	}
}
 
Example 15
Source File: BlobServerDeleteTest.java    From flink with Apache License 2.0 4 votes vote down vote up
/**
 * [FLINK-6020] Tests that concurrent delete operations don't interfere with each other.
 *
 * <p>Note: This test checks that there cannot be two threads which have checked whether a given
 * blob file exist and then one of them fails deleting it. Without the introduced lock, this
 * situation should rarely happen and make this test fail. Thus, if this test should become
 * "unstable", then the delete atomicity is most likely broken.
 *
 * @param jobId
 * 		job ID to use (or <tt>null</tt> if job-unrelated)
 */
private void testConcurrentDeleteOperations(@Nullable final JobID jobId)
		throws IOException, InterruptedException, ExecutionException {

	final Configuration config = new Configuration();
	config.setString(BlobServerOptions.STORAGE_DIRECTORY, temporaryFolder.newFolder().getAbsolutePath());

	final int concurrentDeleteOperations = 3;
	final ExecutorService executor = Executors.newFixedThreadPool(concurrentDeleteOperations);

	final List<CompletableFuture<Void>> deleteFutures = new ArrayList<>(concurrentDeleteOperations);

	final byte[] data = {1, 2, 3};

	try (final BlobServer server = new BlobServer(config, new VoidBlobStore())) {

		server.start();

		final TransientBlobKey blobKey =
			(TransientBlobKey) put(server, jobId, data, TRANSIENT_BLOB);

		assertTrue(server.getStorageLocation(jobId, blobKey).exists());

		for (int i = 0; i < concurrentDeleteOperations; i++) {
			CompletableFuture<Void> deleteFuture = CompletableFuture.supplyAsync(
				() -> {
					try {
						assertTrue(delete(server, jobId, blobKey));
						assertFalse(server.getStorageLocation(jobId, blobKey).exists());
						return null;
					} catch (IOException e) {
						throw new CompletionException(new FlinkException(
							"Could not delete the given blob key " + blobKey + '.'));
					}
				},
			executor);

			deleteFutures.add(deleteFuture);
		}

		CompletableFuture<Void> waitFuture = FutureUtils.waitForAll(deleteFutures);

		// make sure all delete operation have completed successfully
		// in case of no lock, one of the delete operations should eventually fail
		waitFuture.get();

		assertFalse(server.getStorageLocation(jobId, blobKey).exists());

	} finally {
		executor.shutdownNow();
	}
}
 
Example 16
Source File: CompletedOperationCache.java    From flink with Apache License 2.0 4 votes vote down vote up
private CompletableFuture<Void> asyncWaitForResultsToBeAccessed() {
	return FutureUtils.waitForAll(
		Stream.concat(registeredOperationTriggers.values().stream(), completedOperations.asMap().values().stream())
			.map(ResultAccessTracker::getAccessedFuture)
			.collect(Collectors.toList()));
}
 
Example 17
Source File: BlobCacheDeleteTest.java    From flink with Apache License 2.0 4 votes vote down vote up
/**
 * [FLINK-6020] Tests that concurrent delete operations don't interfere with each other.
 *
 * <p>Note: This test checks that there cannot be two threads which have checked whether a given
 * blob file exist and then one of them fails deleting it. Without the introduced lock, this
 * situation should rarely happen and make this test fail. Thus, if this test should become
 * "unstable", then the delete atomicity is most likely broken.
 *  @param jobId
 * 		job ID to use (or <tt>null</tt> if job-unrelated)
 *
 */
private void testConcurrentDeleteOperations(@Nullable final JobID jobId)
		throws IOException, InterruptedException, ExecutionException {

	final Configuration config = new Configuration();
	config.setString(BlobServerOptions.STORAGE_DIRECTORY, temporaryFolder.newFolder().getAbsolutePath());

	final int concurrentDeleteOperations = 3;
	final ExecutorService executor = Executors.newFixedThreadPool(concurrentDeleteOperations);

	final List<CompletableFuture<Void>> deleteFutures = new ArrayList<>(concurrentDeleteOperations);

	final byte[] data = {1, 2, 3};

	try (
		BlobServer server = new BlobServer(config, new VoidBlobStore());
		BlobCacheService cache = new BlobCacheService(config, new VoidBlobStore(), new InetSocketAddress("localhost", server.getPort())
		)) {

		server.start();

		final TransientBlobKey blobKey =
			(TransientBlobKey) put(server, jobId, data, TRANSIENT_BLOB);

		assertTrue(server.getStorageLocation(jobId, blobKey).exists());

		for (int i = 0; i < concurrentDeleteOperations; i++) {
			CompletableFuture<Void> deleteFuture = CompletableFuture
				.supplyAsync(
					() -> {
						try {
							assertTrue(delete(cache, jobId, blobKey));
							assertFalse(cache.getTransientBlobService().getStorageLocation(jobId, blobKey).exists());
							// delete only works on local cache!
							assertTrue(server.getStorageLocation(jobId, blobKey).exists());
							return null;
						} catch (IOException e) {
							throw new CompletionException(new FlinkException(
								"Could not upload blob.", e));
						}
					}, executor);

			deleteFutures.add(deleteFuture);
		}

		CompletableFuture<Void> waitFuture = FutureUtils.waitForAll(deleteFutures);

		// make sure all delete operation have completed successfully
		// in case of no lock, one of the delete operations should eventually fail
		waitFuture.get();

		// delete only works on local cache!
		assertTrue(server.getStorageLocation(jobId, blobKey).exists());

	} finally {
		executor.shutdownNow();
	}
}
 
Example 18
Source File: CompletedOperationCache.java    From Flink-CEPplus with Apache License 2.0 4 votes vote down vote up
private CompletableFuture<Void> asyncWaitForResultsToBeAccessed() {
	return FutureUtils.waitForAll(
		Stream.concat(registeredOperationTriggers.values().stream(), completedOperations.asMap().values().stream())
			.map(ResultAccessTracker::getAccessedFuture)
			.collect(Collectors.toList()));
}
 
Example 19
Source File: CompletedOperationCache.java    From flink with Apache License 2.0 4 votes vote down vote up
private CompletableFuture<Void> asyncWaitForResultsToBeAccessed() {
	return FutureUtils.waitForAll(
		Stream.concat(registeredOperationTriggers.values().stream(), completedOperations.asMap().values().stream())
			.map(ResultAccessTracker::getAccessedFuture)
			.collect(Collectors.toList()));
}
 
Example 20
Source File: ExecutionJobVertex.java    From flink with Apache License 2.0 2 votes vote down vote up
/**
 * Cancels all currently running vertex executions.
 *
 * @return A future that is complete once all tasks have canceled.
 */
public CompletableFuture<Void> cancelWithFuture() {
	return FutureUtils.waitForAll(mapExecutionVertices(ExecutionVertex::cancel));
}