إثبات ملكية الرموز المميّزة للهوية

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

قبل البدء

لإثبات صحة رموز التعريف باستخدام حزمة تطوير البرامج (SDK) الخاصة بمشرفي Firebase، يجب أن يكون لديك حساب خدمة. اتّبِع تعليمات إعداد حزمة SDK للمشرف للحصول على مزيد من المعلومات حول كيفية إعداد حزمة SDK للمشرف باستخدام حساب خدمة.

استرداد رموز التعريف على الأجهزة

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

iOS+‎

Objective-C
FIRUser *currentUser = [FIRAuth auth].currentUser;
[currentUser getIDTokenForcingRefresh:YES
                           completion:^(NSString *_Nullable idToken,
                                        NSError *_Nullable error) {
          if (error) {
            // Handle error
            return;
          }

          // Send token to your backend via HTTPS
          // ...
}];
Swift
let currentUser = FIRAuth.auth()?.currentUser
currentUser?.getIDTokenForcingRefresh(true) { idToken, error in
  if let error = error {
    // Handle error
    return;
  }

  // Send token to your backend via HTTPS
  // ...
}

Android

FirebaseUser mUser = FirebaseAuth.getInstance().getCurrentUser();
mUser.getIdToken(true)
    .addOnCompleteListener(new OnCompleteListener<GetTokenResult>() {
        public void onComplete(@NonNull Task<GetTokenResult> task) {
            if (task.isSuccessful()) {
                String idToken = task.getResult().getToken();
                // Send token to your backend via HTTPS
                // ...
            } else {
                // Handle error -> task.getException();
            }
        }
    });

Unity

Firebase.Auth.FirebaseUser user = auth.CurrentUser;
user.TokenAsync(true).ContinueWith(task => {
  if (task.IsCanceled) {
    Debug.LogError("TokenAsync was canceled.");
   return;
  }

  if (task.IsFaulted) {
    Debug.LogError("TokenAsync encountered an error: " + task.Exception);
    return;
  }

  string idToken = task.Result;

  // Send token to your backend via HTTPS
  // ...
});

C++‎

firebase::auth::User user = auth->current_user();
if (user.is_valid()) {
  firebase::Future<std::string> idToken = user.GetToken(true);

  // Send token to your backend via HTTPS
  // ...
}

الويب

firebase.auth().currentUser.getIdToken(/* forceRefresh */ true).then(function(idToken) {
  // Send token to your backend via HTTPS
  // ...
}).catch(function(error) {
  // Handle error
});

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

التحقّق من صحة رموز التعريف باستخدام حزمة تطوير البرامج (SDK) الخاصة بمدير Firebase

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

اتّبِع تعليمات إعداد حزمة تطوير البرامج (SDK) للمشرف لتهيئة حزمة تطوير البرامج (SDK) للمشرف باستخدام حساب خدمة. بعد ذلك، استخدِم طريقة verifyIdToken() لإثبات صحة رمز تعريف:

Node.js

// idToken comes from the client app
getAuth()
  .verifyIdToken(idToken)
  .then((decodedToken) => {
    const uid = decodedToken.uid;
    // ...
  })
  .catch((error) => {
    // Handle error
  });

Java

// idToken comes from the client app (shown above)
FirebaseToken decodedToken = FirebaseAuth.getInstance().verifyIdToken(idToken);
String uid = decodedToken.getUid();

Python

# id_token comes from the client app (shown above)

decoded_token = auth.verify_id_token(id_token)
uid = decoded_token['uid']

Go

client, err := app.Auth(ctx)
if err != nil {
	log.Fatalf("error getting Auth client: %v\n", err)
}

token, err := client.VerifyIDToken(ctx, idToken)
if err != nil {
	log.Fatalf("error verifying ID token: %v\n", err)
}

log.Printf("Verified ID token: %v\n", token)

#C

FirebaseToken decodedToken = await FirebaseAuth.DefaultInstance
    .VerifyIdTokenAsync(idToken);
string uid = decodedToken.Uid;

