Bergabunglah dengan kami secara langsung dan online di Firebase Summit pada 18 Oktober 2022. Pelajari cara Firebase dapat membantu Anda mempercepat pengembangan aplikasi, merilis aplikasi dengan percaya diri, dan menentukan skala dengan mudah. Daftar sekarang

Tambahkan otentikasi multi-faktor ke aplikasi iOS Anda

Tetap teratur dengan koleksi Simpan dan kategorikan konten berdasarkan preferensi Anda.

Jika Anda telah mengupgrade ke Firebase Authentication dengan Identity Platform, Anda dapat menambahkan autentikasi multi-faktor SMS ke aplikasi iOS Anda.

Otentikasi multi-faktor meningkatkan keamanan aplikasi Anda. Sementara penyerang sering mengkompromikan kata sandi dan akun sosial, penyadapan pesan teks lebih sulit.

Sebelum kamu memulai

  1. Aktifkan setidaknya satu penyedia yang mendukung autentikasi multi-faktor. Setiap penyedia mendukung MFA, kecuali autentikasi telepon, autentikasi anonim, dan Apple Game Center.

  2. Pastikan aplikasi Anda memverifikasi email pengguna. MFA memerlukan verifikasi email. Ini mencegah pelaku jahat mendaftar ke layanan dengan email yang tidak mereka miliki, dan kemudian mengunci pemilik sebenarnya dengan menambahkan faktor kedua.

Mengaktifkan otentikasi multi-faktor

  1. Buka halaman Authentication > Sign-in method dari Firebase console.

  2. Di bagian Lanjutan , aktifkan Otentikasi Multi-faktor SMS .

    Anda juga harus memasukkan nomor telepon yang akan digunakan untuk menguji aplikasi Anda. Meskipun opsional, mendaftarkan nomor telepon uji sangat disarankan untuk menghindari pembatasan selama pengembangan.

  3. Jika Anda belum mengotorisasi domain aplikasi, tambahkan domain tersebut ke daftar yang diizinkan di halaman Authentication > Settings di Firebase console.

Memverifikasi aplikasi Anda

Firebase perlu memverifikasi bahwa permintaan SMS berasal dari aplikasi Anda. Anda dapat melakukan ini dengan dua cara:

  • Notifikasi APN senyap : Saat Anda memasukkan pengguna untuk pertama kalinya, Firebase dapat mengirimkan notifikasi push senyap ke perangkat pengguna. Otentikasi dapat dilanjutkan jika aplikasi menerima pemberitahuan. Perhatikan bahwa mulai iOS 8.0, Anda tidak perlu meminta pengguna untuk mengizinkan pemberitahuan push menggunakan metode ini.

  • verifikasi reCAPTCHA : Jika Anda tidak dapat mengirim notifikasi senyap (misalnya, karena pengguna telah menonaktifkan penyegaran latar belakang, atau Anda sedang menguji aplikasi Anda di simulator iOS), Anda dapat menggunakan reCAPTCHA. Dalam banyak kasus, reCAPTCHA akan menyelesaikan sendiri secara otomatis tanpa interaksi pengguna.

Menggunakan notifikasi senyap

Untuk mengaktifkan notifikasi APN untuk digunakan dengan Firebase:

  1. Di Xcode, aktifkan pemberitahuan push untuk proyek Anda.

  2. Unggah kunci autentikasi APN Anda menggunakan Firebase Console (perubahan Anda akan secara otomatis dibawa ke Google Cloud Firebase). Jika Anda belum memiliki kunci autentikasi APN, lihat Mengonfigurasi APN dengan FCM untuk mempelajari cara mendapatkannya.

    1. Buka Konsol Firebase .

    2. Arahkan ke Pengaturan Proyek .

    3. Pilih tab Pesan Cloud .

    4. Di bawah kunci autentikasi APN , di bagian konfigurasi aplikasi iOS , klik Unggah .

    5. Pilih kunci Anda.

    6. Tambahkan ID kunci untuk kunci tersebut. Anda dapat menemukan ID kunci di bawah Sertifikat, Pengidentifikasi & Profil di Pusat Anggota Pengembang Apple .

    7. Klik Unggah .

Jika Anda sudah memiliki sertifikat APN, Anda dapat mengunggah sertifikat tersebut.

Menggunakan verifikasi reCAPTCHA

