หากอัปเกรดเป็น Firebase Authentication ที่มี Identity Platform แล้ว คุณจะเพิ่มการตรวจสอบสิทธิ์แบบหลายปัจจัยทาง SMS ลงในแอป Flutter ได้
การตรวจสอบสิทธิ์แบบหลายปัจจัย (MFA) ช่วยเพิ่มความปลอดภัยให้แอปของคุณ แม้ว่าผู้โจมตีมักเจาะรหัสผ่านและบัญชีโซเชียล แต่การสกัดกั้นข้อความมีความยากมากกว่า
ก่อนเริ่มต้น
เปิดใช้ผู้ให้บริการอย่างน้อย 1 รายที่รองรับการตรวจสอบสิทธิ์แบบหลายปัจจัย ผู้ให้บริการทุกรายรองรับ MFA ยกเว้นการตรวจสอบสิทธิ์ทางโทรศัพท์ การตรวจสอบสิทธิ์แบบไม่ระบุชื่อ และผ่าน Game Center ของ Apple
ตรวจสอบว่าแอปของคุณยืนยันอีเมลของผู้ใช้ คุณต้องยืนยันอีเมลก่อนจึงจะใช้ MFA ได้ ซึ่งจะช่วยป้องกันไม่ให้ผู้ไม่ประสงค์ดีลงทะเบียนใช้บริการด้วยอีเมลที่ไม่ได้เป็นเจ้าของ แล้วล็อกเจ้าของจริงไม่ให้เข้าถึงได้โดยการเพิ่มปัจจัยที่ 2
Android: หากคุณยังไม่ได้ตั้งค่าแฮช SHA-256 ของแอปในคอนโซล Firebase ให้ตั้งค่าดังกล่าว ดูข้อมูลเกี่ยวกับการค้นหาแฮช SHA-256 ของแอปได้ที่การตรวจสอบสิทธิ์ไคลเอ็นต์
iOS: ใน Xcode ให้เปิดใช้ข้อความ Push สําหรับโปรเจ็กต์ และตรวจสอบว่ากําหนดค่าคีย์การตรวจสอบสิทธิ์ APNs กับ Firebase Cloud Messaging (FCM) แล้ว นอกจากนี้ คุณต้องเปิดใช้โหมดเบื้องหลังสำหรับการแจ้งเตือนจากระยะไกล หากต้องการดูคําอธิบายโดยละเอียดของขั้นตอนนี้ โปรดดูเอกสารประกอบการตรวจสอบสิทธิ์ทางโทรศัพท์ของ Firebase สำหรับ iOS
เว็บ: ตรวจสอบว่าคุณได้เพิ่มโดเมนแอปพลิเคชันในคอนโซล Firebase ในส่วนโดเมนการเปลี่ยนเส้นทาง OAuth แล้ว
การเปิดใช้การตรวจสอบสิทธิ์แบบหลายปัจจัย
เปิดหน้าการตรวจสอบสิทธิ์ > วิธีการลงชื่อเข้าใช้ของคอนโซล Firebase
ในส่วนขั้นสูง ให้เปิดใช้การตรวจสอบสิทธิ์แบบหลายปัจจัยทาง SMS
นอกจากนี้ คุณควรป้อนหมายเลขโทรศัพท์ที่จะใช้ทดสอบแอปด้วย แม้ว่าจะไม่ใช่สิ่งจําเป็น แต่เราขอแนะนําอย่างยิ่งให้ลงทะเบียนหมายเลขโทรศัพท์ที่ใช้ทดสอบเพื่อหลีกเลี่ยงการจํากัดในระหว่างการพัฒนา
หากยังไม่ได้ให้สิทธิ์โดเมนของแอป ให้เพิ่มโดเมนนั้นลงในรายการที่อนุญาตในหน้าการตรวจสอบสิทธิ์ > การตั้งค่าของคอนโซล Firebase
การเลือกรูปแบบการลงทะเบียน
คุณเลือกได้ว่าจะให้แอปใช้การตรวจสอบสิทธิ์แบบหลายปัจจัยหรือไม่ รวมถึงวิธีและเวลาลงทะเบียนผู้ใช้ รูปแบบที่พบบ่อยบางรายการมีดังนี้
ลงทะเบียนปัจจัยที่ 2 ของผู้ใช้เป็นส่วนหนึ่งของการลงทะเบียน ใช้วิธีนี้หากแอปกำหนดให้ผู้ใช้ทุกคนต้องการตรวจสอบสิทธิ์แบบหลายปัจจัย
เสนอตัวเลือกที่ข้ามได้เพื่อลงทะเบียนปัจจัยที่ 2 ในระหว่างการลงทะเบียน แอปที่ต้องการส่งเสริมแต่ไม่บังคับให้ใช้การตรวจสอบสิทธิ์แบบหลายปัจจัยอาจเลือกใช้แนวทางนี้
เพิ่มตัวเลือกให้เพิ่มปัจจัยที่ 2 จากหน้าการจัดการบัญชีหรือโปรไฟล์ของผู้ใช้แทนที่จะเป็นหน้าจอลงชื่อสมัครใช้ วิธีนี้ช่วยลดความยุ่งยากในกระบวนการลงทะเบียนไปพร้อมกับทำให้การตรวจสอบสิทธิ์แบบหลายปัจจัยพร้อมใช้งานสำหรับผู้ใช้ที่ให้ความสำคัญกับความปลอดภัย
กำหนดให้เพิ่มปัจจัยที่ 2 เมื่อผู้ใช้ต้องการเข้าถึงฟีเจอร์ที่มีข้อกำหนดด้านความปลอดภัยที่เพิ่มขึ้น
การลงทะเบียนปัจจัยที่ 2
วิธีลงทะเบียนปัจจัยรองใหม่ให้กับผู้ใช้
ตรวจสอบสิทธิ์ผู้ใช้อีกครั้ง
ขอให้ผู้ใช้ป้อนหมายเลขโทรศัพท์
รับเซสชันแบบหลายปัจจัยสำหรับผู้ใช้ โดยทำดังนี้
final multiFactorSession = await user.multiFactor.getSession();
ยืนยันหมายเลขโทรศัพท์ด้วยเซสชันการตรวจสอบสิทธิ์แบบหลายปัจจัยและการโทรกลับ
await FirebaseAuth.instance.verifyPhoneNumber( multiFactorSession: multiFactorSession, phoneNumber: phoneNumber, verificationCompleted: (_) {}, verificationFailed: (_) {}, codeSent: (String verificationId, int? resendToken) async { // The SMS verification code has been sent to the provided phone number. // ... }, codeAutoRetrievalTimeout: (_) {}, );
เมื่อส่งรหัส SMS แล้ว ให้ขอให้ผู้ใช้ยืนยันรหัสโดยทำดังนี้
final credential = PhoneAuthProvider.credential( verificationId: verificationId, smsCode: smsCode, );
ลงทะเบียนให้เสร็จสมบูรณ์โดยทำดังนี้
await user.multiFactor.enroll( PhoneMultiFactorGenerator.getAssertion( credential, ), );
โค้ดด้านล่างแสดงตัวอย่างที่สมบูรณ์ของการลงทะเบียนปัจจัยที่ 2
final session = await user.multiFactor.getSession();
final auth = FirebaseAuth.instance;
await auth.verifyPhoneNumber(
multiFactorSession: session,
phoneNumber: phoneController.text,
verificationCompleted: (_) {},
verificationFailed: (_) {},
codeSent: (String verificationId, int? resendToken) async {
// See `firebase_auth` example app for a method of retrieving user's sms code:
// https://github.com/firebase/flutterfire/blob/main/packages/firebase_auth/firebase_auth/example/lib/auth.dart#L591
final smsCode = await getSmsCodeFromUser(context);
if (smsCode != null) {
// Create a PhoneAuthCredential with the code
final credential = PhoneAuthProvider.credential(
verificationId: verificationId,
smsCode: smsCode,
);
try {
await user.multiFactor.enroll(
PhoneMultiFactorGenerator.getAssertion(
credential,
),
);
} on FirebaseAuthException catch (e) {
print(e.message);
}
}
},
codeAutoRetrievalTimeout: (_) {},
);
ยินดีด้วย คุณลงทะเบียนปัจจัยที่ 2 ของการตรวจสอบสิทธิ์สําหรับผู้ใช้เรียบร้อยแล้ว
การลงชื่อเข้าใช้ของผู้ใช้ด้วยปัจจัยที่ 2
วิธีลงชื่อเข้าใช้ผู้ใช้ด้วยการยืนยันแบบ 2 ขั้นตอนผ่าน SMS
ลงชื่อเข้าใช้ผู้ใช้ด้วยปัจจัยแรก จากนั้นจับข้อยกเว้น
FirebaseAuthMultiFactorException
ข้อผิดพลาดนี้มีโปรแกรมแก้ไข ซึ่งคุณใช้เพื่อรับปัจจัยที่ 2 ที่ลงทะเบียนของผู้ใช้ได้ รวมถึงมีเซสชันพื้นฐานที่พิสูจน์ว่าผู้ใช้ตรวจสอบสิทธิ์ด้วยปัจจัยแรกสำเร็จตัวอย่างเช่น หากปัจจัยที่หนึ่งของผู้ใช้คืออีเมลและรหัสผ่าน ให้ทำดังนี้
try { await _auth.signInWithEmailAndPassword( email: emailController.text, password: passwordController.text, ); // User is not enrolled with a second factor and is successfully // signed in. // ... } on FirebaseAuthMultiFactorException catch (e) { // The user is a multi-factor user. Second factor challenge is required final resolver = e.resolver // ... }
หากผู้ใช้ลงทะเบียนปัจจัยรองไว้หลายรายการ ให้ถามผู้ใช้ว่าจะใช้ปัจจัยใด
final session = e.resolver.session; final hint = e.resolver.hints[selectedHint];
ส่งข้อความยืนยันไปยังโทรศัพท์ของผู้ใช้พร้อมคำแนะนำและเซสชันการตรวจสอบแบบหลายปัจจัย โดยทำดังนี้
await FirebaseAuth.instance.verifyPhoneNumber( multiFactorSession: session, multiFactorInfo: hint, verificationCompleted: (_) {}, verificationFailed: (_) {}, codeSent: (String verificationId, int? resendToken) async { // ... }, codeAutoRetrievalTimeout: (_) {}, );
โทรหา
resolver.resolveSignIn()
เพื่อดำเนินการตรวจสอบสิทธิ์รองให้เสร็จสมบูรณ์final smsCode = await getSmsCodeFromUser(context); if (smsCode != null) { // Create a PhoneAuthCredential with the code final credential = PhoneAuthProvider.credential( verificationId: verificationId, smsCode: smsCode, ); try { await e.resolver.resolveSignIn( PhoneMultiFactorGenerator.getAssertion(credential) ); } on FirebaseAuthException catch (e) { print(e.message); } }
โค้ดด้านล่างแสดงตัวอย่างการลงชื่อเข้าใช้ผู้ใช้แบบหลายปัจจัยที่สมบูรณ์
try {
await _auth.signInWithEmailAndPassword(
email: emailController.text,
password: passwordController.text,
);
} on FirebaseAuthMultiFactorException catch (e) {
setState(() {
error = '${e.message}';
});
final firstHint = e.resolver.hints.first;
if (firstHint is! PhoneMultiFactorInfo) {
return;
}
await FirebaseAuth.instance.verifyPhoneNumber(
multiFactorSession: e.resolver.session,
multiFactorInfo: firstHint,
verificationCompleted: (_) {},
verificationFailed: (_) {},
codeSent: (String verificationId, int? resendToken) async {
// See `firebase_auth` example app for a method of retrieving user's sms code:
// https://github.com/firebase/flutterfire/blob/main/packages/firebase_auth/firebase_auth/example/lib/auth.dart#L591
final smsCode = await getSmsCodeFromUser(context);
if (smsCode != null) {
// Create a PhoneAuthCredential with the code
final credential = PhoneAuthProvider.credential(
verificationId: verificationId,
smsCode: smsCode,
);
try {
await e.resolver.resolveSignIn(
PhoneMultiFactorGenerator.getAssertion(
credential,
),
);
} on FirebaseAuthException catch (e) {
print(e.message);
}
}
},
codeAutoRetrievalTimeout: (_) {},
);
} catch (e) {
...
}
ยินดีด้วย คุณลงชื่อเข้าใช้ผู้ใช้โดยใช้การตรวจสอบสิทธิ์แบบหลายปัจจัยเรียบร้อยแล้ว
ขั้นตอนถัดไป
- จัดการผู้ใช้ที่ต้องใช้การตรวจสอบสิทธิ์แบบหลายปัจจัยแบบเป็นโปรแกรมด้วย Admin SDK