إضافة عناصر الجذب للمستخدمين إلى إضافة

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

  • أحداث Eventarc: لمنح المستخدمين طريقة للردّ بشكل غير متزامن على الأحداث، يمكنك النشر على Eventarc. يمكن للمستخدمين نشر دوال معالجة الأحداث التي ترسل مثلاً إشعارات بعد اكتمال المهام الطويلة، أو يمكنهم تحديد دوال المعالجة اللاحقة الخاصة بهم.

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

يمكن أن تستخدم الإضافة إحدى الطريقتَين أو كلتيهما.

أحداث Eventarc

لنشر الأحداث من إضافة، اتّبِع الخطوات التالية:

  1. أعلِن عن أنواع الأحداث التي ستنشرها في ملف extension.yaml:

    events:
      - type: publisher-id.extension-name.version.event-name
        description: event-description
      - type: publisher-id.extension-name.version.another-event-name
        description: another-event-description
    

    يتكوّن المعرّف type من عدة حقول مفصولة بنقاط. حقول "رقم تعريف الناشر" و"اسم الإضافة" و"اسم الحدث" مطلوبة. ننصحك بملء حقل "الإصدار". اختَر اسم حدث فريدًا ووصفيًا لكل نوع حدث تنشره.

    على سبيل المثال، تعلن إضافة storage-resize-images عن نوع حدث واحد:

    events:
      - type: firebase.extensions.storage-resize-images.v1.complete
        description: |
          Occurs when image resizing completes. The event will contain further
          details about specific formats and sizes.
    

    سيتمكّن المستخدمون من اختيار الأحداث التي يريدون الاشتراك فيها عند تثبيت الإضافة.

  2. في دوال الإضافة، استورِد Eventarc API من Admin SDK وأَنشِئ قناة أحداث باستخدام إعدادات التثبيت الخاصة بالمستخدم. يتم عرض هذه الإعدادات باستخدام متغيّرات البيئة التالية:

    • EVENTARC_CHANNEL: الاسم المؤهّل بالكامل لقناة Eventarc التي اختار المستخدم نشر الأحداث عليها.
    • EXT_SELECTED_EVENTS: قائمة بأنواع الأحداث التي اختار المستخدم نشرها، مفصولة بفواصل. عند إنشاء قناة باستخدام هذه القيمة، تعمل حزمة تطوير البرامج (SDK) للمشرف تلقائيًا على فلترة الأحداث التي لم يختارها المستخدم.
    • EVENTARC_CLOUD_EVENT_SOURCE: معرّف مصدر Cloud Event. تمرِّر حزمة تطوير البرامج (SDK) للمشرف هذه القيمة تلقائيًا في حقل source للأحداث المنشورة. لا تحتاج عادةً إلى استخدام هذا المتغيّر بشكلٍ صريح.

    إذا لم يتم تفعيل الأحداث أثناء التثبيت، ستكون هذه المتغيّرات غير محدّدة. يمكنك استخدام هذه المعلومة لإنشاء قناة أحداث فقط عندما تكون الأحداث مفعّلة:

    import * as admin from "firebase-admin";
    import {getEventarc} from 'firebase-admin/eventarc';
    
    admin.initializeApp();
    
    // Set eventChannel to a newly-initialized channel, or `undefined` if events
    // aren't enabled.
    const eventChannel =
      process.env.EVENTARC_CHANNEL &&
      getEventarc().channel(process.env.EVENTARC_CHANNEL, {
        allowedEventTypes: process.env.EXT_SELECTED_EVENTS,
      });
    
  3. انشر الأحداث على القناة في النقاط التي تريد عرضها للمستخدمين في الإضافة. على سبيل المثال:

    // If events are enabled, publish a `complete` event to the configured
    // channel.
    eventChannel && eventChannel.publish({
        type: 'firebase.extensions.storage-resize-images.v1.complete',
        subject: filename,  // the name of the original file
        data: {
          // ...
        }
    });
    
  4. وثِّق الأحداث التي تنشرها في ملف PREINSTALL أو POSTINSTALL.

    لكل حدث، وثِّق ما يلي:

    • الغرض المقصود منه
    • النقطة التي يتم فيها تشغيل الحدث في منطق الإضافة
    • بيانات الإخراج التي يتضمّنها
    • شروط تنفيذه

    بالإضافة إلى ذلك، حذِّر المستخدمين من عدم تنفيذ أي إجراءات في معالِجات الأحداث التي قد تؤدي إلى تشغيل الإضافة نفسها، ما يؤدي إلى حلقة لا نهائية.

