clientViaServiceAccountImpersonation function

Future<ImpersonatedAuthClient> clientViaServiceAccountImpersonation({
  1. required AuthClient sourceClient,
  2. required String targetServiceAccount,
  3. required List<String> targetScopes,
  4. List<String>? delegates,
  5. String universeDomain = defaultUniverseDomain,
  6. Duration lifetime = const Duration(hours: 1),
})

Obtains oauth2 credentials by impersonating a service account via IAM API.

Uses a source credential to call the IAM Credentials API to obtain access tokens and sign data as a target service account.

See: https://cloud.google.com/iam/docs/create-short-lived-credentials-direct

client will be used for making the HTTP requests needed to create the returned AccessCredentials.

The source client must have the roles/iam.serviceAccountTokenCreator role on the target service account.

Example:

// Get source client
final sourceClient = await clientViaServiceAccount(credentials, scopes);

// Create impersonated client
final impersonated = await clientViaServiceAccountImpersonation(
  sourceClient: sourceClient,
  targetServiceAccount: 'target@project.iam.gserviceaccount.com',
  targetScopes: ['https://www.googleapis.com/auth/cloud-platform'],
);

// Make authenticated requests
await impersonated.get(Uri.parse('https://...'));

// Sign data as the impersonated account
final signature = await impersonated.sign([1, 2, 3, 4, 5]);

// Explicitly generate a new access token
final token = await impersonated.generateAccessToken();

Implementation

Future<ImpersonatedAuthClient> clientViaServiceAccountImpersonation({
  required AuthClient sourceClient,
  required String targetServiceAccount,
  required List<String> targetScopes,
  List<String>? delegates,
  String universeDomain = defaultUniverseDomain,
  Duration lifetime = const Duration(hours: 1),
}) async {
  final impersonatedClient = ImpersonatedAuthClient(
    sourceClient: sourceClient,
    targetServiceAccount: targetServiceAccount,
    targetScopes: targetScopes,
    delegates: delegates,
    universeDomain: universeDomain,
    lifetime: lifetime,
  );

  // Generate initial credentials
  try {
    final credentials = await impersonatedClient.generateAccessToken();
    impersonatedClient._credentials = credentials;
    return impersonatedClient;
  } catch (e) {
    impersonatedClient.close();
    rethrow;
  }
}