المصادقة مع Firebase من خلال رقم هاتف باستخدام JavaScript

يمكنك استخدام مصادقة Firebase لتسجيل دخول المستخدم عن طريق إرسال رسالة قصيرة SMS إلى هاتفه. يسجّل المستخدم الدخول باستخدام رمز يُستخدم لمرة واحدة مضمَّن في رسالة SMS.

إن أسهل طريقة لإضافة تسجيل الدخول إلى رقم الهاتف إلى تطبيقك هي استخدام FirebaseUI، التي تتضمّن أداة تسجيل دخول للدخول تنفّذ عمليات تسجيل الدخول لتسجيل الدخول باستخدام رقم الهاتف، بالإضافة إلى تسجيل الدخول المستند إلى كلمة المرور والموحّد. ويوضّح هذا المستند كيفية تنفيذ عملية تسجيل الدخول إلى رقم الهاتف باستخدام حزمة تطوير البرامج (SDK) لمنصة Firebase.

قبل البدء

انسخ مقتطف الإعداد من وحدة تحكّم Firebase إلى مشروعك كما هو موضّح في إضافة Firebase إلى مشروع JavaScript، إذا لم يسبق لك إجراء ذلك.

المخاوف المرتبطة بالأمان

تُعدّ المصادقة باستخدام رقم هاتف فقط أقل أمانًا من الطرق الأخرى المتاحة، إذ يمكن نقل ملكية رقم الهاتف بسهولة بين المستخدمين. أيضًا، على الأجهزة التي تحتوي على ملفات شخصية متعددة للمستخدمين، يمكن لأي مستخدم يتلقى رسائل SMS تسجيل الدخول إلى حساب باستخدام رقم هاتف الجهاز.

إذا كنت تستخدم تسجيل الدخول من خلال رقم هاتف في تطبيقك، عليك تقديمه إلى جانب طرق تسجيل دخول أكثر أمانًا، وإبلاغ المستخدمين بالمفاضلات الأمنية الناتجة عن استخدام تسجيل الدخول باستخدام رقم الهاتف.

تفعيل تسجيل الدخول إلى رقم الهاتف لمشروعك على Firebase

لتسجيل دخول المستخدمين عبر الرسائل القصيرة SMS، يجب أولاً تفعيل طريقة تسجيل الدخول باستخدام رقم الهاتف لمشروع Firebase:

  1. في وحدة تحكُّم Firebase، افتح قسم المصادقة.
  2. في صفحة طريقة تسجيل الدخول، فعِّل طريقة تسجيل الدخول رقم الهاتف.
  3. في الصفحة نفسها، إذا لم يكن النطاق الذي سيستضيف تطبيقك مُدرجًا في قسم نطاقات إعادة توجيه OAuth، أضِف نطاقك. لاحظ أنه غير مسموح للمضيف المحلي كنطاق مستضاف لأغراض المصادقة على الهاتف.

حصة طلب تسجيل الدخول إلى رقم الهاتف في Firebase عالية بما يكفي لعدم تأثر معظم التطبيقات. ومع ذلك، إذا كنت بحاجة إلى تسجيل دخول عدد كبير جدًا من المستخدمين باستخدام مصادقة الهاتف، قد تحتاج إلى ترقية خطة الأسعار. اطّلِع على صفحة الأسعار.

إعداد أداة التحقّق من خدمة reCAPTCHA

قبل أن تتمكّن من تسجيل دخول المستخدمين باستخدام أرقام هواتفهم، عليك إعداد أداة التحقّق من reCAPTCHA من Firebase. يستخدم Firebase خدمة reCAPTCHA لمنع إساءة الاستخدام، مثلاً من خلال ضمان أنّ طلب التحقق من رقم الهاتف صادر من أحد النطاقات المسموح بها في تطبيقك.

لا حاجة إلى إعداد عميل reCAPTCHA يدويًا، فعند استخدام عنصر RecaptchaVerifier في حزمة تطوير البرامج (SDK) لمنصة Firebase، ينشئ Firebase ويعالج تلقائيًا أي مفاتيح وأسرار عميل ضرورية.

