قرار دادن توابع با وظایف ابری (نسل اول)

توابع صف وظایف از Google Cloud Tasks بهره می‌برند تا به برنامه شما کمک کنند وظایف زمان‌بر، منابع‌بر یا با محدودیت پهنای باند را به صورت غیرهمزمان و خارج از جریان اصلی برنامه شما اجرا کند.

برای مثال، تصور کنید که می‌خواهید از مجموعه بزرگی از فایل‌های تصویری که در حال حاضر روی یک API با محدودیت سرعت میزبانی می‌شوند، پشتیبان تهیه کنید. برای اینکه مصرف‌کننده مسئولی برای آن API باشید، باید محدودیت‌های سرعت آنها را رعایت کنید. به علاوه، این نوع کار طولانی مدت می‌تواند به دلیل وقفه‌های زمانی و محدودیت‌های حافظه در معرض شکست باشد.

برای کاهش این پیچیدگی، می‌توانید یک تابع صف وظیفه بنویسید که گزینه‌های اساسی وظیفه مانند scheduleTime و dispatchDeadline را تنظیم کند و سپس تابع را به یک صف در Cloud Tasks واگذار کند. محیط Cloud Tasks به طور خاص برای اطمینان از کنترل ازدحام موثر و سیاست‌های تلاش مجدد برای این نوع عملیات طراحی شده است.

کیت توسعه نرم‌افزار Firebase برای Cloud Functions for Firebase نسخه ۳.۲۰.۱ و بالاتر با Firebase Admin SDK ۱۰.۲.۰ و بالاتر برای پشتیبانی از توابع صف وظایف، تعامل دارد.

استفاده از توابع صف وظایف با Firebase می‌تواند منجر به هزینه‌هایی برای پردازش Cloud Tasks شود. برای اطلاعات بیشتر به قیمت‌گذاری Cloud Tasks مراجعه کنید.

ایجاد توابع صف وظایف

برای استفاده از توابع صف وظایف، این گردش کار را دنبال کنید:

  1. با استفاده از Firebase SDK for Cloud Functions یک تابع صف وظایف بنویسید.
  2. تابع خود را با اجرای آن با یک درخواست HTTP آزمایش کنید.
  3. تابع خود را با استفاده از رابط خط فرمان Firebase CLI) مستقر کنید. هنگام استقرار تابع صف وظایف خود برای اولین بار، رابط خط فرمان (CLI) یک صف وظایف در Cloud Tasks با گزینه‌هایی (محدود کردن سرعت و تلاش مجدد) که در کد منبع شما مشخص شده‌اند، ایجاد می‌کند.
  4. وظایف را به صف وظایف تازه ایجاد شده اضافه کنید و در صورت نیاز پارامترهایی را برای تنظیم برنامه اجرا ارسال کنید. می‌توانید با نوشتن کد با استفاده از Admin SDK و استقرار آن در Cloud Functions for Firebase به این هدف دست یابید.

نوشتن توابع صف وظایف

برای شروع نوشتن توابع صف وظایف onDispatch استفاده کنید. بخش مهمی از نوشتن یک تابع صف وظایف، تنظیم پیکربندی تلاش مجدد به ازای هر صف و محدود کردن سرعت است. نمونه‌های کد موجود در این صفحه بر اساس برنامه‌ای است که سرویسی را راه‌اندازی می‌کند که از تمام تصاویر تصویر نجومی روز ناسا پشتیبان‌گیری می‌کند:

پیکربندی توابع صف وظایف

توابع صف وظیفه با مجموعه‌ای قدرتمند از تنظیمات پیکربندی ارائه می‌شوند تا محدودیت‌های نرخ و رفتار تلاش مجدد صف وظیفه را به طور دقیق کنترل کنند:

exports.backupApod = functions
    .runWith( {secrets: ["NASA_API_KEY"]})
    .tasks.taskQueue({
      retryConfig: {
        maxAttempts: 5,
        minBackoffSeconds: 60,
      },
      rateLimits: {
        maxConcurrentDispatches: 6,
      },
    }).onDispatch(async (data) => {
  • retryConfig.maxAttempts=5 : هر وظیفه در صف وظایف به طور خودکار تا 5 بار دوباره امتحان می‌شود. این به کاهش خطاهای گذرا مانند خطاهای شبکه یا اختلال موقت سرویس یک سرویس خارجی وابسته کمک می‌کند.
  • retryConfig.minBackoffSeconds=60 : هر وظیفه حداقل با فاصله ۶۰ ثانیه از هر تلاش دوباره اجرا می‌شود. این یک بافر بزرگ بین هر تلاش فراهم می‌کند، بنابراین ما عجله نمی‌کنیم که ۵ تلاش دوباره را خیلی سریع تمام کنیم.
  • rateLimits.maxConcurrentDispatch=6 : حداکثر ۶ وظیفه در یک زمان معین ارسال می‌شوند. این به تضمین جریان ثابتی از درخواست‌ها به تابع اصلی کمک می‌کند و به کاهش تعداد نمونه‌های فعال و شروع‌های سرد کمک می‌کند.

توابع صف وظیفه را آزمایش کنید

در بیشتر موارد، شبیه‌ساز Cloud Functions بهترین روش برای آزمایش توابع صف وظایف است. برای یادگیری نحوه‌ی تجهیز برنامه‌ی خود برای شبیه‌سازی توابع صف وظایف، به مستندات Emulator Suite مراجعه کنید.

علاوه بر این، توابع صف وظایف به عنوان توابع ساده HTTP در Firebase Local Emulator Suite ارائه می‌شوند. می‌توانید یک تابع وظیفه شبیه‌سازی شده را با ارسال یک درخواست HTTP POST با یک payload داده json آزمایش کنید:

 # start the Firebase Emulators
 firebase emulators:start

 # trigger the emulated task queue function
 curl \
  -X POST                                            # An HTTP POST request...
  -H "content-type: application/json" \              # ... with a JSON body
  http://localhost:$PORT/$PROJECT_ID/$REGION/$NAME \ # ... to function url
  -d '{"data": { ... some data .... }}'              # ... with JSON encoded data

استقرار توابع صف وظایف

استقرار تابع صف وظایف با استفاده از رابط خط فرمان فایربیس:

$ firebase deploy --only functions:backupApod

هنگام استقرار یک تابع صف وظیفه برای اولین بار، رابط خط فرمان (CLI) یک صف وظیفه در Cloud Tasks با گزینه‌هایی (محدود کردن سرعت و تلاش مجدد) که در کد منبع شما مشخص شده‌اند، ایجاد می‌کند.

اگر هنگام استقرار توابع با خطاهای مجوز مواجه شدید، مطمئن شوید که نقش‌های IAM مناسب به کاربری که دستورات استقرار را اجرا می‌کند، اختصاص داده شده است.

توابع صف وظایف را به نوبت درآورید

توابع صف وظایف را می‌توان از یک محیط سرور قابل اعتماد مانند Cloud Functions for Firebase با استفاده از Firebase Admin SDK برای Node.js در Cloud Tasks صف‌بندی کرد. اگر در استفاده از Admin SDK تازه‌کار هستید، برای شروع به بخش افزودن فایربیس به سرور مراجعه کنید.

در یک جریان معمول، Admin SDK یک وظیفه جدید ایجاد می‌کند، آن را در Cloud Tasks قرار می‌دهد و پیکربندی وظیفه را تنظیم می‌کند:

exports.enqueueBackupTasks = functions.https.onRequest(
async (_request, response) => {
  const queue = getFunctions().taskQueue("backupApod");
  const enqueues = [];
  for (let i = 0; i <= 10; i += 1) {
    // Enqueue each task with i*60 seconds delay. Our task queue function
    // should process ~1 task/min.
    const scheduleDelaySeconds = i * 60 
    enqueues.push(
        queue.enqueue(
          { id: `task-${i}` },
          {
            scheduleDelaySeconds,
            dispatchDeadlineSeconds: 60 * 5 // 5 minutes
          },
        ),
    );
  }
  await Promise.all(enqueues);
  response.sendStatus(200);

});
  • scheduleDelaySeconds : کد نمونه سعی می‌کند با اختصاص تأخیر N دقیقه‌ای برای Nمین وظیفه، اجرای وظایف را گسترش دهد. این به معنای راه‌اندازی حدود ۱ وظیفه در دقیقه است. توجه داشته باشید که اگر می‌خواهید Cloud Tasks یک وظیفه را در زمان خاصی راه‌اندازی کند، می‌توانید از scheduleTime نیز استفاده کنید.
  • dispatchDeadlineSeconds : حداکثر مدت زمانی که Cloud Tasks برای تکمیل یک وظیفه منتظر می‌ماند. Cloud Tasks پس از پیکربندی تلاش مجدد صف یا تا زمان رسیدن به این مهلت، وظیفه را دوباره امتحان می‌کند. در نمونه، صف طوری پیکربندی شده است که وظیفه را تا 5 بار دوباره امتحان کند، اما اگر کل فرآیند (شامل تلاش‌های تلاش مجدد) بیش از 5 دقیقه طول بکشد، وظیفه به طور خودکار لغو می‌شود.

عیب‌یابی

فعال کردن ثبت Cloud Tasks

گزارش‌های Cloud Tasks حاوی اطلاعات تشخیصی مفیدی مانند وضعیت درخواست مرتبط با یک وظیفه هستند. به طور پیش‌فرض، گزارش‌های Cloud Tasks به دلیل حجم زیاد گزارش‌هایی که می‌تواند به طور بالقوه در پروژه شما ایجاد کند، غیرفعال هستند. توصیه می‌کنیم در حالی که به طور فعال در حال توسعه و اشکال‌زدایی توابع صف وظایف خود هستید، گزارش‌های اشکال‌زدایی را فعال کنید. به بخش فعال کردن گزارش‌گیری مراجعه کنید.

مجوزهای IAM

ممکن است هنگام قرار دادن وظایف در صف یا زمانی که Cloud Tasks سعی می‌کند توابع صف وظایف شما را فراخوانی کند، با خطای PERMISSION DENIED مواجه شوید. مطمئن شوید که پروژه شما دارای اتصالات IAM زیر است:

  • هویتی که برای قرار دادن وظایف در Cloud Tasks استفاده می‌شود، به مجوز IAM مربوط cloudtasks.tasks.create نیاز دارد.

    در نمونه، این حساب سرویس پیش‌فرض App Engine است

gcloud projects add-iam-policy-binding $PROJECT_ID \
  --member=serviceAccount:${PROJECT_ID}@appspot.gserviceaccount.com \
  --role=roles/cloudtasks.enqueuer
  • هویتی که برای قرار دادن وظایف در Cloud Tasks استفاده می‌شود، برای استفاده از حساب سرویس مرتبط با یک وظیفه در Cloud Tasks نیاز به مجوز دارد.

    در نمونه، این حساب سرویس پیش‌فرض App Engine است.

برای دستورالعمل‌های مربوط به نحوه افزودن حساب سرویس پیش‌فرض App Engine به عنوان کاربر حساب سرویس پیش‌فرض App Engine به مستندات Google Cloud IAM مراجعه کنید.

  • هویتی که برای فعال کردن تابع صف وظایف استفاده می‌شود، به مجوز cloudfunctions.functions.invoke نیاز دارد.

    در نمونه، این حساب سرویس پیش‌فرض App Engine است

gcloud functions add-iam-policy-binding $FUNCTION_NAME \
  --region=us-central1 \
  --member=serviceAccount:${PROJECT_ID}@appspot.gserviceaccount.com \
  --role=roles/cloudfunctions.invoker