Skip to content

Commit 7b55045

Browse files
committed
Rename OIDC delete operation and refactor integration tests. (#411)
I've renamed the delete operation since we need separate methods for deleting OIDC and SAML provider configs. I've also created a ProviderConfigTestUtils class to house shared logic between TenantAwareFirebaseAuthIT and FirebaseAuthIT, and I've added a TemporaryProviderConfig class to make it easier for provider configs to be cleaned up automatically. I've structured this class in such a way that we can easily tack on logic to cleanup SAML provider configs as well. I've also decided to remove testGetUserWithMultipleTenantIds. I initially wrote this test to understand how tenant-aware auths and tenant-agnostic auths interacted with one another. In its existing state, it appears to be leaking created users, and in order to resolve this with TemporaryUser, we would need to declare multiple TemporaryUser objects as rules. I think it's better to avoid this complexity and remove this test. After all, this integration test is mainly making assertions about the server's behavior and not our behavior.
1 parent c323314 commit 7b55045

File tree

6 files changed

+251
-235
lines changed

6 files changed

+251
-235
lines changed

src/main/java/com/google/firebase/auth/AbstractFirebaseAuth.java

Lines changed: 12 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -1107,7 +1107,7 @@ public ApiFuture<OidcProviderConfig> createOidcProviderConfigAsync(
11071107
private CallableOperation<OidcProviderConfig, FirebaseAuthException>
11081108
createOidcProviderConfigOp(final OidcProviderConfig.CreateRequest request) {
11091109
checkNotDestroyed();
1110-
checkNotNull(request, "create request must not be null");
1110+
checkNotNull(request, "Create request must not be null.");
11111111
final FirebaseUserManager userManager = getUserManager();
11121112
return new CallableOperation<OidcProviderConfig, FirebaseAuthException>() {
11131113
@Override
@@ -1147,7 +1147,7 @@ public ApiFuture<OidcProviderConfig> updateOidcProviderConfigAsync(
11471147
private CallableOperation<OidcProviderConfig, FirebaseAuthException> updateOidcProviderConfigOp(
11481148
final OidcProviderConfig.UpdateRequest request) {
11491149
checkNotDestroyed();
1150-
checkNotNull(request, "update request must not be null");
1150+
checkNotNull(request, "Update request must not be null.");
11511151
final FirebaseUserManager userManager = getUserManager();
11521152
return new CallableOperation<OidcProviderConfig, FirebaseAuthException>() {
11531153
@Override
@@ -1188,7 +1188,7 @@ public ApiFuture<OidcProviderConfig> getOidcProviderConfigAsync(@NonNull String
11881188
private CallableOperation<OidcProviderConfig, FirebaseAuthException>
11891189
getOidcProviderConfigOp(final String providerId) {
11901190
checkNotDestroyed();
1191-
checkArgument(!Strings.isNullOrEmpty(providerId), "provider ID must not be null or empty");
1191+
checkArgument(!Strings.isNullOrEmpty(providerId), "Provider ID must not be null or empty.");
11921192
final FirebaseUserManager userManager = getUserManager();
11931193
return new CallableOperation<OidcProviderConfig, FirebaseAuthException>() {
11941194
@Override
@@ -1286,38 +1286,38 @@ protected ListProviderConfigsPage<OidcProviderConfig> execute()
12861286
}
12871287

12881288
/**
1289-
* Deletes the provider config identified by the specified provider ID.
1289+
* Deletes the OIDC Auth provider config identified by the specified provider ID.
12901290
*
12911291
* @param providerId A provider ID string.
12921292
* @throws IllegalArgumentException If the provider ID string is null or empty.
12931293
* @throws FirebaseAuthException If an error occurs while deleting the provider config.
12941294
*/
1295-
public void deleteProviderConfig(@NonNull String providerId) throws FirebaseAuthException {
1296-
deleteProviderConfigOp(providerId).call();
1295+
public void deleteOidcProviderConfig(@NonNull String providerId) throws FirebaseAuthException {
1296+
deleteOidcProviderConfigOp(providerId).call();
12971297
}
12981298

12991299
/**
1300-
* Similar to {@link #deleteProviderConfig} but performs the operation asynchronously.
1300+
* Similar to {@link #deleteOidcProviderConfig} but performs the operation asynchronously.
13011301
*
13021302
* @param providerId A provider ID string.
13031303
* @return An {@code ApiFuture} which will complete successfully when the specified provider
13041304
* config has been deleted. If an error occurs while deleting the provider config, the future
13051305
* throws a {@link FirebaseAuthException}.
13061306
* @throws IllegalArgumentException If the provider ID string is null or empty.
13071307
*/
1308-
public ApiFuture<Void> deleteProviderConfigAsync(String providerId) {
1309-
return deleteProviderConfigOp(providerId).callAsync(firebaseApp);
1308+
public ApiFuture<Void> deleteOidcProviderConfigAsync(String providerId) {
1309+
return deleteOidcProviderConfigOp(providerId).callAsync(firebaseApp);
13101310
}
13111311

1312-
private CallableOperation<Void, FirebaseAuthException> deleteProviderConfigOp(
1312+
private CallableOperation<Void, FirebaseAuthException> deleteOidcProviderConfigOp(
13131313
final String providerId) {
13141314
checkNotDestroyed();
1315-
checkArgument(!Strings.isNullOrEmpty(providerId), "provider ID must not be null or empty");
1315+
checkArgument(!Strings.isNullOrEmpty(providerId), "Provider ID must not be null or empty.");
13161316
final FirebaseUserManager userManager = getUserManager();
13171317
return new CallableOperation<Void, FirebaseAuthException>() {
13181318
@Override
13191319
protected Void execute() throws FirebaseAuthException {
1320-
userManager.deleteProviderConfig(providerId);
1320+
userManager.deleteOidcProviderConfig(providerId);
13211321
return null;
13221322
}
13231323
};

src/main/java/com/google/firebase/auth/FirebaseUserManager.java

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -369,7 +369,7 @@ OidcProviderConfig createOidcProviderConfig(
369369
OidcProviderConfig.CreateRequest request) throws FirebaseAuthException {
370370
GenericUrl url = new GenericUrl(idpConfigMgtBaseUrl + "/oauthIdpConfigs");
371371
String providerId = request.getProviderId();
372-
checkArgument(!Strings.isNullOrEmpty(providerId), "provider ID must not be null or empty");
372+
checkArgument(!Strings.isNullOrEmpty(providerId), "Provider ID must not be null or empty.");
373373
url.set("oauthIdpConfigId", providerId);
374374
return sendRequest("POST", url, request.getProperties(), OidcProviderConfig.class);
375375
}
@@ -378,7 +378,7 @@ OidcProviderConfig updateOidcProviderConfig(OidcProviderConfig.UpdateRequest req
378378
throws FirebaseAuthException {
379379
Map<String, Object> properties = request.getProperties();
380380
checkArgument(!properties.isEmpty(),
381-
"provider config update must have at least one property set");
381+
"Provider config update must have at least one property set.");
382382
GenericUrl url =
383383
new GenericUrl(idpConfigMgtBaseUrl + getOidcUrlSuffix(request.getProviderId()));
384384
url.put("updateMask", generateMask(properties));
@@ -396,7 +396,7 @@ ListOidcProviderConfigsResponse listOidcProviderConfigs(int maxResults, String p
396396
ImmutableMap.<String, Object>builder().put("pageSize", maxResults);
397397
if (pageToken != null) {
398398
checkArgument(!pageToken.equals(
399-
ListTenantsPage.END_OF_LIST), "invalid end of list page token");
399+
ListTenantsPage.END_OF_LIST), "Invalid end of list page token.");
400400
builder.put("nextPageToken", pageToken);
401401
}
402402

@@ -410,7 +410,7 @@ ListOidcProviderConfigsResponse listOidcProviderConfigs(int maxResults, String p
410410
return response;
411411
}
412412

413-
void deleteProviderConfig(String providerId) throws FirebaseAuthException {
413+
void deleteOidcProviderConfig(String providerId) throws FirebaseAuthException {
414414
GenericUrl url = new GenericUrl(idpConfigMgtBaseUrl + getOidcUrlSuffix(providerId));
415415
sendRequest("DELETE", url, null, GenericJson.class);
416416
}
@@ -424,12 +424,12 @@ private static String generateMask(Map<String, Object> properties) {
424424
}
425425

426426
private static String getTenantUrlSuffix(String tenantId) {
427-
checkArgument(!Strings.isNullOrEmpty(tenantId), "tenant ID must not be null or empty");
427+
checkArgument(!Strings.isNullOrEmpty(tenantId), "Tenant ID must not be null or empty.");
428428
return "/tenants/" + tenantId;
429429
}
430430

431431
private static String getOidcUrlSuffix(String providerId) {
432-
checkArgument(!Strings.isNullOrEmpty(providerId), "provider ID must not be null or empty");
432+
checkArgument(!Strings.isNullOrEmpty(providerId), "Provider ID must not be null or empty.");
433433
return "/oauthIdpConfigs/" + providerId;
434434
}
435435

src/test/java/com/google/firebase/auth/FirebaseAuthIT.java

Lines changed: 83 additions & 104 deletions
Original file line numberDiff line numberDiff line change
@@ -46,6 +46,7 @@
4646
import com.google.firebase.FirebaseApp;
4747
import com.google.firebase.FirebaseOptions;
4848
import com.google.firebase.ImplFirebaseTrampolines;
49+
import com.google.firebase.auth.ProviderConfigTestUtils.TemporaryProviderConfig;
4950
import com.google.firebase.auth.hash.Scrypt;
5051
import com.google.firebase.internal.Nullable;
5152
import com.google.firebase.testing.IntegrationTestUtils;
@@ -84,8 +85,9 @@ public class FirebaseAuthIT {
8485
private static final FirebaseAuth auth = FirebaseAuth.getInstance(
8586
IntegrationTestUtils.ensureDefaultApp());
8687

87-
@Rule
88-
public final TemporaryUser temporaryUser = new TemporaryUser();
88+
@Rule public final TemporaryUser temporaryUser = new TemporaryUser();
89+
@Rule public final TemporaryProviderConfig temporaryProviderConfig =
90+
new TemporaryProviderConfig(auth);
8991

9092
@Test
9193
public void testGetNonExistingUser() throws Exception {
@@ -664,124 +666,113 @@ public void testGenerateSignInWithEmailLink() throws Exception {
664666
public void testOidcProviderConfigLifecycle() throws Exception {
665667
// Create config provider
666668
String providerId = "oidc.provider-id";
667-
OidcProviderConfig.CreateRequest createRequest =
669+
OidcProviderConfig config = temporaryProviderConfig.createOidcProviderConfig(
668670
new OidcProviderConfig.CreateRequest()
669671
.setProviderId(providerId)
670672
.setDisplayName("DisplayName")
671673
.setEnabled(true)
672674
.setClientId("ClientId")
673-
.setIssuer("https://oidc.com/issuer");
674-
OidcProviderConfig config = auth.createOidcProviderConfigAsync(createRequest).get();
675+
.setIssuer("https://oidc.com/issuer"));
675676
assertEquals(providerId, config.getProviderId());
676677
assertEquals("DisplayName", config.getDisplayName());
677678
assertTrue(config.isEnabled());
678679
assertEquals("ClientId", config.getClientId());
679680
assertEquals("https://oidc.com/issuer", config.getIssuer());
680681

681-
try {
682-
// Get config provider
683-
config = auth.getOidcProviderConfigAsync(providerId).get();
684-
assertEquals(providerId, config.getProviderId());
685-
assertEquals("DisplayName", config.getDisplayName());
686-
assertTrue(config.isEnabled());
687-
assertEquals("ClientId", config.getClientId());
688-
assertEquals("https://oidc.com/issuer", config.getIssuer());
682+
// Get config provider
683+
config = auth.getOidcProviderConfigAsync(providerId).get();
684+
assertEquals(providerId, config.getProviderId());
685+
assertEquals("DisplayName", config.getDisplayName());
686+
assertTrue(config.isEnabled());
687+
assertEquals("ClientId", config.getClientId());
688+
assertEquals("https://oidc.com/issuer", config.getIssuer());
689689

690-
// Update config provider
691-
OidcProviderConfig.UpdateRequest updateRequest =
692-
new OidcProviderConfig.UpdateRequest(providerId)
693-
.setDisplayName("NewDisplayName")
694-
.setEnabled(false)
695-
.setClientId("NewClientId")
696-
.setIssuer("https://oidc.com/new-issuer");
697-
config = auth.updateOidcProviderConfigAsync(updateRequest).get();
698-
assertEquals(providerId, config.getProviderId());
699-
assertEquals("NewDisplayName", config.getDisplayName());
700-
assertFalse(config.isEnabled());
701-
assertEquals("NewClientId", config.getClientId());
702-
assertEquals("https://oidc.com/new-issuer", config.getIssuer());
703-
} finally {
704-
// Delete config provider
705-
auth.deleteProviderConfigAsync(providerId).get();
706-
}
690+
// Update config provider
691+
OidcProviderConfig.UpdateRequest updateRequest =
692+
new OidcProviderConfig.UpdateRequest(providerId)
693+
.setDisplayName("NewDisplayName")
694+
.setEnabled(false)
695+
.setClientId("NewClientId")
696+
.setIssuer("https://oidc.com/new-issuer");
697+
config = auth.updateOidcProviderConfigAsync(updateRequest).get();
698+
assertEquals(providerId, config.getProviderId());
699+
assertEquals("NewDisplayName", config.getDisplayName());
700+
assertFalse(config.isEnabled());
701+
assertEquals("NewClientId", config.getClientId());
702+
assertEquals("https://oidc.com/new-issuer", config.getIssuer());
707703

708-
assertOidcProviderConfigDoesNotExist(auth, providerId);
704+
// Delete config provider
705+
auth.deleteOidcProviderConfigAsync(providerId).get();
706+
ProviderConfigTestUtils.assertOidcProviderConfigDoesNotExist(auth, providerId);
709707
}
710708

711709
@Test
712710
public void testListOidcProviderConfigs() throws Exception {
713711
final List<String> providerIds = new ArrayList<>();
714712

715-
try {
716-
// Create provider configs
717-
for (int i = 0; i < 3; i++) {
718-
String providerId = "oidc.provider-id" + i;
719-
providerIds.add(providerId);
720-
OidcProviderConfig.CreateRequest createRequest = new OidcProviderConfig.CreateRequest()
713+
// Create provider configs
714+
for (int i = 0; i < 3; i++) {
715+
String providerId = "oidc.provider-id" + i;
716+
providerIds.add(providerId);
717+
OidcProviderConfig config = temporaryProviderConfig.createOidcProviderConfig(
718+
new OidcProviderConfig.CreateRequest()
721719
.setProviderId(providerId)
722720
.setClientId("CLIENT_ID")
723-
.setIssuer("https://oidc.com/issuer");
724-
auth.createOidcProviderConfig(createRequest);
725-
}
726-
727-
// Test list by batches
728-
final AtomicInteger collected = new AtomicInteger(0);
729-
ListProviderConfigsPage<OidcProviderConfig> page =
730-
auth.listOidcProviderConfigsAsync(null).get();
731-
while (page != null) {
732-
for (OidcProviderConfig providerConfig : page.getValues()) {
733-
if (checkProviderConfig(providerIds, providerConfig)) {
734-
collected.incrementAndGet();
735-
}
736-
}
737-
page = page.getNextPage();
738-
}
739-
assertEquals(providerIds.size(), collected.get());
721+
.setIssuer("https://oidc.com/issuer"));
722+
}
740723

741-
// Test iterate all
742-
collected.set(0);
743-
page = auth.listOidcProviderConfigsAsync(null).get();
744-
for (OidcProviderConfig providerConfig : page.iterateAll()) {
724+
// Test list by batches
725+
final AtomicInteger collected = new AtomicInteger(0);
726+
ListProviderConfigsPage<OidcProviderConfig> page =
727+
auth.listOidcProviderConfigsAsync(null).get();
728+
while (page != null) {
729+
for (OidcProviderConfig providerConfig : page.getValues()) {
745730
if (checkProviderConfig(providerIds, providerConfig)) {
746731
collected.incrementAndGet();
747732
}
748733
}
749-
assertEquals(providerIds.size(), collected.get());
750-
751-
// Test iterate async
752-
collected.set(0);
753-
final Semaphore semaphore = new Semaphore(0);
754-
final AtomicReference<Throwable> error = new AtomicReference<>();
755-
ApiFuture<ListProviderConfigsPage<OidcProviderConfig>> pageFuture =
756-
auth.listOidcProviderConfigsAsync(null);
757-
ApiFutures.addCallback(
758-
pageFuture,
759-
new ApiFutureCallback<ListProviderConfigsPage<OidcProviderConfig>>() {
760-
@Override
761-
public void onFailure(Throwable t) {
762-
error.set(t);
763-
semaphore.release();
764-
}
734+
page = page.getNextPage();
735+
}
736+
assertEquals(providerIds.size(), collected.get());
765737

766-
@Override
767-
public void onSuccess(ListProviderConfigsPage<OidcProviderConfig> result) {
768-
for (OidcProviderConfig providerConfig : result.iterateAll()) {
769-
if (checkProviderConfig(providerIds, providerConfig)) {
770-
collected.incrementAndGet();
771-
}
772-
}
773-
semaphore.release();
774-
}
775-
}, MoreExecutors.directExecutor());
776-
semaphore.acquire();
777-
assertEquals(providerIds.size(), collected.get());
778-
assertNull(error.get());
779-
} finally {
780-
// Delete provider configs
781-
for (String providerId : providerIds) {
782-
auth.deleteProviderConfigAsync(providerId).get();
738+
// Test iterate all
739+
collected.set(0);
740+
page = auth.listOidcProviderConfigsAsync(null).get();
741+
for (OidcProviderConfig providerConfig : page.iterateAll()) {
742+
if (checkProviderConfig(providerIds, providerConfig)) {
743+
collected.incrementAndGet();
783744
}
784745
}
746+
assertEquals(providerIds.size(), collected.get());
747+
748+
// Test iterate async
749+
collected.set(0);
750+
final Semaphore semaphore = new Semaphore(0);
751+
final AtomicReference<Throwable> error = new AtomicReference<>();
752+
ApiFuture<ListProviderConfigsPage<OidcProviderConfig>> pageFuture =
753+
auth.listOidcProviderConfigsAsync(null);
754+
ApiFutures.addCallback(
755+
pageFuture,
756+
new ApiFutureCallback<ListProviderConfigsPage<OidcProviderConfig>>() {
757+
@Override
758+
public void onFailure(Throwable t) {
759+
error.set(t);
760+
semaphore.release();
761+
}
762+
763+
@Override
764+
public void onSuccess(ListProviderConfigsPage<OidcProviderConfig> result) {
765+
for (OidcProviderConfig providerConfig : result.iterateAll()) {
766+
if (checkProviderConfig(providerIds, providerConfig)) {
767+
collected.incrementAndGet();
768+
}
769+
}
770+
semaphore.release();
771+
}
772+
}, MoreExecutors.directExecutor());
773+
semaphore.acquire();
774+
assertEquals(providerIds.size(), collected.get());
775+
assertNull(error.get());
785776
}
786777

787778
private Map<String, String> parseLinkParameters(String link) throws Exception {
@@ -924,23 +915,11 @@ private boolean checkProviderConfig(List<String> providerIds, OidcProviderConfig
924915
}
925916

926917

927-
private static void assertOidcProviderConfigDoesNotExist(
928-
AbstractFirebaseAuth firebaseAuth, String providerId) throws Exception {
929-
try {
930-
firebaseAuth.getOidcProviderConfigAsync(providerId).get();
931-
fail("No error thrown for getting a deleted provider config");
932-
} catch (ExecutionException e) {
933-
assertTrue(e.getCause() instanceof FirebaseAuthException);
934-
assertEquals(FirebaseUserManager.CONFIGURATION_NOT_FOUND_ERROR,
935-
((FirebaseAuthException) e.getCause()).getErrorCode());
936-
}
937-
}
938-
939918
private static void assertUserDoesNotExist(AbstractFirebaseAuth firebaseAuth, String uid)
940919
throws Exception {
941920
try {
942921
firebaseAuth.getUserAsync(uid).get();
943-
fail("No error thrown for getting a user which was expected to be absent");
922+
fail("No error thrown for getting a user which was expected to be absent.");
944923
} catch (ExecutionException e) {
945924
assertTrue(e.getCause() instanceof FirebaseAuthException);
946925
assertEquals(FirebaseUserManager.USER_NOT_FOUND_ERROR,

0 commit comments

Comments
 (0)