احراز هویت چند عاملی را به برنامه Flutter خود اضافه کنید

اگر به Firebase Authentication با Identity Platform ارتقا داده اید، می توانید احراز هویت چند عاملی SMS را به برنامه Flutter خود اضافه کنید.

احراز هویت چند عاملی (MFA) امنیت برنامه شما را افزایش می دهد. در حالی که مهاجمان اغلب رمزهای عبور و حساب های اجتماعی را به خطر می اندازند، رهگیری یک پیام متنی دشوارتر است.

قبل از اینکه شروع کنی

  1. حداقل یک ارائه دهنده را فعال کنید که از احراز هویت چند مرحله ای پشتیبانی می کند. هر ارائه‌دهنده‌ای از MFA پشتیبانی می‌کند، به‌جز احراز هویت تلفن، احراز هویت ناشناس و Apple Game Center.

  2. مطمئن شوید که برنامه شما ایمیل های کاربر را تأیید می کند. وزارت امور خارجه به تأیید ایمیل نیاز دارد. این امر مانع از ثبت نام عوامل مخرب در سرویسی با ایمیلی می شود که متعلق به آنها نیست و سپس با افزودن عامل دوم، مالک واقعی را قفل می کند.

  3. Android : اگر قبلاً هش SHA-256 برنامه خود را در کنسول Firebase تنظیم نکرده اید، این کار را انجام دهید. برای اطلاعات در مورد یافتن هش SHA-256 برنامه خود به تأیید اعتبار مشتری خود مراجعه کنید.

  4. iOS : در Xcode، اعلان‌های فشاری را برای پروژه خود فعال کنید و مطمئن شوید که کلید احراز هویت APN‌ها با Firebase Cloud Messaging (FCM) پیکربندی شده است. علاوه بر این، باید حالت‌های پس‌زمینه را برای اعلان‌های راه دور فعال کنید . برای مشاهده توضیح عمیق این مرحله، مستندات Firebase iOS Phone Auth را مشاهده کنید.

  5. وب : اطمینان حاصل کنید که دامنه برنامه های خود را در کنسول Firebase ، تحت دامنه های تغییر مسیر OAuth اضافه کرده اید.

فعال کردن احراز هویت چند عاملی

  1. صفحه Authentication > Sign-in را در کنسول Firebase باز کنید.

  2. در بخش Advanced ، SMS Multi-factor Authentication را فعال کنید.

    همچنین باید شماره تلفن هایی را که برنامه خود را با آنها آزمایش می کنید وارد کنید. در حالی که اختیاری است، ثبت شماره تلفن های آزمایشی قویاً توصیه می شود تا در حین توسعه ایجاد فشار نشود.

  3. اگر قبلاً دامنه برنامه خود را تأیید نکرده‌اید، آن را به فهرست مجاز در صفحه تأیید هویت > تنظیمات کنسول Firebase اضافه کنید.

انتخاب الگوی ثبت نام

می‌توانید انتخاب کنید که آیا برنامه شما به احراز هویت چند مرحله‌ای نیاز دارد یا خیر، و چگونه و چه زمانی کاربران خود را ثبت‌نام کند. برخی از الگوهای رایج عبارتند از:

  • فاکتور دوم کاربر را به عنوان بخشی از ثبت نام ثبت کنید. اگر برنامه شما نیاز به احراز هویت چند عاملی برای همه کاربران دارد، از این روش استفاده کنید.

  • برای ثبت فاکتور دوم در حین ثبت نام، یک گزینه قابل پرش ارائه دهید. برنامه‌هایی که می‌خواهند احراز هویت چند عاملی را تشویق کنند، اما نیازی به احراز هویت ندارند، ممکن است این رویکرد را ترجیح دهند.

  • به جای صفحه ثبت نام، امکان اضافه کردن فاکتور دوم را از صفحه مدیریت حساب کاربری یا نمایه کاربر فراهم کنید. این امر اصطکاک را در طول فرآیند ثبت نام به حداقل می رساند، در حالی که هنوز احراز هویت چند عاملی را برای کاربران حساس به امنیت در دسترس قرار می دهد.

  • هنگامی که کاربر می‌خواهد به ویژگی‌هایی با الزامات امنیتی افزایش یافته دسترسی پیدا کند، باید فاکتور دوم را به صورت تدریجی اضافه کنید.

ثبت عامل دوم

برای ثبت یک عامل ثانویه جدید برای یک کاربر:

  1. احراز هویت مجدد کاربر

  2. از کاربر بخواهید شماره تلفن خود را وارد کند.

  3. یک جلسه چند عاملی برای کاربر دریافت کنید:

    final multiFactorSession = await user.multiFactor.getSession();
    
  4. شماره تلفن را با یک جلسه چند عاملی و تماس های خود تأیید کنید:

    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: (_) {},
    ); 
    
  5. پس از ارسال کد پیامک، از کاربر بخواهید که کد را تأیید کند:

    final credential = PhoneAuthProvider.credential(
      verificationId: verificationId,
      smsCode: smsCode,
    );
    
  6. تکمیل ثبت نام:

    await user.multiFactor.enroll(
      PhoneMultiFactorGenerator.getAssertion(
        credential,
      ),
    );
    

کد زیر یک مثال کامل از ثبت فاکتور دوم را نشان می دهد:

  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/master/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: (_) {},
  );

تبریک می گویم! شما با موفقیت دومین فاکتور احراز هویت را برای یک کاربر ثبت کردید.

ورود کاربران با فاکتور دوم

برای ورود به یک کاربر با تأیید پیامک دو مرحله ای:

  1. کاربر را با اولین فاکتور خود وارد کنید، سپس استثنا FirebaseAuthMultiFactorException را بگیرید. این خطا حاوی یک حل کننده است که می توانید از آن برای به دست آوردن فاکتورهای دوم ثبت شده کاربر استفاده کنید. همچنین شامل یک جلسه اساسی است که ثابت می کند کاربر با موفقیت با اولین عامل خود احراز هویت شده است.

    به عنوان مثال، اگر اولین عامل کاربر ایمیل و رمز عبور باشد:

    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
      // ...
    }
    
  2. اگر کاربر چندین عامل ثانویه را ثبت کرده است، از آنها بپرسید که از کدام یک استفاده کند:

    final session = e.resolver.session;
    
    final hint = e.resolver.hints[selectedHint];
    
  3. با اشاره و جلسه چند عاملی یک پیام تأیید به تلفن کاربر ارسال کنید:

    await FirebaseAuth.instance.verifyPhoneNumber(
      multiFactorSession: session,
      multiFactorInfo: hint,
      verificationCompleted: (_) {},
      verificationFailed: (_) {},
      codeSent: (String verificationId, int? resendToken) async {
        // ...
      },
      codeAutoRetrievalTimeout: (_) {},
    );
    
  4. برای تکمیل احراز هویت ثانویه 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/master/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) {
  ...
} 

تبریک می گویم! شما با موفقیت با استفاده از احراز هویت چند عاملی وارد حساب کاربری شده اید.

بعدش چی