يتوافق الكائن RecaptchaVerifier مع اختبار reCAPTCHA غير المرئي الذي يمكنه غالبًا التحقّق من المستخدم بدون الحاجة إلى اتخاذ أي إجراء من المستخدم، بالإضافة إلى أداة reCAPTCHA التي تتطلب دائمًا تفاعل المستخدم لإكمال العملية بنجاح.

يمكن ترجمة reCAPTCHA المعروض الأساسي حسب ما يفضّله المستخدم، وذلك من خلال تعديل رمز اللغة على مثيل Auth قبل عرض reCAPTCHA. سينطبق الأقلمة المذكور آنفًا أيضًا على رسالة SMS المُرسَلة إلى المستخدم، والتي تتضمَّن رمز التحقق.

Web

import { getAuth } from "firebase/auth";

const auth = getAuth();
auth.languageCode = 'it';
// To apply the default browser preference instead of explicitly setting it.
// auth.useDeviceLanguage();

Web

firebase.auth().languageCode = 'it';
// To apply the default browser preference instead of explicitly setting it.
// firebase.auth().useDeviceLanguage();

استخدام reCAPTCHA غير المرئية

لاستخدام reCAPTCHA غير مرئية، أنشِئ عنصر RecaptchaVerifier مع ضبط المعلَمة size على invisible، مع تحديد معرّف الزر الذي يُرسل نموذج تسجيل الدخول. على سبيل المثال:

Web

import { getAuth, RecaptchaVerifier } from "firebase/auth";

const auth = getAuth();
window.recaptchaVerifier = new RecaptchaVerifier(auth, 'sign-in-button', {
  'size': 'invisible',
  'callback': (response) => {
    // reCAPTCHA solved, allow signInWithPhoneNumber.
    onSignInSubmit();
  }
});

Web

window.recaptchaVerifier = new firebase.auth.RecaptchaVerifier('sign-in-button', {
  'size': 'invisible',
  'callback': (response) => {
    // reCAPTCHA solved, allow signInWithPhoneNumber.
    onSignInSubmit();
  }
});

استخدام تطبيق reCAPTCHA المصغّر

لاستخدام تطبيق reCAPTCHA المرئي، أنشِئ عنصرًا على صفحتك يحتوي على التطبيق المصغّر، ثم أنشِئ عنصر RecaptchaVerifier مع تحديد رقم تعريف الحاوية عند إجراء ذلك. على سبيل المثال:

Web

import { getAuth, RecaptchaVerifier } from "firebase/auth";

const auth = getAuth();
window.recaptchaVerifier = new RecaptchaVerifier(auth, 'recaptcha-container', {});

Web

window.recaptchaVerifier = new firebase.auth.RecaptchaVerifier('recaptcha-container');

اختياري: تحديد مَعلمات reCAPTCHA

يمكنك اختياريًا ضبط وظائف معاودة الاتصال على عنصر RecaptchaVerifier الذي يتم استدعاءه عندما يحل المستخدم اختبار ReCAPTCHA أو عند انتهاء صلاحية reCAPTCHA قبل أن يرسل المستخدم النموذج:

Web

import { getAuth, RecaptchaVerifier } from "firebase/auth";

const auth = getAuth();
window.recaptchaVerifier = new RecaptchaVerifier(auth, 'recaptcha-container', {
  'size': 'normal',
  'callback': (response) => {
    // reCAPTCHA solved, allow signInWithPhoneNumber.
    // ...
  },
  'expired-callback': () => {
    // Response expired. Ask user to solve reCAPTCHA again.
    // ...
  }
});

Web

window.recaptchaVerifier = new firebase.auth.RecaptchaVerifier('recaptcha-container', {
  'size': 'normal',
  'callback': (response) => {
    // reCAPTCHA solved, allow signInWithPhoneNumber.
    // ...
  },
  'expired-callback': () => {
    // Response expired. Ask user to solve reCAPTCHA again.
    // ...
  }
});

