البدء: كتابة الدوال الأولى واختبارها ونشرها


لبدء استخدام Cloud Functions، يُرجى الاطّلاع على هذا البرنامج التعليمي، الذي يبدأ بمهام الإعداد المطلوبة ويتيح لك إنشاء دالتَين مرتبطتَين بهما واختبارهما ونشرهما:

  • دالة "إضافة رسالة" تعرض عنوان URL يقبل قيمة نصية وتكتبه في Cloud Firestore
  • يشير ذلك المصطلح إلى دالة "إنشاء أحرف كبيرة" التي يتم تشغيلها في Cloud Firestore وتحوِّل النص إلى أحرف كبيرة.

لقد اخترنا دالات JavaScript التي يتم تشغيلها في Cloud Firestore وHTTP لهذه العينة جزئيًا لأنّه يمكن اختبار المشغِّلات في الخلفية بدقة من خلال مجموعة أدوات المحاكاة المحلية من Firebase. تتوافق مجموعة الأدوات هذه أيضًا مع المشغلات القابلة للاستدعاء في Realtime Database، وPubSub وAuth وHTTP. يمكن اختبار جميع الأنواع الأخرى من المشغِّلات التي تعمل في الخلفية، مثل "الإعداد عن بُعد" وTestLab و"إحصاءات Google"، بشكل تفاعلي باستخدام مجموعات أدوات غير موضّحة في هذه الصفحة.

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

إنشاء مشروع Firebase

  1. في وحدة تحكُّم Firebase، انقر على إضافة مشروع.

    • لإضافة موارد Firebase إلى مشروع حالي على Google Cloud، أدخِل اسم مشروعه أو اختَره من القائمة المنسدلة.

    • لإنشاء مشروع جديد، أدخِل اسم المشروع المطلوب. يمكنك أيضًا تعديل رقم تعريف المشروع المعروض أسفل اسم المشروع اختياريًا.

  2. راجِع بنود Firebase واقبلها إذا طُلب منك ذلك.

  3. انقر على متابعة.

  4. (اختياري) يمكنك إعداد "إحصاءات Google" لمشروعك، ما يتيح لك الحصول على تجربة مثالية باستخدام أي من منتجات Firebase التالية:

    اختَر حسابًا حاليًا على "إحصاءات Google" أو أنشئ حسابًا جديدًا.

    إذا أنشأت حسابًا جديدًا، اختَر موقع إعداد تقارير "إحصاءات Google"، ثم اقبل إعدادات مشاركة البيانات وبنود "إحصاءات Google" لمشروعك.

  5. انقر على إنشاء مشروع (أو إضافة Firebase إذا كنت تستخدم مشروعًا حاليًا على Google Cloud).

يوفّر Firebase تلقائيًا الموارد لمشروعك على Firebase. عند اكتمال العملية، سيتم نقلك إلى صفحة النظرة العامة لمشروع Firebase في "وحدة تحكُّم Firebase".

إعداد Node.js وواجهة سطر الأوامر في Firebase

ستحتاج إلى بيئة Node.js لكتابة الدوال، وستحتاج إلى واجهة سطر الأوامر في Firebase لنشر الوظائف في وقت تشغيل دوال Cloud. لتثبيت Node.js وnpm، يُنصح باستخدام مدير إصدارات العقدة.

بعد تثبيت Node.js وnpm، يمكنك تثبيت واجهة سطر الأوامر في Firebase من خلال طريقتك المفضّلة. لتثبيت واجهة سطر الأوامر من خلال npm، استخدم:

npm install -g firebase-tools

يؤدي هذا إلى تثبيت أمر firebase المتاح عالميًا. إذا فشل الأمر، قد تحتاج إلى تغيير أذونات npm. للتحديث إلى آخر إصدار من firebase-tools، أعِد تشغيل الأمر نفسه.

إعداد مشروعك

عند إعداد حزمة تطوير البرامج (SDK) لمنصّة Firebase for Cloud Functions، يمكنك إنشاء مشروع فارغ يحتوي على اعتماديات ونموذج رمز أدنى، ويمكنك اختيار TypeScript أو JavaScript لإنشاء الدوال. لأغراض هذا البرنامج التعليمي، ستحتاج أيضًا إلى تهيئة Cloud Firestore.

