google/googleapis.dart

Auth: Support impersonate service account with gcloud cli

Open

#454 ouverte le 30 sept. 2022

Voir sur GitHub
 (2 commentaires) (0 réactions) (0 assignés)Dart (133 forks)github user discovery
enhancementhelp wantedpackage:googleapis_auth

Métriques du dépôt

Stars
 (419 stars)
Métriques de merge PR
 (Métriques PR en attente)

Description

Hi, It will be great if we can use impersonate service account with gcloud cli, so that it can test google service locally without downloading a service account.

currently clientViaApplicationDefaultCredentials will not use source_credentials when running this command

gcloud auth application-default login --impersonate-service-account=principal@example.iam.gserviceaccount.com

the parsing credentials here does not check for source_credentials. as a workaround I just added some code and work properly.

https://github.com/google/googleapis.dart/blob/02ed7aa02ce7fa304b7d5b40eb93b672f46cad63/googleapis_auth/lib/src/adc_utils.dart#L16

Future<AutoRefreshingAuthClient> fromApplicationsCredentialsFile(
  File file,
  String fileSource,
  List<String> scopes,
  Client baseClient,
) async {
  Object? credentials;
  try {
    credentials = json.decode(await file.readAsString());
  } on IOException {
    throw Exception(
      'Failed to read credentials file from $fileSource',
    );
  } on FormatException {
    throw Exception(
      'Failed to parse JSON from credentials file from $fileSource',
    );
  }

  if (credentials is Map && credentials['type'] == 'authorized_user') {
    final clientId = ClientId(
      credentials['client_id'] as String,
      credentials['client_secret'] as String?,
    );
    return AutoRefreshingClient(
      baseClient,
      clientId,
      await refreshCredentials(
        clientId,
        AccessCredentials(
          // Hack: Create empty credentials that have expired.
          AccessToken('Bearer', '', DateTime(0).toUtc()),
          credentials['refresh_token'] as String?,
          scopes,
        ),
        baseClient,
      ),
      quotaProject: credentials['quota_project_id'] as String?,
    );
  }

  if (credentials is Map && credentials['source_credentials']?['type'] == 'authorized_user') {
    final clientId = ClientId(
      credentials['source_credentials']['client_id'] as String,
      credentials['source_credentials']['client_secret'] as String?,
    );
    return AutoRefreshingClient(
      baseClient,
      clientId,
      await refreshCredentials(
        clientId,
        AccessCredentials(
          // Hack: Create empty credentials that have expired.
          AccessToken('Bearer', '', DateTime(0).toUtc()),
          credentials['source_credentials']['refresh_token'] as String?,
          scopes,
        ),
        baseClient,
      ),
      quotaProject: credentials['quota_project_id'] as String?,
    );
  }

  return await clientViaServiceAccount(
    ServiceAccountCredentials.fromJson(credentials),
    scopes,
    baseClient: baseClient,
  );
}

Guide contributeur