اختياري: عرض reCAPTCHA مسبقًا

إذا أردت عرض reCAPTCHA مسبقًا قبل إرسال طلب تسجيل الدخول، عليك التواصل مع render باتّباع الخطوات التالية:

Web

recaptchaVerifier.render().then((widgetId) => {
  window.recaptchaWidgetId = widgetId;
});

Web

recaptchaVerifier.render().then((widgetId) => {
  window.recaptchaWidgetId = widgetId;
});

بعد حلّ render، ستحصل على رقم تعريف أداة reCAPTCHA الذي يمكنك استخدامه لإجراء مكالمات مع واجهة برمجة التطبيقات reCAPTCHA:

Web

const recaptchaResponse = grecaptcha.getResponse(recaptchaWidgetId);

Web

const recaptchaResponse = grecaptcha.getResponse(recaptchaWidgetId);

إرسال رمز تحقُّق إلى هاتف المستخدم

لبدء تسجيل الدخول إلى رقم الهاتف، يمكنك تقديم واجهة للمستخدم تطلب منه تقديم رقم هاتفه، ثم الاتصال بـ signInWithPhoneNumber لطلب من Firebase إرسال رمز مصادقة إلى هاتف المستخدم من خلال رسالة قصيرة SMS:

  1. احصل على رقم هاتف المستخدم.

    تختلف المتطلبات القانونية، ولكن وفقًا لأفضل الممارسات ولتحديد توقعات المستخدمين، عليك إبلاغهم بأنّهم قد يتلقّون رسالة SMS لإجراء عملية التحقّق، وسيتم تطبيق الأسعار العادية في حال استخدامهم تسجيل الدخول عبر الهاتف.

  2. يمكنك الاتصال بـ signInWithPhoneNumber، وإرسال رقم هاتف المستخدم ورقم RecaptchaVerifier الذي أنشأته سابقًا إليه.

    Web

    import { getAuth, signInWithPhoneNumber } from "firebase/auth";
    
    const phoneNumber = getPhoneNumberFromUserInput();
    const appVerifier = window.recaptchaVerifier;
    
    const auth = getAuth();
    signInWithPhoneNumber(auth, phoneNumber, appVerifier)
        .then((confirmationResult) => {
          // SMS sent. Prompt user to type the code from the message, then sign the
          // user in with confirmationResult.confirm(code).
          window.confirmationResult = confirmationResult;
          // ...
        }).catch((error) => {
          // Error; SMS not sent
          // ...
        });

    Web

    const phoneNumber = getPhoneNumberFromUserInput();
    const appVerifier = window.recaptchaVerifier;
    firebase.auth().signInWithPhoneNumber(phoneNumber, appVerifier)
        .then((confirmationResult) => {
          // SMS sent. Prompt user to type the code from the message, then sign the
          // user in with confirmationResult.confirm(code).
          window.confirmationResult = confirmationResult;
          // ...
        }).catch((error) => {
          // Error; SMS not sent
          // ...
        });
    إذا أدى خطأ في signInWithPhoneNumber إلى حدوث خطأ، يُرجى إعادة ضبط reCAPTCHA ليتمكّن المستخدم من إعادة المحاولة:
    grecaptcha.reset(window.recaptchaWidgetId);
    
    // Or, if you haven't stored the widget ID:
    window.recaptchaVerifier.render().then(function(widgetId) {
      grecaptcha.reset(widgetId);
    });
    

تُصدر طريقة signInWithPhoneNumber تحدي reCAPTCHA إلى المستخدم، وإذا اجتاز المستخدم التحدي، يطلب مصادقة Firebase إرسال رسالة SMS تحتوي على رمز التحقق إلى هاتف المستخدم.

سجِّل دخول المستخدم باستخدام رمز التحقّق.