لتهيئة مشروعك:

  1. شغِّل firebase login لتسجيل الدخول من خلال المتصفّح ومصادقة واجهة سطر الأوامر في Firebase.
  2. انتقِل إلى دليل مشروع Firebase.
  3. تشغيل firebase init firestore في هذا البرنامج التعليمي، يمكنك قبول القيم التلقائية عندما يُطلب منك إدخال قواعد Firestore وملفات الفهرسة. إذا لم تكن قد استخدمت Cloud Firestore في هذا المشروع حتى الآن، عليك أيضًا اختيار وضع البدء والموقع الجغرافي لـ Firestore كما هو موضّح في بدء استخدام Cloud Firestore.
  4. تشغيل firebase init functions يطالبك واجهة سطر الأوامر باختيار قاعدة أكواد حالية أو تهيئة قاعدة جديدة وتسميتها. عندما تبدأ للتو، يكفي توفّر قاعدة رموز برمجية واحدة في الموقع التلقائي. في وقت لاحق، مع توسيع عملية التنفيذ، قد تريد تنظيم الدوال في قواعد الرموز.
  5. يمنحك واجهة سطر الأوامر خيارين للحصول على دعم اللغة:

    للاطّلاع على هذا البرنامج التعليمي، اختَر JavaScript.

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

بعد اكتمال هذه الأوامر بنجاح، سيبدو هيكل مشروعك كما يلي:

myproject
 +- .firebaserc    # Hidden file that helps you quickly switch between
 |                 # projects with `firebase use`
 |
 +- firebase.json  # Describes properties for your project
 |
 +- functions/     # Directory containing all your functions code
      |
      +- .eslintrc.json  # Optional file containing rules for JavaScript linting.
      |
      +- package.json  # npm package file describing your Cloud Functions code
      |
      +- index.js      # main source file for your Cloud Functions code
      |
      +- node_modules/ # directory where your dependencies (declared in
                       # package.json) are installed

يحتوي ملف package.json الذي تم إنشاؤه أثناء الإعداد على مفتاح مهم: "engines": {"node": "16"}. يحدّد ذلك إصدار Node.js لكتابة الدوال ونشرها. يمكنك اختيار إصدارات أخرى متوافقة.

استيراد الوحدات المطلوبة وإعداد تطبيق

بعد الانتهاء من مهام الإعداد، يمكنك فتح الدليل المصدر والبدء في إضافة الرمز كما هو مُوضَّح في الأقسام التالية. في هذا النموذج، يجب أن يستورد مشروعك وحدتَي Cloud Functions وAdmin SDK باستخدام عبارات Node require. أضِف إلى ملف index.js سطورًا مثل ما يلي:

// The Cloud Functions for Firebase SDK to create Cloud Functions and set up triggers.
const functions = require('firebase-functions/v1');

// The Firebase Admin SDK to access Firestore.
const admin = require("firebase-admin");
admin.initializeApp();

تُحمِّل هذه الأسطر الوحدتَين firebase-functions وfirebase-admin، وتضبط مثيل تطبيق admin الذي يمكن إجراء تغييرات Cloud Firestore منه. في أي مكان يتوفر دعم SDK للمشرف، كما هو الحال بالنسبة إلى خدمة "المراسلة عبر السحابة الإلكترونية من Firebase" والمصادقة وقاعدة بيانات Firebase في الوقت الفعلي، فإنه يوفر طريقة فعّالة لدمج Firebase باستخدام وظائف السحابة الإلكترونية.

يعمل واجهة سطر الأوامر في Firebase تلقائيًا على تثبيت وحدات عقدة Firebase وFirebase SDK for Cloud Functions عند إعداد مشروعك. لإضافة مكتبات تابعة لجهات خارجية إلى مشروعك، يمكنك تعديل package.json وتشغيل npm install. لمزيد من المعلومات، يُرجى الاطّلاع على تبعيات الاسم المعرِّف.

إضافة الدالة addMessage()

في الدالة addMessage()، أضِف هذه الأسطر إلى index.js:

// Take the text parameter passed to this HTTP endpoint and insert it into
// Firestore under the path /messages/:documentId/original
exports.addMessage = functions.https.onRequest(async (req, res) => {
  // Grab the text parameter.
  const original = req.query.text;
  // Push the new message into Firestore using the Firebase Admin SDK.
  const writeResult = await admin
    .firestore()
    .collection("messages")
    .add({ original: original });
  // Send back a message that we've successfully written the message
  res.json({ result: `Message with ID: ${writeResult.id} added.` });
});