Untuk mengaktifkan SDK klien menggunakan reCAPTCHA:

  1. Buka konfigurasi proyek Anda di Xcode.

  2. Klik dua kali nama proyek di tampilan hierarki kiri.

  3. Pilih aplikasi Anda dari bagian Target .

  4. Pilih tab Info .

  5. Perluas bagian Jenis URL .

  6. Klik tombol + .

  7. Masukkan ID klien terbalik Anda di bidang Skema URL . Anda dapat menemukan nilai ini tercantum dalam file konfigurasi GoogleService-Info.plist sebagai REVERSED_CLIENT_ID .

Setelah selesai, konfigurasi Anda akan terlihat seperti berikut:

Skema kustom

Secara opsional, Anda dapat menyesuaikan cara aplikasi menyajikan SFSafariViewController atau UIWebView saat menampilkan reCAPTCHA. Untuk melakukannya, buat kelas khusus yang sesuai dengan protokol FIRAuthUIDelegate , dan teruskan ke verifyPhoneNumber:UIDelegate:completion: .

Memilih pola pendaftaran

Anda dapat memilih apakah aplikasi Anda memerlukan autentikasi multi-faktor, serta bagaimana dan kapan mendaftarkan pengguna Anda. Beberapa pola umum meliputi:

  • Daftarkan faktor kedua pengguna sebagai bagian dari pendaftaran. Gunakan metode ini jika aplikasi Anda memerlukan autentikasi multi-faktor untuk semua pengguna. Perhatikan bahwa akun harus memiliki alamat email terverifikasi untuk mendaftarkan faktor kedua, jadi alur pendaftaran Anda harus mengakomodasi ini.

  • Tawarkan opsi yang dapat dilewati untuk mendaftarkan faktor kedua selama pendaftaran. Aplikasi yang ingin mendorong, tetapi tidak memerlukan, autentikasi multi-faktor mungkin lebih menyukai pendekatan ini.

  • Memberikan kemampuan untuk menambahkan faktor kedua dari akun pengguna atau halaman pengelolaan profil, bukan dari layar pendaftaran. Ini meminimalkan gesekan selama proses pendaftaran, sambil tetap membuat otentikasi multi-faktor tersedia untuk pengguna yang sensitif terhadap keamanan.

  • Memerlukan penambahan faktor kedua secara bertahap saat pengguna ingin mengakses fitur dengan persyaratan keamanan yang ditingkatkan.

Mendaftarkan faktor kedua

Untuk mendaftarkan faktor sekunder baru bagi pengguna:

  1. Otentikasi ulang pengguna.

  2. Minta pengguna memasukkan nomor telepon mereka.

  3. Dapatkan sesi multi-faktor untuk pengguna:

    Cepat

    authResult.user.multiFactor.getSessionWithCompletion() { (session, error) in
      // ...
    }
    

    Objective-C

    [authResult.user.multiFactor
      getSessionWithCompletion:^(FIRMultiFactorSession * _Nullable session,
                                NSError * _Nullable error) {
        // ...
    }];
    
  4. Kirim pesan verifikasi ke ponsel pengguna. Pastikan nomor telepon diformat dengan awalan + dan tidak ada tanda baca atau spasi putih lainnya (misalnya: +15105551234 )

    Cepat

    // Send SMS verification code.
    PhoneAuthProvider.provider().verifyPhoneNumber(
      phoneNumber,
      uiDelegate: nil,
      multiFactorSession: session) { (verificationId, error) in
        // verificationId will be needed for enrollment completion.
    }
    

    Objective-C

    // Send SMS verification code.
    [FIRPhoneAuthProvider.provider verifyPhoneNumber:phoneNumber
                                          UIDelegate:nil
                                  multiFactorSession:session
                                          completion:^(NSString * _Nullable verificationID,
                                                        NSError * _Nullable error) {
        // verificationId will be needed for enrollment completion.
    }];
    

    Meskipun tidak diwajibkan, merupakan praktik terbaik untuk memberi tahu pengguna sebelumnya bahwa mereka akan menerima pesan SMS, dan tarif standar berlaku.

    Metode verifyPhoneNumber() memulai proses verifikasi aplikasi di latar belakang menggunakan pemberitahuan push senyap. Jika pemberitahuan push diam tidak tersedia, tantangan reCAPTCHA dikeluarkan sebagai gantinya.

  5. Setelah kode SMS dikirim, minta pengguna untuk memverifikasi kode. Kemudian, gunakan respons mereka untuk membuat PhoneAuthCredential :

    Cepat

    // Ask user for the verification code. Then:
    let credential = PhoneAuthProvider.provider().credential(
      withVerificationID: verificationId,
      verificationCode: verificationCode)
    

    Objective-C

    // Ask user for the SMS verification code. Then:
    FIRPhoneAuthCredential *credential = [FIRPhoneAuthProvider.provider
                                           credentialWithVerificationID:verificationID
                                           verificationCode:kPhoneSecondFactorVerificationCode];
    
  6. Inisialisasi objek pernyataan:

    Cepat

    let assertion = PhoneMultiFactorGenerator.assertion(with: credential)
    

    Objective-C

    FIRMultiFactorAssertion *assertion = [FIRPhoneMultiFactorGenerator assertionWithCredential:credential];
    
  7. Lengkapi pendaftaran. Secara opsional, Anda dapat menentukan nama tampilan untuk faktor kedua. Ini berguna untuk pengguna dengan beberapa faktor detik, karena nomor telepon disembunyikan selama alur autentikasi (misalnya, +1******1234).

    Cepat

    // Complete enrollment. This will update the underlying tokens
    // and trigger ID token change listener.
    user.multiFactor.enroll(with: assertion, displayName: displayName) { (error) in
      // ...
    }
    

    Objective-C

    // Complete enrollment. This will update the underlying tokens
    // and trigger ID token change listener.
    [authResult.user.multiFactor enrollWithAssertion:assertion
                                         displayName:nil
                                          completion:^(NSError * _Nullable error) {
        // ...
    }];
    

