میتوانید به کاربران اجازه دهید با پیوند دادن اطلاعات اعتباری ارائهدهنده اصالتسنجی به حساب کاربری موجود، بااستفاده از چندین ارائهدهنده اصالتسنجی به سیستم برنامهتان وارد شوند. کاربران صرفنظر از ارائهدهنده اصالتسنجی که برای ورود به سیستم استفاده کردهاند، با همان شناسه کاربر Firebase قابلشناسایی هستند. برای مثال، کاربری که با گذرواژه به سیستم وارد شده است میتواند «حساب Google» را پیوند دهد و در آینده با هریک از این روشها به سیستم وارد شود. یا، کاربر ناشناسی میتواند حساب Facebook را پیوند دهد و سپس، بعداً با Facebook به سیستم وارد شود تا به استفاده از برنامه شما ادامه دهد.
قبل از شروع
پشتیبانی از دو یا چند ارائهدهنده اصالتسنجی (احتمالاً شامل اصالتسنجی ناشناس) را به برنامهتان اضافه کنید.
پیوند دادن اطلاعات اعتباری ارائهدهنده اصالتسنجی به حساب کاربر
برای پیوند دادن اطلاعات اعتباری ارائهدهنده اصالتسنجی به حساب کاربری موجود:
- کاربر را بااستفاده از هر روش یا ارائهدهنده اصالتسنجی به سیستم وارد کنید.
- جریان ورود به سیستم را برای ارائهدهنده اصالتسنجی جدید تا مرحله فراخوانی یکی از روشهای
FIRAuth.signInWithتکمیل کنید، اما این مرحله را شامل نشود. برای مثال، گذرکلید Google کاربر، گذرکلید دسترسی Facebook، یا ایمیل و گذرواژه را دریافت کنید.
FIRAuthCredentialرا برای ارائهدهنده اصالتسنجی جدید دریافت کنید:ورود با Google
Swift
guard let authentication = user?.authentication, let idToken = authentication.idToken else { return } let credential = GoogleAuthProvider.credential(withIDToken: idToken, accessToken: authentication.accessToken)
Objective-C
FIRAuthCredential *credential = [FIRGoogleAuthProvider credentialWithIDToken:result.user.idToken.tokenString accessToken:result.user.accessToken.tokenString];
ورود به سیستم فیسبوک
Swift
let credential = FacebookAuthProvider .credential(withAccessToken: AccessToken.current!.tokenString)
Objective-C
FIRAuthCredential *credential = [FIRFacebookAuthProvider credentialWithAccessToken:[FBSDKAccessToken currentAccessToken].tokenString];
ورود به سیستم با ایمیل و گذرواژه
Swift
let credential = EmailAuthProvider.credential(withEmail: email, password: password)
Objective-C
FIRAuthCredential *credential = [FIREmailAuthProvider credentialWithEmail:email password:password];
شیء
FIRAuthCredentialرا به روشlinkWithCredential:completion:کاربر واردشده به سیستم ارسال کنید:Swift
user.link(with: credential) { authResult, error in // ... } }
Objective-C
[[FIRAuth auth].currentUser linkWithCredential:credential completion:^(FIRAuthDataResult *result, NSError *_Nullable error) { // ... }];
اگر اطلاعات اعتباری ازقبل به حساب کاربری دیگری پیوند داده شده باشد، تماس با
linkWithCredential:completion:ناموفق خواهد بود. در این وضعیت، باید ادغام حسابها و دادههای منسوب را بهنحوی که برای برنامهتان مناسب است انجام دهید:Swift
let prevUser = Auth.auth().currentUser Auth.auth().signIn(with: credential) { authResult, error in if let error = error { let authError = error as NSError if isMFAEnabled, authError.code == AuthErrorCode.secondFactorRequired.rawValue { // The user is a multi-factor user. Second factor challenge is required. let resolver = authError .userInfo[AuthErrorUserInfoMultiFactorResolverKey] as! MultiFactorResolver var displayNameString = "" for tmpFactorInfo in resolver.hints { displayNameString += tmpFactorInfo.displayName ?? "" displayNameString += " " } self.showTextInputPrompt( withMessage: "Select factor to sign in\n\(displayNameString)", completionBlock: { userPressedOK, displayName in var selectedHint: PhoneMultiFactorInfo? for tmpFactorInfo in resolver.hints { if displayName == tmpFactorInfo.displayName { selectedHint = tmpFactorInfo as? PhoneMultiFactorInfo } } PhoneAuthProvider.provider() .verifyPhoneNumber(with: selectedHint!, uiDelegate: nil, multiFactorSession: resolver .session) { verificationID, error in if error != nil { print( "Multi factor start sign in failed. Error: \(error.debugDescription)" ) } else { self.showTextInputPrompt( withMessage: "Verification code for \(selectedHint?.displayName ?? "")", completionBlock: { userPressedOK, verificationCode in let credential: PhoneAuthCredential? = PhoneAuthProvider.provider() .credential(withVerificationID: verificationID!, verificationCode: verificationCode!) let assertion: MultiFactorAssertion? = PhoneMultiFactorGenerator .assertion(with: credential!) resolver.resolveSignIn(with: assertion!) { authResult, error in if error != nil { print( "Multi factor finanlize sign in failed. Error: \(error.debugDescription)" ) } else { self.navigationController?.popViewController(animated: true) } } } ) } } } ) } else { self.showMessagePrompt(error.localizedDescription) return } // ... return } // User is signed in // ... } // Merge prevUser and currentUser accounts and data // ... }
Objective-C
FIRUser *prevUser = [FIRAuth auth].currentUser; [[FIRAuth auth] signInWithCredential:credential completion:^(FIRAuthDataResult * _Nullable authResult, NSError * _Nullable error) { if (isMFAEnabled && error && error.code == FIRAuthErrorCodeSecondFactorRequired) { FIRMultiFactorResolver *resolver = error.userInfo[FIRAuthErrorUserInfoMultiFactorResolverKey]; NSMutableString *displayNameString = [NSMutableString string]; for (FIRMultiFactorInfo *tmpFactorInfo in resolver.hints) { [displayNameString appendString:tmpFactorInfo.displayName]; [displayNameString appendString:@" "]; } [self showTextInputPromptWithMessage:[NSString stringWithFormat:@"Select factor to sign in\n%@", displayNameString] completionBlock:^(BOOL userPressedOK, NSString *_Nullable displayName) { FIRPhoneMultiFactorInfo* selectedHint; for (FIRMultiFactorInfo *tmpFactorInfo in resolver.hints) { if ([displayName isEqualToString:tmpFactorInfo.displayName]) { selectedHint = (FIRPhoneMultiFactorInfo *)tmpFactorInfo; } } [FIRPhoneAuthProvider.provider verifyPhoneNumberWithMultiFactorInfo:selectedHint UIDelegate:nil multiFactorSession:resolver.session completion:^(NSString * _Nullable verificationID, NSError * _Nullable error) { if (error) { [self showMessagePrompt:error.localizedDescription]; } else { [self showTextInputPromptWithMessage:[NSString stringWithFormat:@"Verification code for %@", selectedHint.displayName] completionBlock:^(BOOL userPressedOK, NSString *_Nullable verificationCode) { FIRPhoneAuthCredential *credential = [[FIRPhoneAuthProvider provider] credentialWithVerificationID:verificationID verificationCode:verificationCode]; FIRMultiFactorAssertion *assertion = [FIRPhoneMultiFactorGenerator assertionWithCredential:credential]; [resolver resolveSignInWithAssertion:assertion completion:^(FIRAuthDataResult * _Nullable authResult, NSError * _Nullable error) { if (error) { [self showMessagePrompt:error.localizedDescription]; } else { NSLog(@"Multi factor finanlize sign in succeeded."); } }]; }]; } }]; }]; } else if (error) { // ... return; } // User successfully signed in. Get user data from the FIRUser object if (authResult == nil) { return; } FIRUser *user = authResult.user; // ... }]; // Merge prevUser and currentUser accounts and data // ... }];
اگر تماس با linkWithCredential:completion: موفقیتآمیز باشد، کاربر اکنون میتواند بااستفاده از
هریک از ارائهدهندگان اصالتسنجی پیوندشده به سیستم وارد شود و به همان دادههای Firebase دسترسی پیدا کند.
لغو پیوند ارائهدهنده اصالتسنجی از حساب کاربر
یک حساب کاربری Firebase میتواند چندین ارائهدهنده اصالتسنجی پیوندشده داشته باشد (برای مثال، ایمیل/گذرواژه، Google، Facebook)، که به کاربر امکان میدهد ازطریق روشهای مختلف به همان حساب Firebase وارد شود.
اگر ارائهدهنده اصالتسنجی را از حساب کاربری لغو پیوند کنید، کاربر دیگر نمیتواند با آن ارائهدهنده به سیستم وارد شود.
برای لغو پیوند ارائهدهنده اصالتسنجی از حساب کاربر، شناسه ارائهدهنده را به
متد unlink ارسال کنید. میتوانید شناسههای ارائهدهنده
ارائهدهندگان اصالتسنجی پیوندشده به کاربر را از providerData
دارایی دریافت کنید.
Swift
Auth.auth().currentUser?.unlink(fromProvider: providerID!) { user, error in // ... }
Objective-C
[[FIRAuth auth].currentUser unlinkFromProvider:providerID completion:^(FIRUser *_Nullable user, NSError *_Nullable error) { // ... }];
عیبیابی
اگر هنگام تلاش برای پیوند دادن چند حساب با خطا مواجه شدید، مستندات مربوط به نشانیهای ایمیل تأییدشده را ببینید.