الدالة addMessage() هي نقطة نهاية HTTP. ينتج عن أي طلب لنقطة النهاية كائنان Request وResponse بنمطَي ExpressJS يتم تمريرهما إلى استدعاء onRequest().

تكون دوال HTTP متزامنة (على غرار الدوال القابلة للاستدعاء)، لذا يجب إرسال استجابة في أسرع وقت ممكن وتأجيل العمل باستخدام Cloud Firestore. تضبط دالة HTTP addMessage() قيمة نصية إلى نقطة نهاية HTTP وتدخلها في قاعدة البيانات ضمن المسار /messages/:documentId/original.

إضافة الدالة makeUppercase()

في الدالة makeUppercase()، أضِف هذه الأسطر إلى index.js:

// Listens for new messages added to /messages/:documentId/original and creates an
// uppercase version of the message to /messages/:documentId/uppercase
exports.makeUppercase = functions.firestore
  .document("/messages/{documentId}")
  .onCreate((snap, context) => {
    // Grab the current value of what was written to Firestore.
    const original = snap.data().original;

    // Access the parameter `{documentId}` with `context.params`
    functions.logger.log("Uppercasing", context.params.documentId, original);

    const uppercase = original.toUpperCase();

    // You must return a Promise when performing asynchronous tasks inside a Functions such as
    // writing to Firestore.
    // Setting an 'uppercase' field in Firestore document returns a Promise.
    return snap.ref.set({ uppercase }, { merge: true });
  });

يتم تنفيذ الدالة makeUppercase() عند كتابة بيانات Cloud Firestore إلى. تحدد الدالة ref.set المستند الذي سيستمع إليه. لأسباب تتعلق بالأداء، يجب أن تكون محددًا قدر الإمكان.

الأقواس، مثل {documentId}، المحيطة بـ "المَعلمات"، وهي أحرف بدل تعرض البيانات المتطابقة في معاودة الاتصال.

تؤدي Cloud Firestore إلى تفعيل معاودة الاتصال onCreate() عند إضافة رسائل جديدة.

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

محاكاة تنفيذ الدوال

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

لمحاكاة الدوال:

  1. شغِّل firebase emulators:start وتحقَّق من عنوان URL الخاص بواجهة المستخدم في Emulator Suite. ويتم ضبطها تلقائيًا على localhost:4000، ولكن قد تتم استضافتها على منفذ مختلف على جهازك. أدخِل عنوان URL هذا في المتصفّح لفتح واجهة مستخدم Emulator Suite.

  2. يمكنك التحقّق من ناتج الأمر firebase emulators:start في عنوان URL الخاص بدالة HTTP addMessage(). سيبدو مشابهًا للرمز http://localhost:5001/MY_PROJECT/us-central1/addMessage، باستثناء ما يلي:

    1. سيتم استبدال MY_PROJECT برقم تعريف مشروعك.
    2. قد يختلف المنفذ على جهازك المحلي.
  3. أضِف سلسلة طلب البحث ?text=uppercaseme إلى نهاية عنوان URL للدالة. من المفترض أن يبدو العرض على النحو التالي: http://localhost:5001/MY_PROJECT/us-central1/addMessage?text=uppercaseme. يمكنك اختياريًا تغيير الرسالة "كبير الأحرف" إلى رسالة مخصّصة.

  4. يمكنك إنشاء رسالة جديدة من خلال فتح عنوان URL في علامة تبويب جديدة في المتصفّح.

  5. عرض تأثيرات الدوال في واجهة مستخدم Emulator Suite:

    1. في علامة التبويب السجلات، من المفترض أن تظهر لك سجلّات جديدة تشير إلى أنّه تم تشغيل الدالتَين addMessage() وmakeUppercase():

      i functions: Beginning execution of "addMessage"

      i functions: Beginning execution of "makeUppercase"

    2. في علامة التبويب Firestore، من المفترض أن يظهر لك مستند يحتوي على رسالتك الأصلية، بالإضافة إلى النسخة الكبيرة من رسالتك (إذا كانت كتابة الرسالة "كبيرة" في الأصل، ستظهر لك عبارة "أحرف كبيرة").

نشر الدوال في بيئة إنتاج