Kode di bawah ini menunjukkan contoh lengkap mendaftarkan faktor kedua:

Cepat

let user = Auth.auth().currentUser
user?.multiFactor.getSessionWithCompletion({ (session, error) in
  // Send SMS verification code.
  PhoneAuthProvider.provider().verifyPhoneNumber(
    phoneNumber,
    uiDelegate: nil,
    multiFactorSession: session
  ) { (verificationId, error) in
    // verificationId will be needed for enrollment completion.
    // Ask user for the verification code.
    let credential = PhoneAuthProvider.provider().credential(
      withVerificationID: verificationId!,
      verificationCode: phoneSecondFactorVerificationCode)
    let assertion = PhoneMultiFactorGenerator.assertion(with: credential)
    // Complete enrollment. This will update the underlying tokens
    // and trigger ID token change listener.
    user?.multiFactor.enroll(with: assertion, displayName: displayName) { (error) in
      // ...
    }
  }
})

Objective-C

FIRUser *user = FIRAuth.auth.currentUser;
[user.multiFactor getSessionWithCompletion:^(FIRMultiFactorSession * _Nullable session,
                                              NSError * _Nullable error) {
    // Send SMS verification code.
    [FIRPhoneAuthProvider.provider
      verifyPhoneNumber:phoneNumber
      UIDelegate:nil
      multiFactorSession:session
      completion:^(NSString * _Nullable verificationID, NSError * _Nullable error) {
        // verificationId will be needed for enrollment completion.

        // Ask user for the verification code.
        // ...

        // Then:
        FIRPhoneAuthCredential *credential =
            [FIRPhoneAuthProvider.provider credentialWithVerificationID:verificationID
                                                        verificationCode:kPhoneSecondFactorVerificationCode];
        FIRMultiFactorAssertion *assertion =
            [FIRPhoneMultiFactorGenerator assertionWithCredential:credential];

        // Complete enrollment. This will update the underlying tokens
        // and trigger ID token change listener.
        [user.multiFactor enrollWithAssertion:assertion
                                  displayName:displayName
                                    completion:^(NSError * _Nullable error) {
            // ...
        }];
    }];
}];

Selamat! Anda berhasil mendaftarkan faktor otentikasi kedua untuk pengguna.

Membuat pengguna masuk dengan faktor kedua

