Skip to content

Commit ba39057

Browse files
committed
feat(gotrue): implement linkIdentityWithIdToken method
- Add linkIdentityWithIdToken method for linking identities with ID tokens - Refactor signInWithIdToken and linkIdentityWithIdToken to share common code - Create _signInWithIdToken helper method to eliminate code duplication - Maintain backward compatibility with existing signInWithIdToken API - Add proper documentation and experimental annotation
1 parent d729fa4 commit ba39057

File tree

1 file changed

+70
-13
lines changed

1 file changed

+70
-13
lines changed

packages/gotrue/lib/src/gotrue_client.dart

Lines changed: 70 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -382,17 +382,14 @@ class GoTrueClient {
382382
/// If the ID token contains a `nonce` claim, then [nonce] must be
383383
/// provided to compare its hash with the value in the ID token.
384384
///
385-
/// [captchaToken] is the verification token received when the user
386-
/// completes the captcha on the app.
387-
///
388-
/// This method is experimental.
389-
@experimental
390-
Future<AuthResponse> signInWithIdToken({
385+
/// Sign in with ID token (internal helper method).
386+
Future<AuthResponse> _signInWithIdToken({
391387
required OAuthProvider provider,
392388
required String idToken,
393389
String? accessToken,
394390
String? nonce,
395391
String? captchaToken,
392+
required bool linkIdentity,
396393
}) async {
397394
if (provider != OAuthProvider.google &&
398395
provider != OAuthProvider.apple &&
@@ -402,18 +399,24 @@ class GoTrueClient {
402399
'${OAuthProvider.google.name}, ${OAuthProvider.apple.name}, ${OAuthProvider.kakao.name} or ${OAuthProvider.keycloak.name}.');
403400
}
404401

402+
final body = {
403+
'provider': provider.snakeCase,
404+
'id_token': idToken,
405+
'nonce': nonce,
406+
'gotrue_meta_security': {'captcha_token': captchaToken},
407+
'access_token': accessToken,
408+
};
409+
410+
if (linkIdentity) {
411+
body['link_identity'] = true;
412+
}
413+
405414
final response = await _fetch.request(
406415
'$_url/token',
407416
RequestMethodType.post,
408417
options: GotrueRequestOptions(
409418
headers: _headers,
410-
body: {
411-
'provider': provider.snakeCase,
412-
'id_token': idToken,
413-
'nonce': nonce,
414-
'gotrue_meta_security': {'captcha_token': captchaToken},
415-
'access_token': accessToken,
416-
},
419+
body: body,
417420
query: {'grant_type': 'id_token'},
418421
),
419422
);
@@ -432,6 +435,28 @@ class GoTrueClient {
432435
return authResponse;
433436
}
434437

438+
/// [captchaToken] is the verification token received when the user
439+
/// completes the captcha on the app.
440+
///
441+
/// This method is experimental.
442+
@experimental
443+
Future<AuthResponse> signInWithIdToken({
444+
required OAuthProvider provider,
445+
required String idToken,
446+
String? accessToken,
447+
String? nonce,
448+
String? captchaToken,
449+
}) async {
450+
return _signInWithIdToken(
451+
provider: provider,
452+
idToken: idToken,
453+
accessToken: accessToken,
454+
nonce: nonce,
455+
captchaToken: captchaToken,
456+
linkIdentity: false,
457+
);
458+
}
459+
435460
/// Log in a user using magiclink or a one-time password (OTP).
436461
///
437462
/// If the `{{ .ConfirmationURL }}` variable is specified in the email template, a magiclink will be sent.
@@ -914,6 +939,38 @@ class GoTrueClient {
914939
return res.user?.identities ?? [];
915940
}
916941

942+
/// Link an identity to the current user using an ID token.
943+
///
944+
/// [provider] is the OAuth provider (google, apple, kakao, or keycloak)
945+
///
946+
/// [idToken] is the ID token from the OAuth provider
947+
///
948+
/// [accessToken] is the access token from the OAuth provider
949+
///
950+
/// [nonce] is the nonce used for the OAuth flow
951+
///
952+
/// [captchaToken] is the verification token received when the user
953+
/// completes the captcha on the app.
954+
///
955+
/// This method is experimental.
956+
@experimental
957+
Future<AuthResponse> linkIdentityWithIdToken({
958+
required OAuthProvider provider,
959+
required String idToken,
960+
String? accessToken,
961+
String? nonce,
962+
String? captchaToken,
963+
}) async {
964+
return _signInWithIdToken(
965+
provider: provider,
966+
idToken: idToken,
967+
accessToken: accessToken,
968+
nonce: nonce,
969+
captchaToken: captchaToken,
970+
linkIdentity: true,
971+
);
972+
}
973+
917974
/// Returns the URL to link the user's identity with an OAuth provider.
918975
Future<OAuthResponse> getLinkIdentityUrl(
919976
OAuthProvider provider, {

0 commit comments

Comments
 (0)