您可以透過 Firebase 驗證功能,傳送內含登入連結的電子郵件給使用者,讓對方點選連結登入。系統也會在過程中驗證使用者的電子郵件地址。
使用電子郵件登入有許多好處:
- 輕鬆註冊及登入。
- 降低在不同應用程式重複使用密碼的風險,即使密碼選得再好,重複使用仍可能導致安全性問題。
- 驗證使用者身分,同時確認使用者是電子郵件地址的合法擁有者。
- 使用者只要有可存取的電子郵件帳戶就能登入。無須擁有電話號碼或社群媒體帳戶。
- 使用者不必提供 (或記住) 密碼,即可安全登入,這在行動裝置上可能很麻煩。
- 如果現有使用者先前是透過電子郵件 ID (密碼或同盟) 登入,可以升級為僅使用電子郵件登入。舉例來說,使用者忘記密碼時,仍可登入帳戶,不必重設密碼。
事前準備
使用 Swift Package Manager 安裝及管理 Firebase 依附元件。
- 在 Xcode 中保持開啟應用程式專案,然後依序點選「File」(檔案) 和「Add Packages」(新增 Package)。
- 系統提示時,請新增 Firebase Apple 平台 SDK 存放區:
- 選擇 Firebase Authentication 程式庫。
- 將
-ObjC
標記新增至目標建構設定的「Other Linker Flags」部分。 - 完成後,Xcode 會自動開始在背景中解析並下載依附元件。
https://github.com/firebase/firebase-ios-sdk.git
為 Firebase 專案啟用電子郵件連結登入功能
如要透過電子郵件連結登入使用者,請先為 Firebase 專案啟用電子郵件供應商和電子郵件連結登入方法:
- 在 Firebase 控制台中,開啟「驗證」部分。
- 在「登入方式」分頁中,啟用「電子郵件地址/密碼」供應商。請注意,如要使用電子郵件連結登入,必須先啟用電子郵件/密碼登入功能。
- 在同一個部分中,啟用「電子郵件連結 (不需要密碼即可登入)」登入方法。
- 按一下 [儲存]。
將驗證連結傳送至使用者的電子郵件地址
如要啟動驗證流程,請向使用者顯示介面,提示使用者提供電子郵件地址,然後呼叫 sendSignInLink
,要求 Firebase 將驗證連結傳送至使用者的電子郵件地址。
建構
ActionCodeSettings
物件,向 Firebase 提供電子郵件連結的建構方式。設定下列欄位:url
:要嵌入的深層連結,以及要一併傳遞的任何其他狀態。 您必須在 Firebase 主控台的授權網域清單中,將連結的網域加入許可清單。如要查看這份清單,請前往「登入方式」分頁 (「驗證」->「登入方式」)。
iOSBundleID
和androidPackageName
:協助 Firebase Authentication 判斷是否應建立僅限網頁或行動裝置的連結,並在 Android 或 Apple 裝置上開啟。handleCodeInApp
:設為 true。與其他頻外電子郵件動作 (密碼重設和電子郵件驗證) 不同,登入作業一律須在應用程式中完成。這是因為在流程結束時,使用者應已登入,且應用程式會保留其 Auth 狀態。linkDomain
:為專案定義自訂 Hosting 連結網域時,請指定要使用哪個網域,讓連結由特定行動應用程式開啟。否則系統會自動選取預設網域 (例如 )。PROJECT_ID.firebaseapp.com
dynamicLinkDomain
:已淘汰。請勿指定此參數。
Swift
let actionCodeSettings = ActionCodeSettings() actionCodeSettings.url = URL(string: "https://www.example.com") // The sign-in operation has to always be completed in the app. actionCodeSettings.handleCodeInApp = true actionCodeSettings.setIOSBundleID(Bundle.main.bundleIdentifier!) actionCodeSettings.setAndroidPackageName("com.example.android", installIfNotAvailable: false, minimumVersion: "12")
Objective-C
FIRActionCodeSettings *actionCodeSettings = [[FIRActionCodeSettings alloc] init]; [actionCodeSettings setURL:[NSURL URLWithString:@"https://www.example.com"]]; // The sign-in operation has to always be completed in the app. actionCodeSettings.handleCodeInApp = YES; [actionCodeSettings setIOSBundleID:[[NSBundle mainBundle] bundleIdentifier]]; [actionCodeSettings setAndroidPackageName:@"com.example.android" installIfNotAvailable:NO minimumVersion:@"12"];
如要進一步瞭解
ActionCodeSettings
,請參閱「在電子郵件動作中傳遞狀態」一節。詢問使用者的電子郵件地址。
將驗證連結傳送至使用者的電子郵件地址,並儲存該地址,以防使用者在同一部裝置上完成電子郵件登入程序。
Swift
Auth.auth().sendSignInLink(toEmail: email, actionCodeSettings: actionCodeSettings) { error in // ... if let error = error { self.showMessagePrompt(error.localizedDescription) return } // The link was successfully sent. Inform the user. // Save the email locally so you don't need to ask the user for it again // if they open the link on the same device. UserDefaults.standard.set(email, forKey: "Email") self.showMessagePrompt("Check your email for link") // ... }
Objective-C
[[FIRAuth auth] sendSignInLinkToEmail:email actionCodeSettings:actionCodeSettings completion:^(NSError *_Nullable error) { // ... if (error) { [self showMessagePrompt:error.localizedDescription]; return; } // The link was successfully sent. Inform the user. // Save the email locally so you don't need to ask the user for it again // if they open the link on the same device. [NSUserDefaults.standardUserDefaults setObject:email forKey:@"Email"]; [self showMessagePrompt:@"Check your email for link"]; // ... }];
使用電子郵件連結完成登入程序
安全疑慮
為避免登入連結遭人濫用,導致使用者登入錯誤帳戶或裝置,Firebase Auth 會要求使用者在完成登入流程時提供電子郵件地址。如要順利登入,這個電子郵件地址必須與登入連結原始傳送的地址相符。
如果使用者在要求連結的同一部裝置上開啟登入連結,您可以在傳送登入電子郵件時,將他們的電子郵件地址儲存在本機,簡化這個流程。然後使用這個地址完成程序。
登入完成後,系統會從使用者移除任何先前未驗證的登入機制,並使現有工作階段失效。舉例來說,如果有人先前使用相同的電子郵件地址和密碼建立未經驗證的帳戶,系統會移除該使用者的密碼,防止冒用者聲明擁有權並建立未經驗證的帳戶,然後再次使用相同帳戶登入。
在 Apple 行動應用程式中完成登入程序
Firebase Authentication 會使用 Firebase Hosting 將電子郵件連結傳送至行動裝置。如要透過行動應用程式完成登入,必須設定應用程式,以便偵測傳入的應用程式連結、剖析底層的深層連結,然後完成登入。如要進一步瞭解如何完成這項操作,請參閱「iOS 上的通用連結和相關聯網域」。
設定 Firebase Hosting
Firebase Authentication 在建立及傳送要在行動應用程式中開啟的連結時,會使用 Firebase Hosting 網域。系統已為您設定預設 Firebase Hosting 網域。
設定 Firebase Hosting 網域:
在 Firebase 控制台中,開啟「Hosting」部分。
如要使用預設網域做為在行動應用程式中開啟的電子郵件連結,請前往預設網站,並記下預設Hosting網域。預設 Hosting 網域通常如下所示:
。PROJECT_ID.firebaseapp.com
設定應用程式來攔截傳入的連結時,會需要用到這個值。
如要使用自訂網域做為電子郵件連結,可以向 Firebase Hosting 註冊網域,並將該網域用於連結。
設定 Apple 應用程式:
您必須將所選網域設定為應用程式連結的關聯網域。如要在應用程式中設定授權,請在 Xcode 中開啟目標的「Signing & Capabilities」分頁,然後將上一個步驟中的 Firebase Hosting 網域新增至「Associated Domains」功能。如果使用預設 Firebase Hosting 網域,則為
。applinks:PROJECT_ID.firebaseapp.com
詳情請參閱 Apple 說明文件網站上的「支援相關聯的網域」。
驗證連結並登入
收到上述連結後,請確認該連結是用於電子郵件連結驗證,然後完成登入程序。
Swift
if Auth.auth().isSignIn(withEmailLink: link) { Auth.auth().signIn(withEmail: email, link: self.link) { user, error in // ... } }
Objective-C
if ([[FIRAuth auth] isSignInWithEmailLink:link]) { [[FIRAuth auth] signInWithEmail:email link:link completion:^(FIRAuthDataResult * _Nullable authResult, NSError * _Nullable error) { // ... }]; }
如要瞭解如何在 Android 應用程式中處理電子郵件連結登入作業,請參閱 Android 指南。
如要瞭解如何在網頁應用程式中處理透過電子郵件連結登入的程序,請參閱網頁指南。
透過電子郵件連結連結/重新驗證
您也可以將這種驗證方法連結至現有使用者。舉例來說,使用者先前透過其他供應商 (例如電話號碼) 進行驗證,現在可以將這種登入方式新增至現有帳戶。
兩者的差異在於作業的後半部分:
Swift
let credential = EmailAuthCredential.credential(withEmail:email link:link) Auth.auth().currentUser?.link(with: credential) { authData, error in if (error) { // And error occurred during linking. return } // The provider was successfully linked. // The phone user can now sign in with their phone number or email. }
Objective-C
FIRAuthCredential *credential = [FIREmailAuthProvider credentialWithEmail:email link:link]; [FIRAuth auth].currentUser linkWithCredential:credential completion:^(FIRAuthDataResult *_Nullable result, NSError *_Nullable error) { if (error) { // And error occurred during linking. return; } // The provider was successfully linked. // The phone user can now sign in with their phone number or email. }];
您也可以使用這項功能,在執行敏感作業前,重新驗證電子郵件連結使用者。
Swift
let credential = EmailAuthProvider.credential(withEmail:email link:link) Auth.auth().currentUser?.reauthenticate(with: credential) { authData, error in if (error) { // And error occurred during re-authentication. return } // The user was successfully re-authenticated. }
Objective-C
FIRAuthCredential *credential = [FIREmailAuthCredential credentialWithEmail:email link:link]; [FIRAuth auth].currentUser reauthenticateWithCredential:credential completion:^(FIRAuthDataResult *_Nullable result, NSError *_Nullable error) { if (error) { // And error occurred during re-authentication return; } // The user was successfully re-authenticated. }];
不過,由於流程可能會在原始使用者未登入的其他裝置上結束,因此這項流程可能無法完成。在這種情況下,系統可能會向使用者顯示錯誤訊息,強制他們在同一部裝置上開啟連結。您可以在連結中傳遞某些狀態,提供作業類型和使用者 UID 的相關資訊。
已淘汰:以 Firebase Dynamic Links 為準的驗證
在 Firebase Authentication iOS SDK 11.8.0 版推出前,電子郵件連結登入功能會使用 Firebase Dynamic Links 開啟正確應用程式中的登入連結。由於 Firebase Dynamic Links 將於 2025 年 8 月 25 日關閉,因此這些驗證連結已遭淘汰。
如果應用程式使用舊版樣式的連結,請遷移應用程式至新的 Firebase Hosting 系統。
已淘汰:區分電子郵件/密碼和電子郵件連結
如果您是在 2023 年 9 月 15 日當天或之後建立專案,系統預設會啟用電子郵件列舉防護功能。這項功能可提升專案使用者帳戶的安全性,但會停用 fetchSignInMethodsForEmail()
方法,我們先前建議您實作以 ID 為優先的流程。
雖然您可以為專案停用電子郵件列舉防護功能,但我們不建議這麼做。
詳情請參閱「啟用或停用電子郵件列舉保護措施」。
後續步驟
使用者首次登入後,系統會建立新的使用者帳戶,並連結至使用者登入時使用的憑證 (即使用者名稱和密碼、電話號碼或驗證供應商資訊)。這個新帳戶會儲存在 Firebase 專案中,可用於識別專案中每個應用程式的使用者,無論使用者登入方式為何。
在 Firebase Realtime Database 和 Cloud Storage 安全規則中,您可以從
auth
變數取得已登入使用者的專屬使用者 ID, 並使用該 ID 控制使用者可存取的資料。
您可以將驗證供應商憑證連結至現有使用者帳戶,允許使用者透過多個驗證供應商登入應用程式。
如要登出使用者,請呼叫
signOut:
。
Swift
let firebaseAuth = Auth.auth() do { try firebaseAuth.signOut() } catch let signOutError as NSError { print("Error signing out: %@", signOutError) }
Objective-C
NSError *signOutError; BOOL status = [[FIRAuth auth] signOut:&signOutError]; if (!status) { NSLog(@"Error signing out: %@", signOutError); return; }
您也可以新增錯誤處理程式碼,處理各種驗證錯誤。請參閱「處理錯誤」。