Untuk memasukkan pengguna dengan verifikasi SMS dua faktor:

  1. Masuk pengguna dengan faktor pertama mereka, lalu tangkap kesalahan yang menunjukkan otentikasi multi-faktor diperlukan. Kesalahan ini berisi resolver, petunjuk tentang faktor kedua yang terdaftar, dan sesi dasar yang membuktikan bahwa pengguna berhasil diautentikasi dengan faktor pertama.

    Misalnya, jika faktor pertama pengguna adalah email dan kata sandi:

    Cepat

    Auth.auth().signIn(
      withEmail: email,
      password: password
    ) { (result, error) in
      let authError = error as NSError
      if authError?.code == AuthErrorCode.secondFactorRequired.rawValue {
        // The user is a multi-factor user. Second factor challenge is required.
        let resolver =
          authError!.userInfo[AuthErrorUserInfoMultiFactorResolverKey] as! MultiFactorResolver
        // ...
      } else {
        // Handle other errors such as wrong password.
      }
    }
    

    Objective-C

    [FIRAuth.auth signInWithEmail:email
                         password:password
                       completion:^(FIRAuthDataResult * _Nullable authResult,
                                    NSError * _Nullable error) {
        if (error == nil || error.code != FIRAuthErrorCodeSecondFactorRequired) {
            // User is not enrolled with a second factor and is successfully signed in.
            // ...
        } else {
            // The user is a multi-factor user. Second factor challenge is required.
        }
    }];
    

    Jika faktor pertama pengguna adalah penyedia federasi, seperti OAuth, tangkap kesalahannya setelah memanggil getCredentialWith() .

  2. Jika pengguna memiliki beberapa faktor sekunder yang terdaftar, tanyakan yang mana yang akan digunakan. Anda bisa mendapatkan nomor telepon bertopeng dengan resolver.hints[selectedIndex].phoneNumber dan nama tampilan dengan resolver.hints[selectedIndex].displayName .

    Cepat

    // Ask user which second factor to use. Then:
    if resolver.hints[selectedIndex].factorID == PhoneMultiFactorID {
      // User selected a phone second factor.
      // ...
    } else {
      // Unsupported second factor.
      // Note that only phone second factors are currently supported.
    }
    

    Objective-C

    FIRMultiFactorResolver *resolver =
        (FIRMultiFactorResolver *) error.userInfo[FIRAuthErrorUserInfoMultiFactorResolverKey];
    
    // Ask user which second factor to use. Then:
    FIRPhoneMultiFactorInfo *hint = (FIRPhoneMultiFactorInfo *) resolver.hints[selectedIndex];
    if (hint.factorID == FIRPhoneMultiFactorID) {
      // User selected a phone second factor.
      // ...
    } else {
      // Unsupported second factor.
      // Note that only phone second factors are currently supported.
    }
    
  3. Kirim pesan verifikasi ke ponsel pengguna:

    Cepat

    // Send SMS verification code.
    let hint = resolver.hints[selectedIndex] as! PhoneMultiFactorInfo
    PhoneAuthProvider.provider().verifyPhoneNumber(
      with: hint,
      uiDelegate: nil,
      multiFactorSession: resolver.session
    ) { (verificationId, error) in
      // verificationId will be needed for sign-in completion.
    }
    

    Objective-C

    // Send SMS verification code
    [FIRPhoneAuthProvider.provider
      verifyPhoneNumberWithMultiFactorInfo:hint
      UIDelegate:nil
      multiFactorSession:resolver.session
      completion:^(NSString * _Nullable verificationID, NSError * _Nullable error) {
        if (error != nil) {
            // Failed to verify phone number.
        }
    }];
    
  4. Setelah kode SMS dikirim, minta pengguna untuk memverifikasi kode dan menggunakannya untuk membuat PhoneAuthCredential :

    Cepat

    // Ask user for the verification code. Then:
    let credential = PhoneAuthProvider.provider().credential(
      withVerificationID: verificationId!,
      verificationCode: verificationCodeFromUser)
    

    Objective-C

    // Ask user for the SMS verification code. Then:
    FIRPhoneAuthCredential *credential =
        [FIRPhoneAuthProvider.provider
          credentialWithVerificationID:verificationID
                      verificationCode:verificationCodeFromUser];
    
  5. Inisialisasi objek pernyataan dengan kredensial:

    Cepat

    let assertion = PhoneMultiFactorGenerator.assertion(with: credential)
    

    Objective-C

    FIRMultiFactorAssertion *assertion =
        [FIRPhoneMultiFactorGenerator assertionWithCredential:credential];
    
  6. Selesaikan proses masuk. Anda kemudian dapat mengakses hasil masuk asli, yang menyertakan kredensial autentikasi dan data khusus penyedia standar:

    Cepat

    // Complete sign-in. This will also trigger the Auth state listeners.
    resolver.resolveSignIn(with: assertion) { (authResult, error) in
      // authResult will also contain the user, additionalUserInfo, optional
      // credential (null for email/password) associated with the first factor sign-in.
    
      // For example, if the user signed in with Google as a first factor,
      // authResult.additionalUserInfo will contain data related to Google provider that
      // the user signed in with.
    
      // user.credential contains the Google OAuth credential.
      // user.credential.accessToken contains the Google OAuth access token.
      // user.credential.idToken contains the Google OAuth ID token.
    }
    

    Objective-C

    // Complete sign-in.
    [resolver resolveSignInWithAssertion:assertion
                              completion:^(FIRAuthDataResult * _Nullable authResult,
                                            NSError * _Nullable error) {
        if (error != nil) {
            // User successfully signed in with the second factor phone number.
        }
    }];
    

