class GcsUtil {

  @VisibleForTesting
  @Nullable
  Bucket getBucket(GcsPath path, BackOff backoff, Sleeper sleeper) throws IOException {
    Storage.Buckets.Get getBucket =
        storageClient.buckets().get(path.getBucket());

      try {
        Bucket bucket = ResilientOperation.retry(
            ResilientOperation.getGoogleRequestCallable(getBucket),
            backoff,
            new RetryDeterminer<IOException>() {
              @Override
              public boolean shouldRetry(IOException e) {
                if (errorExtractor.itemNotFound(e) || errorExtractor.accessDenied(e)) {
                  return false;
                }
                return RetryDeterminer.SOCKET_ERRORS.shouldRetry(e);
              }
            },
            IOException.class,
            sleeper);

        return bucket;
      } catch (GoogleJsonResponseException e) {
        if (errorExtractor.accessDenied(e)) {
          throw new AccessDeniedException(path.toString(), null, e.getMessage());
        }
        if (errorExtractor.itemNotFound(e)) {
          throw new FileNotFoundException(e.getMessage());
        }
        throw e;
      } catch (InterruptedException e) {
        Thread.currentThread().interrupt();
        throw new IOException(
            String.format("Error while attempting to verify existence of bucket gs://%s",
                path.getBucket()), e);
     }
  }

  private  GcsUtil(
      Storage storageClient,
      HttpRequestInitializer httpRequestInitializer,
      ExecutorService executorService,
      @Nullable Integer uploadBufferSizeBytes);

}