بعد نجاح الاتصال إلى signInWithPhoneNumber، اطلب من المستخدم كتابة رمز التحقق الذي تلقّاه عبر رسالة SMS. بعد ذلك، سجِّل دخول المستخدم من خلال تمرير الرمز إلى طريقة confirm في العنصر ConfirmationResult الذي تم تمريره إلى معالج تنفيذ signInWithPhoneNumber (أي حظر then). على سبيل المثال:

Web

const code = getCodeFromUserInput();
confirmationResult.confirm(code).then((result) => {
  // User signed in successfully.
  const user = result.user;
  // ...
}).catch((error) => {
  // User couldn't sign in (bad verification code?)
  // ...
});

Web

const code = getCodeFromUserInput();
confirmationResult.confirm(code).then((result) => {
  // User signed in successfully.
  const user = result.user;
  // ...
}).catch((error) => {
  // User couldn't sign in (bad verification code?)
  // ...
});

إذا نجحت المكالمة إلى confirm، يتم تسجيل دخول المستخدم بنجاح.

الحصول على كائن AuthCredential المتوسط

إذا كنت تريد الحصول على عنصر AuthCredential لحساب المستخدم، أرسِل رمز التحقّق من نتيجة التأكيد ورمز التحقّق إلى PhoneAuthProvider.credential بدلاً من طلب الرقم confirm:

var credential = firebase.auth.PhoneAuthProvider.credential(confirmationResult.verificationId, code);

بعد ذلك، يمكنك تسجيل دخول المستخدم باستخدام بيانات الاعتماد:

firebase.auth().signInWithCredential(credential);

الاختبار باستخدام أرقام هواتف خيالية

يمكنك إعداد أرقام هواتف خيالية للتطوير من خلال "وحدة تحكُّم Firebase". يوفر الاختبار باستخدام أرقام هواتف خيالية هذه الفوائد:

  • اختبِر مصادقة رقم الهاتف بدون استهلاك حصة الاستخدام.
  • اختبار مصادقة رقم الهاتف بدون إرسال رسالة قصيرة SMS فعلية.
  • يمكنك إجراء اختبارات متتالية باستخدام رقم الهاتف نفسه بدون قيود. يحدّ ذلك من خطر الرفض أثناء عملية المراجعة على متجر التطبيقات إذا استخدم المراجع رقم الهاتف نفسه للاختبار.
  • يمكنك الاختبار بسهولة في بيئات التطوير بدون أي جهد إضافي، مثل إمكانية التطوير في محاكي لنظام التشغيل iOS أو محاكي Android بدون "خدمات Google Play".
  • يمكنك كتابة اختبارات الدمج بدون أن يتم حظرها من خلال عمليات فحص الأمان التي يتم تطبيقها عادةً على أرقام الهواتف الحقيقية في بيئة إنتاج.

يجب أن تستوفي أرقام الهواتف الخيالية المتطلبات التالية:

  1. تأكد من استخدام أرقام هواتف خيالية فعلاً، وغير موجودة بالفعل. لا تسمح لك مصادقة Firebase بتعيين أرقام الهواتف الحالية التي يستخدمها المستخدمون الحقيقيون كأرقام اختبار. أحد الخيارات المتاحة هو استخدام 555 رقمًا البادئة كأرقام هواتف تجريبية في الولايات المتحدة، مثلاً: +1 650-555-3434
  2. يجب تنسيق أرقام الهواتف بشكل صحيح وفقًا لطولها مع قيود أخرى. سيخضع لعملية التحقق نفسها التي يخضع لها رقم هاتف المستخدم الحقيقي.
  3. يمكنك إضافة ما يصل إلى 10 أرقام هواتف لتطويرها.
  4. استخدِم أرقام هواتف أو رموزًا تجريبية يصعُب تخمينها وغيّرها بشكلٍ متكرّر.

