Skip to content

Commit

Permalink
refactor: simplify IAM access token creation API
Browse files Browse the repository at this point in the history
  • Loading branch information
man8pr committed Apr 2, 2024
1 parent d74f77e commit 8e967c3
Show file tree
Hide file tree
Showing 7 changed files with 23 additions and 35 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,8 @@
* Wrapper around GCP IAM-API for decoupling.
*/
public interface IamService {
GcpServiceAccount ADC_SERVICE_ACCOUNT = new GcpServiceAccount("adc-email", "adc-name", "application default");

/**
* Returns the existing service account with the matching name.
*
Expand All @@ -33,15 +35,9 @@ public interface IamService {
/**
* Creates a temporary valid OAunth2.0 access token for the service account
*
* @param serviceAccount The service account the token should be created for
* @param serviceAccount service account the token should be created for;
* if null or ADC_SERVICE_ACCOUNT, access token from ADC is created.
* @return {@link GcpAccessToken}
*/
GcpAccessToken createAccessToken(GcpServiceAccount serviceAccount);

/**
* Creates a temporary valid OAunth2.0 access token using the application default account credentials.
*
* @return {@link GcpAccessToken}
*/
GcpAccessToken createDefaultAccessToken();
}
Original file line number Diff line number Diff line change
Expand Up @@ -67,6 +67,10 @@ public GcpServiceAccount getServiceAccount(String serviceAccountName) {

@Override
public GcpAccessToken createAccessToken(GcpServiceAccount serviceAccount) {
if (serviceAccount == null || serviceAccount.equals(ADC_SERVICE_ACCOUNT)) {
return applicationDefaultCredentials.getAccessToken();
}

try (var iamCredentialsClient = iamCredentialsClientSupplier.get()) {
var name = ServiceAccountName.of("-", serviceAccount.getEmail());
var lifetime = Duration.newBuilder().setSeconds(ONE_HOUR_IN_S).build();
Expand All @@ -84,11 +88,6 @@ public GcpAccessToken createAccessToken(GcpServiceAccount serviceAccount) {
}
}

@Override
public GcpAccessToken createDefaultAccessToken() {
return applicationDefaultCredentials.getAccessToken();
}

private String getServiceAccountEmail(String name, String project) {
return String.format("%s@%s.iam.gserviceaccount.com", name, project);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -114,7 +114,7 @@ void testCreateDefaultAccessToken() {
long timeout = 3600;
when(accessTokenProvider.getAccessToken()).thenReturn(new GcpAccessToken(expectedTokenString, timeout));

var accessToken = iamApi.createDefaultAccessToken();
var accessToken = iamApi.createAccessToken(IamService.ADC_SERVICE_ACCOUNT);
assertThat(accessToken.getToken()).isEqualTo(expectedTokenString);
assertThat(accessToken.getExpiration()).isEqualTo(timeout);
}
Expand All @@ -123,7 +123,7 @@ void testCreateDefaultAccessToken() {
void testCreateDefaultAccessTokenError() {
when(accessTokenProvider.getAccessToken()).thenReturn(null);

var accessToken = iamApi.createDefaultAccessToken();
var accessToken = iamApi.createAccessToken(IamService.ADC_SERVICE_ACCOUNT);
assertThat(accessToken).isNull();
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,6 @@
import static java.util.concurrent.CompletableFuture.completedFuture;

public class BigQueryProvisioner implements Provisioner<BigQueryResourceDefinition, BigQueryProvisionedResource> {
public static final GcpServiceAccount ADC_SERVICE_ACCOUNT = new GcpServiceAccount("adc-email", "adc-name", "application default");
private final GcpConfiguration gcpConfiguration;
private final BigQueryFactory bqFactory;
private final IamService iamService;
Expand Down Expand Up @@ -95,12 +94,10 @@ public CompletableFuture<StatusResult<ProvisionResponse>> provision(

GcpAccessToken token = null;

if (serviceAccount != null) {
token = iamService.createAccessToken(serviceAccount);
} else {
serviceAccount = ADC_SERVICE_ACCOUNT;
token = iamService.createDefaultAccessToken();
if (serviceAccount == null) {
serviceAccount = IamService.ADC_SERVICE_ACCOUNT;
}
token = iamService.createAccessToken(serviceAccount);
monitor.info("BigQuery Provisioner token ready");

var resource = getProvisionedResource(resourceDefinition, resourceName, tableName, serviceAccount);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -172,10 +172,8 @@ private void provisionSucceeds(String serviceAccountName) throws IOException {
// When using defuault credentials, createBigQuery is executed passing a null argument.
when(bqFactory.createBigQuery(null)).thenReturn(bigQuery);

serviceAccount = BigQueryProvisioner.ADC_SERVICE_ACCOUNT;
serviceAccount = IamService.ADC_SERVICE_ACCOUNT;
serviceAccountName = serviceAccount.getName();

when(iamService.createDefaultAccessToken()).thenReturn(token);
} else {
// Using credentials specified in the transfer request.
resourceDefinitionBuilder.property(BigQueryServiceSchema.SERVICE_ACCOUNT_NAME, serviceAccountName);
Expand All @@ -185,9 +183,8 @@ private void provisionSucceeds(String serviceAccountName) throws IOException {

serviceAccount = new GcpServiceAccount(TEST_EMAIL, serviceAccountName, TEST_DESCRIPTION);
when(iamService.getServiceAccount(serviceAccountName)).thenReturn(serviceAccount);

when(iamService.createAccessToken(serviceAccount)).thenReturn(token);
}
when(iamService.createAccessToken(serviceAccount)).thenReturn(token);

var resourceDefinition = resourceDefinitionBuilder.build();
var expectedResource = BigQueryProvisionedResource.Builder.newInstance()
Expand Down Expand Up @@ -218,7 +215,7 @@ private void provisionSucceeds(String serviceAccountName) throws IOException {
verify(iamService).getServiceAccount(serviceAccountName);
verify(iamService).createAccessToken(serviceAccount);
} else {
verify(iamService).createDefaultAccessToken();
verify(iamService).createAccessToken(serviceAccount);
}

var content = assertThat(result).succeedsWithin(1, SECONDS)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -86,11 +86,10 @@ public CompletableFuture<StatusResult<ProvisionResponse>> provision(
var serviceAccountName = getServiceAccountName(resourceDefinition);
if (serviceAccountName != null) {
serviceAccount = iamService.getServiceAccount(serviceAccountName);
token = iamService.createAccessToken(serviceAccount);
} else {
serviceAccount = new GcpServiceAccount("adc-email", "adc-name", "application default");
token = iamService.createDefaultAccessToken();
serviceAccount = IamService.ADC_SERVICE_ACCOUNT;
}
token = iamService.createAccessToken(serviceAccount);

var resource = getProvisionedResource(resourceDefinition, resourceName, bucketName, serviceAccount);

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -83,11 +83,14 @@ void provisionSuccess() {

when(storageServiceMock.getOrCreateBucket(bucketName, bucketLocation)).thenReturn(bucket);
when(storageServiceMock.isEmpty(bucketName)).thenReturn(true);
when(iamServiceMock.createDefaultAccessToken()).thenReturn(token);
when(iamServiceMock.createAccessToken(IamService.ADC_SERVICE_ACCOUNT)).thenReturn(token);
doNothing().when(storageServiceMock).addProviderPermissions(bucket, serviceAccount);

var response = provisioner.provision(resourceDefinition, testPolicy).join().getContent();

verify(storageServiceMock).getOrCreateBucket(bucketName, bucketLocation);
verify(iamServiceMock).createAccessToken(IamService.ADC_SERVICE_ACCOUNT);

assertThat(response.getResource()).isInstanceOfSatisfying(GcsProvisionedResource.class, resource -> {
assertThat(resource.getId()).isEqualTo(resourceDefinitionId);
assertThat(resource.getTransferProcessId()).isEqualTo(transferProcessId);
Expand All @@ -97,9 +100,6 @@ void provisionSuccess() {
assertThat(response.getSecretToken()).isInstanceOfSatisfying(GcpAccessToken.class, secretToken -> {
assertThat(secretToken.getToken()).isEqualTo("token");
});

verify(storageServiceMock).getOrCreateBucket(bucketName, bucketLocation);
verify(iamServiceMock).createDefaultAccessToken();
}

@Test
Expand Down Expand Up @@ -155,7 +155,7 @@ void provisionSucceedsIfBucketNotEmpty() {
assertThat(response.failed()).isFalse();

verify(storageServiceMock).getOrCreateBucket(bucketName, bucketLocation);
verify(iamServiceMock, times(1)).createDefaultAccessToken();
verify(iamServiceMock, times(1)).createAccessToken(IamService.ADC_SERVICE_ACCOUNT);
}

@Test
Expand Down

0 comments on commit 8e967c3

Please sign in to comment.