يتطلّب إثبات صحة الرمز المميّز لمعرّف المستخدم رقم تعريف مشروع. تحاول حزمة تطوير البرامج (SDK) الخاصة بمسؤول Firebase الحصول على رقم تعريف المشروع بإحدى الطرق التالية:

  • إذا تمّت تهيئة حزمة SDK باستخدام خيار تطبيق projectId صريح، تستخدم حزمة SDK قيمة هذا الخيار.
  • إذا تمّت تهيئة حزمة تطوير البرامج (SDK) باستخدام بيانات اعتماد حساب الخدمة، ستستخدم حزمة تطوير البرامج (SDK) الحقل project_id لكائن JSON الخاص بحساب الخدمة.
  • في حال ضبط متغيّر البيئة GOOGLE_CLOUD_PROJECT، تستخدِم حزمة SDK قيمته كرقم تعريف المشروع. متغيّر البيئة هذا متاح للرمز الذي يتم تشغيله على بنية Google التحتية، مثل App Engine وCompute Engine.

التحقّق من صحة رموز التعريف باستخدام مكتبة JWT تابعة لجهة خارجية

إذا كانت الخلفية بلغة غير متوافقة مع حزمة تطوير البرامج (SDK) الخاصة بخدمة Firebase Admin، سيظل بإمكانك إثبات صحة رموز التعريف. أولاً، ابحث عن مكتبة JWT تابعة لجهة خارجية للغتك. بعد ذلك، تحقَّق من العنوان والحمولة والتوقيع الخاصين برمز التعريف المميز.

تأكَّد من أنّ عنوان رمز التعريف المميز يتوافق مع القيود التالية:

مطالبات عنوان رمز التعريف
alg خوارزمية "RS256"
kid معرّف المفتاح يجب أن يتوافق مع أحد المفاتيح العامة المدرَجة في https://www.googleapis.com/robot/v1/metadata/x509/securetoken@system.gserviceaccount.com

تأكَّد من أنّ حمولة رمز التعريف المميز تتوافق مع القيود التالية:

مطالبات حمولة الرمز المميز لبطاقة التعريف
exp وقت انتهاء الصلاحية يجب أن يكون في المستقبل. ويتم قياس الوقت بالثواني منذ بدء حساب الفترة في نظام التشغيل UNIX.
iat وقت الإصدار يجب أن يكون التاريخ في الماضي. ويتم قياس الوقت بالثواني منذ بدء حساب الفترة في نظام التشغيل UNIX.
aud الجمهور يجب أن يكون رقم تعريف مشروعك على Firebase، وهو المعرّف الفريد لمشروعك على Firebase، ويمكن العثور عليه في عنوان URL الخاص بوحدة تحكّم هذا المشروع.
iss جهة الإصدار يجب أن تكون القيمة "https://securetoken.google.com/<projectId>"، حيث <projectId> هو رقم تعريف المشروع نفسه المستخدَم في aud أعلاه.
sub الموضوع يجب أن تكون سلسلة غير فارغة وأن تكون uid المستخدم أو الجهاز.
auth_time وقت المصادقة يجب أن يكون التاريخ في الماضي. الوقت الذي تمت فيه مصادقة المستخدم

أخيرًا، تأكَّد من أنّ المفتاح الخاص الذي تم استخدامه لتوقيع رمز التعريف يتطابق مع قيمة المطالبة kid في الرمز المميز. احصل على المفتاح العام من https://www.googleapis.com/robot/v1/metadata/x509/securetoken@system.gserviceaccount.com واستخدِم مكتبة JWT للتحقّق من التوقيع. استخدِم قيمة max-age في عنوان Cache-Control للردّ من نقطة النهاية هذه لمعرفة الوقت المناسب لإعادة تحميل المفاتيح العامة.

في حال نجاح جميع عمليات التحقّق المذكورة أعلاه، يمكنك استخدام موضوع (sub) رمز التعريف المميز كـ uid للمستخدم أو الجهاز المعنيّ.