إنشاء أرقام هواتف ورموز تحقّق خيالية

  1. في وحدة تحكُّم Firebase، افتح قسم المصادقة.
  2. في علامة التبويب طريقة تسجيل الدخول، فعِّل مزوِّد خدمة الهاتف إذا لم يسبق لك تفعيله.
  3. افتح قائمة أكورديون أرقام الهواتف للاختبار.
  4. أدخِل رقم الهاتف الذي تريد اختباره، مثل +1 650-555-3434.
  5. أدخِل رمز التحقّق المكوّن من 6 أرقام لهذا الرقم تحديدًا، مثل 654321.
  6. أضِف الرقم. ويمكنك حذف رقم الهاتف ورمزه من خلال تمرير مؤشر الماوس فوق الصف المقابل والنقر على رمز المهملات، إذا كنت بحاجة إلى ذلك.

الاختبار اليدوي

يمكنك البدء مباشرةً في استخدام رقم هاتف خيالي في تطبيقك. ويتيح لك ذلك إجراء اختبار يدوي أثناء مراحل التطوير بدون التسبب في مشاكل في الحصة أو تقييدها. يمكنك أيضًا الاختبار مباشرةً من خلال محاكي iOS أو محاكي Android بدون تثبيت "خدمات Google Play".

عندما تقدم رقم هاتفًا خياليًا وترسل رمز التحقق، لا يتم إرسال أي رسالة قصيرة SMS فعلية. بدلاً من ذلك، عليك تقديم رمز التحقق الذي تم إعداده مسبقًا لإكمال عملية تسجيل الدخول.

عند اكتمال عملية تسجيل الدخول، يتم إنشاء مستخدم Firebase برقم الهاتف هذا. ويكون للمستخدم سلوك وخصائص مماثلة كما هو الحال لدى مستخدم رقم هاتف حقيقي، ويمكنه الوصول إلى قاعدة بيانات الوقت الفعلي/Cloud Firestore والخدمات الأخرى بالطريقة نفسها. ويكون للرمز المميّز لرقم التعريف الذي تم استخراجه خلال هذه العملية التوقيع نفسه المُستخدَم مع مستخدم رقم هاتف حقيقي.

ويمكنك أيضًا تحديد دور اختباري من خلال مطالبات مخصّصة لهؤلاء المستخدمين بهدف التفريق بينهم كمستخدمين مزيّفين إذا أردت فرض قيود إضافية على إمكانية الوصول.

اختبار الدمج

بالإضافة إلى الاختبار اليدوي، توفر مصادقة Firebase واجهات برمجة تطبيقات للمساعدة في كتابة اختبارات الدمج لاختبار المصادقة على الهاتف. وتؤدي واجهات برمجة التطبيقات هذه إلى إيقاف التحقق من التطبيقات عن طريق إيقاف شرط reCAPTCHA في الويب والإشعارات الفورية الصامتة لنظام التشغيل iOS. وهذا يجعل اختبار الأتمتة ممكنًا في هذه التدفقات ويسهل تنفيذه. بالإضافة إلى ذلك، تساعد في توفير القدرة على اختبار تدفقات التحقق الفوري على Android.

على الويب، اضبط السمة appVerificationDisabledForTesting على true قبل عرض firebase.auth.RecaptchaVerifier. يؤدي ذلك إلى حل reCAPTCHA تلقائيًا، ما يتيح لك تمرير رقم الهاتف بدون حله يدويًا. يُرجى العِلم أنّه على الرغم من إيقاف خدمة reCAPTCHA، سيؤدي استخدام رقم هاتف غير خيالي إلى عدم إكمال عملية تسجيل الدخول. يمكن استخدام أرقام هواتف خيالية فقط مع واجهة برمجة التطبيقات هذه.

// Turn off phone auth app verification.
firebase.auth().settings.appVerificationDisabledForTesting = true;

var phoneNumber = "+16505554567";
var testVerificationCode = "123456";

