diff --git a/phpunit.xml.dist b/phpunit.xml.dist index 415a835b4..60553299c 100644 --- a/phpunit.xml.dist +++ b/phpunit.xml.dist @@ -6,6 +6,10 @@ bootstrap="tests/bootstrap.php" colors="true" > + + + + tests/Unit diff --git a/src/Firebase/Auth.php b/src/Firebase/Auth.php index 65a1e68b5..d079c22f3 100644 --- a/src/Firebase/Auth.php +++ b/src/Firebase/Auth.php @@ -59,7 +59,7 @@ /** * @internal */ -final class Auth implements Contract\Auth +final class Auth implements Contract\Auth, Contract\Transitional\FederatedUserFetcher { private readonly Parser $jwtParser; @@ -210,6 +210,22 @@ public function getUserByPhoneNumber(Stringable|string $phoneNumber): UserRecord return UserRecord::fromResponseData($data['users'][0]); } + public function getUserByProviderUid(Stringable|string $providerId, Stringable|string $providerUid): UserRecord + { + $providerId = (string) $providerId; + $providerUid = (string) $providerUid; + + $response = $this->client->getUserByProviderUid($providerId, $providerUid); + + $data = Json::decode((string) $response->getBody(), true); + + if (empty($data['users'][0])) { + throw new UserNotFound("No user with federated account ID '{$providerId}:{$providerUid}' found."); + } + + return UserRecord::fromResponseData($data['users'][0]); + } + public function createAnonymousUser(): UserRecord { return $this->createUser(CreateUser::new()); diff --git a/src/Firebase/Auth/ApiClient.php b/src/Firebase/Auth/ApiClient.php index 7775c6153..749a53bd9 100644 --- a/src/Firebase/Auth/ApiClient.php +++ b/src/Firebase/Auth/ApiClient.php @@ -118,6 +118,16 @@ public function getUserByPhoneNumber(string $phoneNumber): ResponseInterface return $this->requestApi($url, ['phoneNumber' => [$phoneNumber]]); } + /** + * @throws AuthException + */ + public function getUserByProviderUid(string $providerId, string $uid): ResponseInterface + { + $url = $this->awareAuthResourceUrlBuilder->getUrl('/accounts:lookup'); + + return $this->requestApi($url, ['federatedUserId' => [['providerId' => $providerId, 'rawId' => $uid]]]); + } + /** * @throws AuthException */ diff --git a/src/Firebase/Contract/Transitional/FederatedUserFetcher.php b/src/Firebase/Contract/Transitional/FederatedUserFetcher.php new file mode 100644 index 000000000..c894ddb01 --- /dev/null +++ b/src/Firebase/Contract/Transitional/FederatedUserFetcher.php @@ -0,0 +1,24 @@ +auth->getUserByPhoneNumber($phoneNumber); } + #[Test] + public function getUserByNonExistingProviderUid(): void + { + if ($this->auth instanceof FederatedUserFetcher) { + $provider = 'test.com'; + $uid = 'u' . random_int(1000000, 9999999); + + $this->expectException(UserNotFound::class); + /** @phpstan-ignore method.notFound */ + $this->auth->getUserByProviderUid($provider, $uid); + } else { + $this->fail("{\$this->auth} does not implement FederatedUserFetcher as expected - cannot test"); + } + } + #[Test] public function createUser(): void {