All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.google.cloud.hadoop.util.CredentialFromAccessTokenProviderClassFactory Maven / Gradle / Ivy

/*
 * Copyright 2018 Google Inc. All Rights Reserved.
 *
 *  Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except
 * in compliance with the License. You may obtain a copy of the License at
 *
 *  http://www.apache.org/licenses/LICENSE-2.0
 *
 *  Unless required by applicable law or agreed to in writing, software distributed under the
 * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either
 * express or implied. See the License for the specific language governing permissions and
 * limitations under the License.
 */

package com.google.cloud.hadoop.util;

import com.google.api.client.auth.oauth2.Credential;
import com.google.api.client.auth.oauth2.TokenResponse;
import com.google.api.client.googleapis.auth.oauth2.GoogleCredential;
import com.google.api.client.util.Clock;
import com.google.cloud.hadoop.util.AccessTokenProvider.AccessToken;
import com.google.common.base.Preconditions;
import com.google.common.flogger.GoogleLogger;
import java.io.IOException;
import java.security.GeneralSecurityException;
import java.util.Collection;
import org.apache.hadoop.conf.Configuration;

/**
 * Given an {@link AccessTokenProviderClassFromConfigFactory} and a Hadoop {@link Configuration},
 * generate a {@link Credential}.
 */
public final class CredentialFromAccessTokenProviderClassFactory {

  /**
   * A wrapper class that exposes a {@link GoogleCredential} interface using an {@link
   * AccessTokenProvider}.
   */
  static final class GoogleCredentialWithAccessTokenProvider extends GoogleCredential {
    private final Clock clock;
    private final AccessTokenProvider accessTokenProvider;

    private GoogleCredentialWithAccessTokenProvider(
        Clock clock, AccessTokenProvider accessTokenProvider) {
      this.clock = clock;
      this.accessTokenProvider = accessTokenProvider;
    }

    static GoogleCredential fromAccessTokenProvider(
        Clock clock, AccessTokenProvider accessTokenProvider) {
      GoogleCredentialWithAccessTokenProvider withProvider =
          new GoogleCredentialWithAccessTokenProvider(clock, accessTokenProvider);
      AccessToken accessToken =
          Preconditions.checkNotNull(
              accessTokenProvider.getAccessToken(), "Access Token cannot be null!");

      withProvider
          .setAccessToken(accessToken.getToken())
          .setExpirationTimeMilliseconds(accessToken.getExpirationTimeMilliSeconds());
      // TODO: This should be setting the refresh token as well.
      return withProvider;
    }

    @Override
    protected TokenResponse executeRefreshToken() throws IOException {
      accessTokenProvider.refresh();
      AccessToken accessToken =
          Preconditions.checkNotNull(
              accessTokenProvider.getAccessToken(), "Access Token cannot be null!");

      String token =
          Preconditions.checkNotNull(accessToken.getToken(), "Access Token cannot be null!");
      Long expirationTimeMilliSeconds = accessToken.getExpirationTimeMilliSeconds();
      return new TokenResponse()
          .setAccessToken(token)
          .setExpiresInSeconds(
              expirationTimeMilliSeconds == null
                  ? null
                  : (expirationTimeMilliSeconds - clock.currentTimeMillis()) / 1000);
    }
  }

  private static final GoogleLogger logger = GoogleLogger.forEnclosingClass();

  /** Generate the credential from the {@link AccessTokenProvider}. */
  public static Credential credential(
      AccessTokenProvider accessTokenProvider, Collection scopes)
      throws IOException, GeneralSecurityException {
    return getCredentialFromAccessTokenProvider(accessTokenProvider, scopes);
  }

  /**
   * Generate the credential.
   *
   * 

If the {@link AccessTokenProviderClassFromConfigFactory} generates no Class for the * provider, return null. */ public static Credential credential( AccessTokenProviderClassFromConfigFactory providerClassFactory, Configuration config, Collection scopes) throws IOException, GeneralSecurityException { Class clazz = providerClassFactory.getAccessTokenProviderClass(config); if (clazz != null) { logger.atFine().log("Using AccessTokenProvider (%s)", clazz.getName()); try { AccessTokenProvider accessTokenProvider = clazz.getDeclaredConstructor().newInstance(); accessTokenProvider.setConf(config); return getCredentialFromAccessTokenProvider(accessTokenProvider, scopes); } catch (ReflectiveOperationException ex) { throw new IOException("Can't instantiate " + clazz.getName(), ex); } } return null; } /** Creates a {@link Credential} based on information from the access token provider. */ private static Credential getCredentialFromAccessTokenProvider( AccessTokenProvider accessTokenProvider, Collection scopes) throws IOException, GeneralSecurityException { Preconditions.checkArgument( accessTokenProvider.getAccessToken() != null, "Access Token cannot be null!"); GoogleCredential credential = GoogleCredentialWithAccessTokenProvider.fromAccessTokenProvider( Clock.SYSTEM, accessTokenProvider); // TODO: credential.createScoped does nothing at the moment, since // GoogleCredentialWithAccessTokenProvider never sets the serviceAccountPrivateKey. // The AccessTokenProvider interface does not provide a mechanism to return a private key, // and scopes cannot be sent down to the AccessTokenProvider // so they're essentially ignored at the moment. return credential.createScoped(scopes); } }





© 2015 - 2025 Weber Informatics LLC | Privacy Policy