@Test public void resilientUnderMultipleThreads() throws InterruptedException { BlockingTimestamp blockingTimestampReturning1 = new BlockingTimestamp(1); when(rawTimelockService.getFreshTimestamp()) .thenAnswer(blockingTimestampReturning1) .thenReturn(2L); Future<Void> blockingGetFreshTimestampCall = CompletableFuture.runAsync(timelockService::getFreshTimestamp); blockingTimestampReturning1.waitForFirstCallToBlock(); assertThat(timelockService.getFreshTimestamp()) .as("This should have updated the lower bound to 2") .isEqualTo(2L); blockingTimestampReturning1.countdown(); assertThatCode(blockingGetFreshTimestampCall::get) .doesNotThrowAnyException(); }
@Override public long getFreshTimestamp() { return checkAndUpdateLowerBound(delegate::getFreshTimestamp, x -> x, x -> x, OperationType.TIMESTAMP); }
TimestampCorroboratingTimelockService implements AutoDelegate_TimelockService { @Override public long getFreshTimestamp() { return checkAndUpdateLowerBound(delegate::getFreshTimestamp, x -> x, x -> x, OperationType.TIMESTAMP); } }
TimestampCorroboratingTimelockService implements AutoDelegate_TimelockService { @Override public long getFreshTimestamp() { return checkAndUpdateLowerBound(delegate::getFreshTimestamp, x -> x, x -> x, OperationType.TIMESTAMP); } private  TimestampCorroboratingTimelockService(TimelockService delegate); }
TimestampCorroboratingTimelockService implements AutoDelegate_TimelockService { @Override public long getFreshTimestamp() { return checkAndUpdateLowerBound(delegate::getFreshTimestamp, x -> x, x -> x, OperationType.TIMESTAMP); } private  TimestampCorroboratingTimelockService(TimelockService delegate); static TimelockService create(TimelockService delegate); @Override TimelockService delegate(); @Override long getFreshTimestamp(); @Override TimestampRange getFreshTimestamps(int numTimestampsRequested); @Override List<StartIdentifiedAtlasDbTransactionResponse> startIdentifiedAtlasDbTransactionBatch(int count); }
TimestampCorroboratingTimelockService implements AutoDelegate_TimelockService { @Override public long getFreshTimestamp() { return checkAndUpdateLowerBound(delegate::getFreshTimestamp, x -> x, x -> x, OperationType.TIMESTAMP); } private  TimestampCorroboratingTimelockService(TimelockService delegate); static TimelockService create(TimelockService delegate); @Override TimelockService delegate(); @Override long getFreshTimestamp(); @Override TimestampRange getFreshTimestamps(int numTimestampsRequested); @Override List<StartIdentifiedAtlasDbTransactionResponse> startIdentifiedAtlasDbTransactionBatch(int count);  }