@Test
  public void concurrentUndeleteTestOnSameBlob() throws Exception {
    final MockId idToUndelete = put(1, PUT_RECORD_SIZE, Utils.Infinite_Time).get(0);
    delete(idToUndelete);
    int count = 2;
    long logEndOffsetBeforeUndelete = store.getLogEndOffsetInBytes();
    long indexEndOffsetBeforeUndelete = store.getSizeInBytes();
    ExecutorService executorService = Executors.newFixedThreadPool(count);
    try {
      List<Future<Void>> futures = new ArrayList<>();
      for (int i = 0; i < count; i++) {
        futures.add(executorService.submit(() -> {
          undelete(idToUndelete);
          return null;
        }));
      }
      int failedCount = 0;
      int succeededCount = 0;
      for (Future<Void> future : futures) {
        try {
          future.get();
          succeededCount++;
        } catch (ExecutionException e) {
          failedCount++;
          assertTrue(e.getCause() instanceof StoreException);
          assertEquals(StoreErrorCodes.IDUndeleted, ((StoreException) e.getCause()).getErrorCode());
        }
      }

      assertEquals(1, succeededCount);
      assertEquals(count - 1, failedCount);
      long logEndOffsetAfterUndelete = store.getLogEndOffsetInBytes();
      long indexEndOffsetAfterUndelete = store.getSizeInBytes();
      assertEquals((long) UNDELETE_RECORD_SIZE, logEndOffsetAfterUndelete - logEndOffsetBeforeUndelete);
      assertEquals((long) UNDELETE_RECORD_SIZE, indexEndOffsetAfterUndelete - indexEndOffsetBeforeUndelete);
    } finally {
      executorService.shutdownNow();
    }
  }
Test when undeleting the same blob at the same time. Only one undelete can go through and only one log and index
record should be persisted.
@throws Exception
ambry-store/src/test/java/com/github/ambry/store/BlobStoreTest.java