إنّ مشغّل https.onCall في Cloud Functions هو مشغّل HTTPS بتنسيق محدّد للطلب والاستجابة. يقدّم هذا القسم مواصفات لتنسيقات طلبات HTTPS واستجاباتها التي تستخدمها حِزم SDK للعميل لتنفيذ واجهة برمجة التطبيقات. قد تكون هذه المعلومات مفيدة إذا لم يكن بالإمكان تلبية متطلباتك باستخدام حِزم SDK على Android أو منصات Apple أو الويب.
تنسيق الطلب: العناوين
يجب أن يكون طلب HTTP إلى نقطة نهاية مشغّل قابل للاستدعاء POST مع العناوين التالية:
- مطلوب:
Content-Type: application/json- يُسمح باستخدام
; charset=utf-8الاختياري.
- يُسمح باستخدام
- اختياري:
Authorization: Bearer <token>- رمز تعريف مستخدم Firebase Authentication للمستخدم الذي سجّل الدخول وأرسل الطلب. يتحقّق النظام الخلفي تلقائيًا من هذا الرمز ويجعله متاحًا في
contextالمعالج. إذا لم يكن الرمز صالحًا، يتم رفض الطلب.
- رمز تعريف مستخدم Firebase Authentication للمستخدم الذي سجّل الدخول وأرسل الطلب. يتحقّق النظام الخلفي تلقائيًا من هذا الرمز ويجعله متاحًا في
- اختياري:
Firebase-Instance-ID-Token: <iid>- رمز التسجيل في "المراسلة عبر السحابة الإلكترونية من Firebase" من حزمة Firebase Client SDK. يجب أن يكون هذا الرمز سلسلة. وهو متاح في
contextالمعالج. ويُستخدم لاستهداف الإشعارات الفورية.
- رمز التسجيل في "المراسلة عبر السحابة الإلكترونية من Firebase" من حزمة Firebase Client SDK. يجب أن يكون هذا الرمز سلسلة. وهو متاح في
- اختياري:
X-Firebase-AppCheck: <token>- رمز ميزة "فحص التطبيقات من Firebase" الذي يقدّمه تطبيق العميل الذي يرسل الطلب. يتحقّق النظام الخلفي تلقائيًا من هذا الرمز ويفك ترميزه، ويُدرِج
appIdفيcontextالمعالج. إذا تعذّر التحقّق من الرمز، يتم رفض الطلب. (متاح لإصدار حزمة SDK >=3.14.0)
- رمز ميزة "فحص التطبيقات من Firebase" الذي يقدّمه تطبيق العميل الذي يرسل الطلب. يتحقّق النظام الخلفي تلقائيًا من هذا الرمز ويفك ترميزه، ويُدرِج
إذا تم تضمين أي عناوين أخرى، يتم رفض الطلب، كما هو موضّح في مستندات الاستجابة أدناه.
ملاحظة: في عملاء JavaScript، تؤدي هذه الطلبات إلى تشغيل عملية فحص مسبق لطلبات OPTIONS في CORS، للأسباب التالية:
- لا يُسمح باستخدام
application/json. يجب أن يكونtext/plainأوapplication/x-www-form-urlencoded. - عنوان
Authorizationليس عنوان طلب مدرَجًا في القائمة الآمنة لطلبات CORS. - وبالمثل، لا يُسمح باستخدام العناوين الأخرى.
يتعامل المشغّل القابل للاستدعاء تلقائيًا مع طلبات OPTIONS هذه.
نص الطلب
يجب أن يكون نص طلب HTTP كائن JSON يتضمّن أيًا من الحقول التالية:
- مطلوب:
data- الوسيطة التي تم تمريرها إلى الدالة. يمكن أن تكون هذه القيمة أي قيمة JSON صالحة. يتم فك ترميزها تلقائيًا إلى أنواع JavaScript الأصلية وفقًا لتنسيق التسلسل الموضّح أدناه.
إذا كانت هناك أي حقول أخرى في الطلب، يعتبر النظام الخلفي أنّ الطلب غير صالح ويتم رفضه.
تنسيق الاستجابة: رموز الحالة
هناك عدة حالات قد تؤدي إلى رموز حالة HTTP مختلفة و رموز حالة سلسلة لـ الأخطاء في الاستجابة.
في حال حدوث خطأ HTTP قبل استدعاء مشغّل
client، لا يتم التعامل مع الاستجابة كدالة عميل. على سبيل المثال، إذا حاول أحد العملاء استدعاء دالة غير موجودة، سيتلقّى استجابة404 Not Found.إذا تم استدعاء مشغّل العميل، ولكن كان الطلب بتنسيق غير صحيح، مثل عدم كونه JSON أو احتوائه على حقول غير صالحة أو عدم تضمينه حقل
data، يتم رفض الطلب مع عرض400 Bad Requestورمز الخطأINVALID_ARGUMENT.إذا كان رمز المصادقة المقدَّم في الطلب غير صالح، يتم رفض الطلب مع عرض
401 Unauthorizedورمز الخطأUNAUTHENTICATED.إذا كان رمز التسجيل في "المراسلة عبر السحابة الإلكترونية من Firebase" المقدَّم في الطلب غير صالح، يكون السلوك غير محدّد. لا يتم التحقّق من الرمز في كل طلب، إلا عند استخدامه لإرسال إشعار فوري باستخدام "المراسلة عبر السحابة الإلكترونية من Firebase".
إذا تم استدعاء المشغّل القابل للاستدعاء، ولكن تعذّر تنفيذه بسبب استثناء لم تتم معالجته أو عرض وعد فاشل، يتم رفض الطلب مع عرض
500 Internal Server Errorورمز الخطأINTERNAL. يمنع ذلك عرض أخطاء البرمجة للمستخدمين النهائيين عن غير قصد.إذا تم استدعاء الدالة القابلة للاستدعاء وعرضت حالة خطأ صريحة باستخدام واجهة برمجة التطبيقات المقدَّمة للدوال القابلة للاستدعاء، سيفشل الطلب. يستند رمز حالة HTTP الذي يتم عرضه إلى الربط الرسمي لحالة الخطأ بحالة HTTP، كما هو محدّد في code.proto. يتم ترميز رمز الخطأ والرسالة والتفاصيل المحدّدة التي يتم عرضها في نص الاستجابة كما هو موضّح أدناه. يعني ذلك أنّه إذا كانت الدالة تعرِض خطأً صريحًا بحالة
OK، ستكون حالة الاستجابة200 OK، ولكن يتم ضبط حقلerrorفي الاستجابة.إذا نجح مشغّل العميل، تكون حالة الاستجابة
200 OK.
تنسيق الاستجابة: العناوين
تحتوي الاستجابة على العناوين التالية:
Content-Type: application/json- يُسمح باستخدام
; charset=utf-8الاختياري.
نص الرد
تكون الاستجابة من نقطة نهاية العميل دائمًا كائن JSON. تحتوي على result أو error على الأقل، بالإضافة إلى أي حقول اختيارية. إذا لم تكن الاستجابة كائن JSON أو لم تكن تحتوي على data أو error، يجب أن تتعامل حزمة SDK للعميل مع الطلب على أنّه فاشل مع رمز خطأ Google INTERNAL (13).
error- إذا كان هذا الحقل موجودًا، يُعتبر الطلب فاشلاً، بغض النظر عن رمز حالة HTTP أو ما إذا كانdataموجودًا أيضًا. يجب أن تكون قيمة هذا الحقل كائن JSON بتنسيق Google Cloud HTTP Mapping العادي للأخطاء، مع حقولstatusوmessageوdetails(اختياريًا). يجب عدم تضمين الحقلcode. إذا لم يتم ضبط الحقلstatusأو كانت قيمته غير صالحة، يجب أن يتعامل العميل مع الحالة على أنّهاINTERNAL، وفقًا لـ code.proto. إذا كانdetailsموجودًا، يتم تضمينه في أي معلومات مستخدم مرفقة بالخطأ في حزمة SDK للعميل، إذا كان ذلك ممكنًا.
ملاحظة: الحقلdetailsهنا هو قيمة يقدّمها المستخدم. وليس بالضرورة قائمة بالقيم التي يتم تحديد مفاتيحها حسب نوع proto كما في تنسيق GoogleStatus.result- القيمة التي تعرِضها الدالة. يمكن أن تكون هذه القيمة أي قيمة JSON صالحة. تُرمِّز حزمة firebase-functions SDK تلقائيًا القيمة التي يعرِضها المستخدم بهذا التنسيق JSON. تفك حِزم SDK للعميل تلقائيًا ترميز هذه المَعلمات إلى أنواع أصلية وفقًا لتنسيق التسلسل الموضّح أدناه.
إذا كانت هناك حقول أخرى، يجب تجاهلها.
نشر الحلقات على نحو متسلسِل
يكون تنسيق التسلسل لحِملات البيانات العشوائية هو نفسه لكل من الطلب والاستجابة.
لضمان الاتساق بين المنصات، يتم ترميز هذه البيانات بتنسيق JSON كما لو كانت قيمة حقل Any في مخزن مؤقت لبروتوكول proto3، باستخدام ربط JSON العادي. يتم ترميز قيم الأنواع البسيطة، مثل null أو int أو double أو string مباشرةً، ولا تتضمّن نوعها الصريح. لذلك، يتم ترميز float وdouble بالطريقة نفسها، وقد لا تعرف أيًا منهما تم استلامه على الطرف الآخر من المكالمة. بالنسبة إلى الأنواع غير الأصلية في JSON، يتم استخدام ترميز proto3 المكتوب للقيمة. لمزيد من المعلومات، اطّلِع على مستندات ترميز Any JSON.
يُسمح بالأنواع التالية:
- null -
null - int (موقّعة أو غير موقّعة، تصل إلى 32 بت) - مثل
3أو-30. - float - مثل
3.14 - double - مثل
3.14 - boolean -
trueأوfalse - string - مثل
"hello world" - map<string, any=""> - مثل
{"x": 3}</string,> - list
- مثل [1, 2, 3] - long (موقّعة أو غير موقّعة، تصل إلى 64 بت) - [اطّلِع على التفاصيل أدناه]
لا يُسمح باستخدام القيم NaN وInfinity لـ float وdouble.
يُرجى العِلم أنّ long هو نوع خاص لا يُسمح به عادةً في JSON، ولكنّه مشمول بمواصفات proto3. على سبيل المثال، يتم ترميز هذه الأنواع على النحو التالي:
long
{
'@type': 'type.googleapis.com/google.protobuf.Int64Value',
'value': '-123456789123456'
}
unsigned long
{
'@type': 'type.googleapis.com/google.protobuf.UInt64Value',
'value': '123456789123456'
}
بشكل عام، يجب اعتبار المفتاح @type محجوزًا وعدم استخدامه للخرائط التي يتم تمريرها.
لأنّه لا يتم تحديد النوع للأنواع البسيطة، ستتغيّر بعض القيم بعد تمريرها عبر الشبكة. يصبح float الذي تم تمريره double. يصبح short int وما إلى ذلك. في Android، يُسمح باستخدام كل من List وJSONArray لقيم القوائم. في هذه الحالات، سيؤدي تمرير JSONArray إلى List.
إذا تم إلغاء تسلسل خريطة تتضمّن حقل @type غير معروف، يتم تركها كخريطة. يسمح ذلك للمطوّرين بإضافة حقول بأنواع جديدة إلى القيم التي يعرضونها بدون إيقاف عمل العملاء الأقدم.
عيّنات تعليمات برمجية
توضّح العيّنات في هذا القسم كيفية ترميز ما يلي:
- مثال على `callable.call` في Swift
- استجابة ناجحة للطلب
- استجابة فاشلة للطلب
مثال على `Callable.call` في Swift لترميز
callable.call([
"aString": "some string",
"anInt": 57,
"aFloat": 1.23,
"aLong": -123456789123456 as Int64
])
عنوان الطلب:
Method: POST
Content-Type: application/json; charset=utf-8
Authorization: Bearer some-auth-token
Firebase-Instance-ID-Token: some-iid-token
نص الطلب:
{
"data": {
"aString": "some string",
"anInt": 57,
"aFloat": 1.23,
"aLong": {
"@type": "type.googleapis.com/google.protobuf.Int64Value",
"value": "-123456789123456"
}
}
}
الاستجابة المطلوب ترميزها
return {
"aString": "some string",
"anInt": 57,
"aFloat": 1.23
};
عنوان الاستجابة الناجحة:
200 OK
Content-Type: application/json; charset=utf-8
نص الاستجابة الناجحة:
{
"response": {
"aString": "some string",
"anInt": 57,
"aFloat": 1.23
}
}
الاستجابة الفاشلة المطلوب ترميزها
throw new HttpsError("unauthenticated", "Request had invalid credentials.", {
"some-key": "some-value"
});
عنوان الاستجابة الفاشلة:
401 UNAUTHENTICATED
Content-Type: application/json; charset=utf-8
نص الاستجابة الفاشلة:
{
"error": {
"message": "Request had invalid credentials.",
"status": "UNAUTHENTICATED",
"details": {
"some-key": "some-value"
}
}
}