// This will render a fake reCAPTCHA as appVerificationDisabledForTesting is true.
// This will resolve after rendering without app verification.
var appVerifier = new firebase.auth.RecaptchaVerifier('recaptcha-container');
// signInWithPhoneNumber will call appVerifier.verify() which will resolve with a fake
// reCAPTCHA response.
firebase.auth().signInWithPhoneNumber(phoneNumber, appVerifier)
    .then(function (confirmationResult) {
      // confirmationResult can resolve with the fictional testVerificationCode above.
      return confirmationResult.confirm(testVerificationCode)
    }).catch(function (error) {
      // Error; SMS not sent
      // ...
    });

تختلف سلوك أدوات التحقق من تطبيقات reCAPTCHA المرئية وغير المرئية عند إيقاف التحقق من التطبيقات:

  • خدمة reCAPTCHA المرئية: عند عرض reCAPTCHA المرئية عبر appVerifier.render()، يتم حل المشكلة تلقائيًا بعد جزء من التأخير الثاني. يعادل ذلك عندما ينقر المستخدم على reCAPTCHA فور العرض. ستنتهي صلاحية استجابة reCAPTCHA بعد مرور بعض الوقت، وسيتم حلها تلقائيًا مرة أخرى.
  • خدمة reCAPTCHA غير المرئية: لا يتم حل رمز reCAPTCHA غير المرئي تلقائيًا عند العرض، بل يتم حله تلقائيًا عند الطلب appVerifier.verify()أو عند النقر على علامة ارتساء زر reCAPTCHA بعد بضع ثوانٍ. وبالمثل، ستنتهي صلاحية الردّ بعد مرور بعض الوقت وسيتم حله تلقائيًا فقط إما بعد طلب appVerifier.verify() أو عند النقر على علامة ارتساء خدمة reCAPTCHA مرة أخرى.

عندما يتم التعامل بشكل نهائي مع reCAPTCHA، يتم تفعيل وظيفة معاودة الاتصال المقابلة على النحو المتوقّع مع الردّ الزائف. إذا تم أيضًا تحديد طلب معاودة الاتصال لانتهاء الصلاحية، سيتم إجراء ذلك عند انتهاء الصلاحية.

الخطوات اللاحقة

بعد تسجيل دخول المستخدم للمرة الأولى، يتم إنشاء حساب مستخدم جديد وربطه ببيانات الاعتماد - أي اسم المستخدم وكلمة المرور أو رقم الهاتف أو معلومات موفّر المصادقة - المستخدم الذي سجّل الدخول من خلاله. يتم تخزين هذا الحساب الجديد كجزء من مشروع Firebase، ويمكن استخدامه لتحديد هوية مستخدم عبر كل تطبيق في مشروعك، بغض النظر عن الطريقة التي يسجّل بها هذا المستخدم دخوله.

  • إنّ الطريقة التي يُنصح بها في تطبيقاتك لمعرفة حالة المصادقة للمستخدم هي ضبط مراقب على الكائن Auth. يمكنك بعد ذلك الحصول على معلومات الملف الشخصي الأساسية للمستخدم من الكائن User. يمكنك الاطّلاع على إدارة المستخدمين.

  • في قاعدة بيانات Firebase في الوقت الفعلي وقواعد الأمان في Cloud Storage، يمكنك الحصول على رقم تعريف المستخدم الفريد للمستخدم الذي سجّل الدخول من خلال المتغيّر auth، واستخدامه للتحكّم في البيانات التي يمكن للمستخدم الوصول إليها.

يمكنك السماح للمستخدمين بتسجيل الدخول إلى تطبيقك باستخدام مزوّدي مصادقة متعددين من خلال ربط بيانات اعتماد موفّر المصادقة بحساب مستخدم حالي.

لتسجيل خروج المستخدم، يمكنك الاتصال على signOut:

Web

import { getAuth, signOut } from "firebase/auth";

const auth = getAuth();
signOut(auth).then(() => {
  // Sign-out successful.
}).catch((error) => {
  // An error happened.
});

Web

firebase.auth().signOut().then(() => {
  // Sign-out successful.
}).catch((error) => {
  // An error happened.
});