Kode di bawah ini menunjukkan contoh lengkap masuk ke pengguna multi-faktor:

Cepat

Auth.auth().signIn(
  withEmail: email,
  password: password
) { (result, error) in
  let authError = error as NSError?
  if authError?.code == AuthErrorCode.secondFactorRequired.rawValue {
    let resolver =
      authError!.userInfo[AuthErrorUserInfoMultiFactorResolverKey] as! MultiFactorResolver

    // Ask user which second factor to use.
    // ...

    // Then:
    let hint = resolver.hints[selectedIndex] as! PhoneMultiFactorInfo

    // Send SMS verification code
    PhoneAuthProvider.provider().verifyPhoneNumber(
      with: hint,
      uiDelegate: nil,
      multiFactorSession: resolver.session
    ) { (verificationId, error) in
      if error != nil {
        // Failed to verify phone number.
      }
      // Ask user for the SMS verification code.
      // ...

      // Then:
      let credential = PhoneAuthProvider.provider().credential(
        withVerificationID: verificationId!,
        verificationCode: verificationCodeFromUser)
      let assertion = PhoneMultiFactorGenerator.assertion(with: credential)

      // Complete sign-in.
      resolver.resolveSignIn(with: assertion) { (authResult, error) in
        if error != nil {
          // User successfully signed in with the second factor phone number.
        }
      }
    }
  }
}

Objective-C

[FIRAuth.auth signInWithEmail:email
                     password:password
                   completion:^(FIRAuthDataResult * _Nullable authResult,
                               NSError * _Nullable error) {
    if (error == nil || error.code != FIRAuthErrorCodeSecondFactorRequired) {
        // User is not enrolled with a second factor and is successfully signed in.
        // ...
    } else {
        FIRMultiFactorResolver *resolver =
            (FIRMultiFactorResolver *) error.userInfo[FIRAuthErrorUserInfoMultiFactorResolverKey];

        // Ask user which second factor to use.
        // ...

        // Then:
        FIRPhoneMultiFactorInfo *hint = (FIRPhoneMultiFactorInfo *) resolver.hints[selectedIndex];

        // Send SMS verification code
        [FIRPhoneAuthProvider.provider
          verifyPhoneNumberWithMultiFactorInfo:hint
                                    UIDelegate:nil
                            multiFactorSession:resolver.session
                                    completion:^(NSString * _Nullable verificationID,
                                                NSError * _Nullable error) {
            if (error != nil) {
                // Failed to verify phone number.
            }

            // Ask user for the SMS verification code.
            // ...

            // Then:
            FIRPhoneAuthCredential *credential =
                [FIRPhoneAuthProvider.provider
                  credentialWithVerificationID:verificationID
                              verificationCode:kPhoneSecondFactorVerificationCode];
            FIRMultiFactorAssertion *assertion =
                [FIRPhoneMultiFactorGenerator assertionWithCredential:credential];

            // Complete sign-in.
            [resolver resolveSignInWithAssertion:assertion
                                      completion:^(FIRAuthDataResult * _Nullable authResult,
                                                    NSError * _Nullable error) {
                if (error != nil) {
                    // User successfully signed in with the second factor phone number.
                }
            }];
        }];
    }
}];

Selamat! Anda berhasil masuk sebagai pengguna menggunakan autentikasi multi-faktor.

Apa berikutnya