بعد أن تعمل الوظائف على النحو المطلوب في المحاكي، يمكنك مواصلة نشرها واختبارها وتشغيلها في بيئة الإنتاج. تذكَّر أنّه للنشر في بيئة وقت تشغيل Node.js 14 المقترَحة، يجب أن يكون مشروعك على خطة تسعير Blaze. يُرجى الاطّلاع على أسعار Cloud Functions.

لإكمال البرنامج التعليمي، انشر الدوال ثم نفِّذ addMessage() لتشغيل makeUppercase().

  1. نفِّذ الأمر التالي لنشر الدوال:

     firebase deploy --only functions
     

    بعد تشغيل هذا الأمر، يُخرج واجهة سطر الأوامر في Firebase عنوان URL لأي نقاط نهاية لدوال HTTP. في الوحدة الطرفية، من المفترض أن يظهر خط مثل ما يلي:

    Function URL (addMessage): https://us-central1-MY_PROJECT.cloudfunctions.net/addMessage
    

    يحتوي عنوان URL على رقم تعريف مشروعك بالإضافة إلى منطقة لدالة HTTP. ليس عليك القلق الآن، ولكن يجب أن تحدّد بعض دوال HTTP للإنتاج موقعًا جغرافيًا لتقليل وقت استجابة الشبكة.

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

  2. باستخدام إخراج عنوان URL addMessage() من خلال واجهة سطر الأوامر، أضِف مَعلمة طلب بحث نصي، وافتحها في متصفّح على النحو التالي:

    https://us-central1-MY_PROJECT.cloudfunctions.net/addMessage?text=uppercasemetoo
    

    تنفِّذ الدالة المتصفّح وتعيد توجيهه إلى وحدة تحكُّم Firebase في موقع قاعدة البيانات الذي يتم فيه تخزين السلسلة النصية. يؤدي حدث الكتابة هذا إلى تشغيل makeUppercase()، الذي يكتب نسخة بأحرف كبيرة من السلسلة.

بعد نشر الوظائف وتنفيذها، يمكنك عرض السجلات في وحدة تحكُّم Google Cloud. إذا كنت تريد حذف الدوال في مرحلة التطوير أو الإنتاج، استخدِم واجهة سطر الأوامر في Firebase.

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

مراجعة نموذج الرمز البرمجي الكامل

إليك functions/index.js المكتملة التي تحتوي على الدالتين addMessage() وmakeUppercase(). تسمح لك هذه الدوال بتمرير معلمة إلى نقطة نهاية HTTP تكتب قيمة إلى Cloud Firestore، ثم تحوِّلها من خلال إضافة جميع أحرف السلسلة.

// The Cloud Functions for Firebase SDK to create Cloud Functions and set up triggers.
const functions = require('firebase-functions/v1');

// The Firebase Admin SDK to access Firestore.
const admin = require("firebase-admin");
admin.initializeApp();

// Take the text parameter passed to this HTTP endpoint and insert it into
// Firestore under the path /messages/:documentId/original
exports.addMessage = functions.https.onRequest(async (req, res) => {
  // Grab the text parameter.
  const original = req.query.text;
  // Push the new message into Firestore using the Firebase Admin SDK.
  const writeResult = await admin
    .firestore()
    .collection("messages")
    .add({ original: original });
  // Send back a message that we've successfully written the message
  res.json({ result: `Message with ID: ${writeResult.id} added.` });
});

// Listens for new messages added to /messages/:documentId/original and creates an
// uppercase version of the message to /messages/:documentId/uppercase
exports.makeUppercase = functions.firestore
  .document("/messages/{documentId}")
  .onCreate((snap, context) => {
    // Grab the current value of what was written to Firestore.
    const original = snap.data().original;

    // Access the parameter `{documentId}` with `context.params`
    functions.logger.log("Uppercasing", context.params.documentId, original);

    const uppercase = original.toUpperCase();

    // You must return a Promise when performing asynchronous tasks inside a Functions such as
    // writing to Firestore.
    // Setting an 'uppercase' field in Firestore document returns a Promise.
    return snap.ref.set({ uppercase }, { merge: true });
  });

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

في هذا المستند، يمكنك معرفة المزيد حول كيفية إدارة الدوال لـ Cloud Functions بالإضافة إلى كيفية التعامل مع جميع أنواع الأحداث المتوافقة مع Cloud Functions.

لمعرفة المزيد عن دوال السحابة، يمكنك أيضًا إجراء ما يلي: