/** * This method is supposed to be called from {@link AttemptCallable#call()} * * @param ignored The ignored request; the actual request will be composed based on the result of * the {@code initialFuture}. * @param callContext call context */ @Override public ApiFuture<OperationSnapshot> futureCall(RequestT ignored, ApiCallContext callContext) { try { if (!initialFuture.isDone() || initialFuture.isCancelled()) { return initialFuture; } // Since initialFuture is done at this point, the following call should be non-blocking OperationSnapshot initialOperation = initialFuture.get(); if (initialOperation.isDone()) { return initialFuture; } return longRunningClient .getOperationCallable() .futureCall(initialOperation.getName(), callContext); } catch (ExecutionException e) { return ApiFutures.immediateFailedFuture(e.getCause()); } catch (InterruptedException e) { return ApiFutures.immediateFailedFuture(e); } } }
/** * This method is supposed to be called from {@link AttemptCallable#call()} * * @param ignored The ignored request; the actual request will be composed based on the result of * the {@code initialFuture}. * @param callContext call context */ @Override public ApiFuture<OperationSnapshot> futureCall(RequestT ignored, ApiCallContext callContext) { try { if (!initialFuture.isDone() || initialFuture.isCancelled()) { return initialFuture; } // Since initialFuture is done at this point, the following call should be non-blocking OperationSnapshot initialOperation = initialFuture.get(); if (initialOperation.isDone()) { return initialFuture; } return longRunningClient .getOperationCallable() .futureCall(initialOperation.getName(), callContext); } catch (ExecutionException e) { return ApiFutures.immediateFailedFuture(e.getCause()); } catch (InterruptedException e) { return ApiFutures.immediateFailedFuture(e); } } }
@Test public void translateException_cancelled() throws Exception { GrpcExceptionCallable<Integer, Integer> exceptionCallable = new GrpcExceptionCallable<>(inactiveCallable(), Collections.<StatusCode.Code>emptySet()); ApiFuture<Integer> result = exceptionCallable.futureCall(0); Truth.assertThat(result.isDone()).isFalse(); result.cancel(true); Truth.assertThat(result.isCancelled()).isTrue(); Truth.assertThat(result.isDone()).isTrue(); }
private void assertFutureSuccessMetaSuccess( String opName, OperationFuture<Color, Money> future, Color resp, Money meta) throws Exception { assertThat(future.getName()).isEqualTo(opName); assertThat(future.get(3, TimeUnit.SECONDS)).isEqualTo(resp); assertThat(future.isDone()).isTrue(); assertThat(future.isCancelled()).isFalse(); assertThat(future.get()).isEqualTo(resp); assertThat(future.peekMetadata().get()).isEqualTo(meta); assertThat(future.peekMetadata()).isSameAs(future.peekMetadata()); assertThat(future.peekMetadata().isDone()).isTrue(); assertThat(future.peekMetadata().isCancelled()).isFalse(); assertThat(future.getMetadata().get()).isEqualTo(meta); assertThat(future.getMetadata()).isSameAs(future.getMetadata()); assertThat(future.getMetadata().isDone()).isTrue(); assertThat(future.getMetadata().isCancelled()).isFalse(); }
private void assertFutureSuccessMetaSuccess( String opName, OperationFuture<Color, Currency> future, Color resp, Currency meta) throws InterruptedException, ExecutionException, TimeoutException { assertThat(future.getName()).isEqualTo(opName); Truth.assertThat(future.get(3, TimeUnit.SECONDS)).isEqualTo(resp); assertThat(future.isDone()).isTrue(); assertThat(future.isCancelled()).isFalse(); Truth.assertThat(future.get()).isEqualTo(resp); Truth.assertThat(future.peekMetadata().get()).isEqualTo(meta); assertThat(future.peekMetadata()).isSameAs(future.peekMetadata()); assertThat(future.peekMetadata().isDone()).isTrue(); assertThat(future.peekMetadata().isCancelled()).isFalse(); Truth.assertThat(future.getMetadata().get()).isEqualTo(meta); assertThat(future.getMetadata()).isSameAs(future.getMetadata()); assertThat(future.getMetadata().isDone()).isTrue(); assertThat(future.getMetadata().isCancelled()).isFalse(); }
assertThat(future.peekMetadata().isCancelled()).isFalse(); assertThat(future.getMetadata().isCancelled()).isFalse();
assertThat(cause.getStatusCode()).isEqualTo(statusCode); assertThat(future.peekMetadata().isDone()).isTrue(); assertThat(future.peekMetadata().isCancelled()).isFalse(); assertThat(cause.getStatusCode()).isEqualTo(statusCode); assertThat(future.getMetadata().isDone()).isTrue(); assertThat(future.getMetadata().isCancelled()).isFalse();
private void assertFutureFailMetaSuccess( OperationFuture<Color, Currency> future, Currency meta, FakeStatusCode statusCode, String errorMessage) throws TimeoutException, InterruptedException, ExecutionException { Exception exception = null; try { future.get(3, TimeUnit.SECONDS); } catch (ExecutionException e) { exception = e; } assertThat(exception).isNotNull(); assertExceptionMatchesCode(statusCode, exception.getCause()); ApiException cause = (ApiException) exception.getCause(); assertThat(cause.getStatusCode()).isEqualTo(statusCode); assertThat(cause.getMessage()).isEqualTo(errorMessage); assertThat(future.isDone()).isTrue(); assertThat(future.isCancelled()).isFalse(); Truth.assertThat(future.peekMetadata().get()).isEqualTo(meta); assertThat(future.peekMetadata()).isSameAs(future.peekMetadata()); assertThat(future.peekMetadata().isDone()).isTrue(); assertThat(future.peekMetadata().isCancelled()).isFalse(); Truth.assertThat(future.getMetadata().get()).isEqualTo(meta); assertThat(future.getMetadata()).isSameAs(future.getMetadata()); assertThat(future.getMetadata().isDone()).isTrue(); assertThat(future.getMetadata().isCancelled()).isFalse(); }
private void assertFutureCancelMetaCancel(OperationFuture<Color, Currency> future) throws InterruptedException, ExecutionException, TimeoutException { Exception exception = null; try { future.get(3, TimeUnit.SECONDS); } catch (CancellationException e) { exception = e; } assertThat(exception).isNotNull(); assertThat(future.isDone()).isTrue(); assertThat(future.isCancelled()).isTrue(); try { future.peekMetadata().get(); } catch (CancellationException e) { exception = e; } assertThat(future.peekMetadata()).isSameAs(future.peekMetadata()); assertThat(exception).isNotNull(); assertThat(future.peekMetadata().isDone()).isTrue(); assertThat(future.peekMetadata().isCancelled()).isTrue(); try { future.getMetadata().get(); } catch (CancellationException e) { exception = e; } assertThat(future.getMetadata()).isSameAs(future.getMetadata()); assertThat(exception).isNotNull(); assertThat(future.getMetadata().isDone()).isTrue(); assertThat(future.getMetadata().isCancelled()).isTrue(); }
@Test public void cancellationDuringRetryDelay() throws Exception { Throwable throwable = new UnavailableException(null, FakeStatusCode.of(StatusCode.Code.UNAVAILABLE), true); CancellationTrackingFuture<Integer> innerFuture = CancellationTrackingFuture.create(); Mockito.when(callInt.futureCall((Integer) Mockito.any(), (ApiCallContext) Mockito.any())) .thenReturn(RetryingTest.<Integer>immediateFailedFuture(throwable)) .thenReturn(innerFuture); CountDownLatch retryScheduledLatch = new CountDownLatch(1); LatchCountDownScheduler scheduler = LatchCountDownScheduler.get(retryScheduledLatch, 0L, 0L); UnaryCallSettings<Integer, Integer> callSettings = RetryingTest.createSettings(SLOW_RETRY_SETTINGS); UnaryCallable<Integer, Integer> callable = FakeCallableFactory.createUnaryCallable( callInt, callSettings, clientContext.toBuilder().setExecutor(scheduler).build()); ApiFuture<Integer> resultFuture = callable.futureCall(0); CancellationHelpers.cancelInThreadAfterLatchCountDown(resultFuture, retryScheduledLatch); CancellationException gotException = null; try { resultFuture.get(); } catch (CancellationException e) { gotException = e; } Truth.assertThat(gotException).isNotNull(); Truth.assertThat(resultFuture.isDone()).isTrue(); Truth.assertThat(resultFuture.isCancelled()).isTrue(); Truth.assertThat(innerFuture.isCancelled()).isFalse(); scheduler.shutdownNow(); }
Truth.assertThat(resultFuture.isCancelled()).isTrue(); Truth.assertThat(innerFuture.isDone()).isTrue();
@Test public void testFutureCallInitialCancel() throws Exception { String opName = "testFutureCallInitialCancel"; OperationSnapshot initialOperation = getOperation(opName, null, null, null, false); OperationSnapshot resultOperation = getOperation(opName, null, null, null, false); UnaryCallable<Integer, OperationSnapshot> initialCallable = mockGetOpSnapshotCallable(StatusCode.Code.OK, initialOperation); LongRunningClient longRunningClient = mockGetOperation(StatusCode.Code.OK, resultOperation); OperationCallableImpl<Integer, Color, Currency> callableImpl = Callables.longRunningOperationImpl( initialCallable, callSettings, initialContext, longRunningClient); OperationFutureImpl<Color, Currency> future = callableImpl.futureCall( new ListenableFutureToApiFuture<>( Futures.<OperationSnapshot>immediateCancelledFuture()), FakeCallContext.createDefault()); Exception exception = null; try { future.get(3, TimeUnit.SECONDS); } catch (CancellationException e) { exception = e; } assertThat(exception).isNotNull(); assertThat(future.isDone()).isTrue(); assertThat(future.isCancelled()).isTrue(); assertThat(future.getInitialFuture().isDone()).isTrue(); assertThat(future.getInitialFuture().isCancelled()).isTrue(); assertFutureCancelMetaCancel(future); assertThat(executor.getIterationsCount()).isEqualTo(0); }
assertSame(future.getAttemptResult(), future.getAttemptResult()); assertFalse(future.getAttemptResult().isDone()); assertFalse(future.getAttemptResult().isCancelled());
assertSame(future.peekAttemptResult(), future.peekAttemptResult()); assertFalse(future.getAttemptResult().isDone()); assertFalse(future.getAttemptResult().isCancelled()); if (attemptResult != null) { assertTrue(attemptResult.isDone()); assertFalse(attemptResult.isCancelled()); try { attemptResult.get();
assertSame(future.peekAttemptResult(), future.peekAttemptResult()); assertTrue(future.peekAttemptResult().isDone()); assertFalse(future.peekAttemptResult().isCancelled()); assertSame(future.getAttemptResult(), future.getAttemptResult()); assertTrue(future.getAttemptResult().isDone()); assertFalse(future.getAttemptResult().isCancelled());
assertSame(future.getAttemptResult(), future.getAttemptResult()); assertFalse(future.getAttemptResult().isDone()); assertFalse(future.getAttemptResult().isCancelled());
@Test public void testSuccessWithFailuresPeekGetAttempt() throws Exception { FailingCallable callable = new FailingCallable(5, "SUCCESS", tracer); RetryingExecutorWithContext<String> executor = getExecutor(getAlgorithm(FAST_RETRY_SETTINGS, 0, null)); RetryingFuture<String> future = executor.createFuture(callable, retryingContext); assertNull(future.peekAttemptResult()); assertSame(future.peekAttemptResult(), future.peekAttemptResult()); assertFalse(future.getAttemptResult().isDone()); assertFalse(future.getAttemptResult().isCancelled()); Exception exception = null; try { future.get(1L, TimeUnit.MILLISECONDS); } catch (TimeoutException e) { exception = e; } assertNotNull(exception); future.setAttemptFuture(executor.submit(future)); assertFutureSuccess(future); assertEquals(5, future.getAttemptSettings().getAttemptCount()); }
void assertFutureSuccess(RetryingFuture<String> future) throws ExecutionException, InterruptedException, TimeoutException { assertEquals("SUCCESS", future.get(3, TimeUnit.SECONDS)); assertTrue(future.isDone()); assertFalse(future.isCancelled()); assertEquals("SUCCESS", future.peekAttemptResult().get(3, TimeUnit.SECONDS)); assertSame(future.peekAttemptResult(), future.peekAttemptResult()); assertTrue(future.peekAttemptResult().isDone()); assertFalse(future.peekAttemptResult().isCancelled()); assertEquals("SUCCESS", future.getAttemptResult().get(3, TimeUnit.SECONDS)); assertSame(future.getAttemptResult(), future.getAttemptResult()); assertTrue(future.getAttemptResult().isDone()); assertFalse(future.getAttemptResult().isCancelled()); String res = future.get(); ApiFuture<?> gottentAttempt = future.getAttemptResult(); ApiFuture<?> peekedAttempt = future.peekAttemptResult(); // testing completed immutability assertFalse(future.cancel(true)); assertFalse(future.cancel(false)); assertSame(gottentAttempt, future.getAttemptResult()); assertSame(peekedAttempt, future.peekAttemptResult()); assertSame(res, future.get()); assertTrue(future.isDone()); assertFalse(future.isCancelled()); }
assertSame(future.getAttemptResult(), future.getAttemptResult()); assertTrue(future.getAttemptResult().isDone()); assertTrue(future.getAttemptResult().isCancelled()); try { future.peekAttemptResult().get(3, TimeUnit.SECONDS); assertSame(future.peekAttemptResult(), future.peekAttemptResult()); assertTrue(future.peekAttemptResult().isDone()); assertTrue(future.peekAttemptResult().isCancelled());