عند نشر الأحداث من إضافة، يمكن للمستخدمين نشر معالِجات الأحداث للردّ باستخدام منطق مخصّص.

على سبيل المثال، يحذف المثال التالي الصورة الأصلية بعد تغيير حجمها. يُرجى العِلم أنّ معالج المثال هذا يستخدم السمة subject للحدث، وهي في هذه الحالة اسم الملف الأصلي للصورة.

exports.onimageresized = onCustomEventPublished(
    "firebase.extensions.storage-resize-images.v1.complete",
    (event) => {
      logger.info("Received image resize completed event", event);
      // For example, delete the original.
      return admin.storage()
          .bucket("my-project.firebasestorage.app")
          .file(event.subject)
          .delete();
    });

لمزيد من المعلومات، اطّلِع على مشغّلات الأحداث المخصّصة.

مثال

توفر إضافة Resize Images الرسمية خطافًا غير متزامن من خلال النشر على Eventarc بعد تغيير حجم صورة.

الخطافات المتزامنة

عندما تريد تزويد المستخدمين بخطاف يجب أن يكتمل بنجاح لكي تعمل إحدى دوال الإضافة، استخدِم الخطافات المتزامنة.

يستدعي الخطاف المتزامن دالة Cloud Function قابلة للاستدعاء عبر HTTPS يحدّدها المستخدم وينتظر اكتمالها (ربما مع قيمة يتم إرجاعها) قبل المتابعة. يؤدي حدوث خطأ في الدالة التي يقدّمها المستخدم إلى حدوث خطأ في دالة الإضافة.

لعرض خطاف متزامن، اتّبِع الخطوات التالية:

  1. أضِف مَعلمة إلى الإضافة تسمح للمستخدمين بضبط الإضافة باستخدام عنوان URL لدالة Cloud Function المخصّصة. على سبيل المثال:

    - param: PREPROCESSING_FUNCTION
      label: Pre-processing function URL
      description: >
        An HTTPS callable function that will be called to transform the input data
        before it is processed by this function.
      type: string
      example: https://us-west1-my-project-id.cloudfunctions.net/preprocessData
      required: false
    
  2. في النقطة التي تريد عرض الخطاف فيها في الإضافة، استدعِ الدالة باستخدام عنوان URL الخاص بها. على سبيل المثال:

    const functions = require('firebase-functions/v1');
    const fetch = require('node-fetch');
    
    const preprocessFunctionURL = process.env.PREPROCESSING_FUNCTION;
    
    exports.yourFunctionName = functions.firestore.document("collection/{doc_id}")
        .onWrite((change, context) => {
          // PREPROCESSING_FUNCTION hook begins here.
          // If a preprocessing function is defined, call it before continuing.
          if (preprocessFunctionURL) {
            try {
              await fetch(preprocessFunctionURL); // Could also be a POST request if you want to send data.
            } catch (e) {
              // Preprocessing failure causes the function to fail.
              functions.logger.error("Preprocessor error:", e);
              return;
            }
          }
          // End of PREPROCESSING_FUNCTION hook.
    
          // Main function logic follows.
          // ...
        });
    
  3. وثِّق أي خطافات تتيحها في ملف PREINSTALL أو POSTINSTALL.

    لكل خطاف، وثِّق ما يلي:

    • الغرض المقصود منه
    • النقطة التي يتم فيها تشغيل الخطاف في منطق الإضافة
    • المدخلات والمخرجات المتوقّعة
    • شروط (أو خيارات) تنفيذه

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

مثال

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