مراكز المهام في الدوال الدائمة (دوال Azure)

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

Diagram showing concept of function app and task hub concept.

من الناحية المفاهيمية، يقوم مركز المهام بتخزين المعلومات التالية:

  • حالات المثيل لجميع حالات التزامن والكيان.
  • الرسائل التي ستتم معالجتها، بما في ذلك
    • أي رسائل نشاط تمثل الأنشطة تنتظر التشغيل.
    • أي رسائل مثيل تنتظر تسليمها للمثيلات.

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

داخليًا، قد يستخدم كل مزود تخزين منظمة مختلفة لتمثيل حالات المثيل والرسائل. على سبيل المثال، يتم تخزين الرسائل في قوائم انتظار تخزين Azure بواسطة موفر Azure Storage، ولكن في جداول علائقية بواسطة موفر MSSQL. لا تهم هذه الاختلافات بقدر ما يتعلق الأمر بتصميم التطبيق، ولكن بعضها قد يؤثر على خصائص الأداء. سنناقشها في قسم التمثيل في التخزين أدناه.

عناصر العمل

تمثل رسائل النشاط ورسائل المثيل في مركز المهام العمل الذي يحتاج تطبيق الوظيفة لمعالجته. أثناء تشغيل تطبيق الوظيفة، يقوم باستمرار بجلب عناصر العمل من مركز المهام. ويعالج كل عنصر عمل رسالة واحدة أو أكثر. نميز بين نوعين من عناصر العمل:

  • عناصر عمل النشاط: تشغيل دالة نشاط لمعالجة رسالة نشاط.
  • عنصر عمل المنسق: تشغيل منسق أو دالة كيان لمعالجة رسالة مثيل واحدة أو أكثر.

يمكن للعمال معالجة عناصر عمل متعددة في نفس الوقت، وفقًا لحدود التزامن المكونة لكل عامل.

وبمجرد أن يكمل العامل عنصر عمل، فإنه يقوم بتثبيت التأثيرات مرة أخرى إلى مركز المهام. قد تختلف هذه التأثيرات حسب نوع الدالة التي تم تنفيذها:

  • كما تنشئ دالة النشاط المكتملة رسالة مثيل تحتوي على النتيجة، موجهة إلى مثيل المنسق الأصل.
  • وتقوم دالة المنسق المكتملة بتحديث حالة التزامن والمحفوظات، وقد تنشئ رسائل جديدة.
  • تقوم دالة الكيان المكتملة بتحديث حالة الكيان، وقد تنشئ أيضًا رسائل مثيل جديدة.

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

مثال التنفيذ

ضع في الاعتبار تزامن المروحة الذي يبدأ نشاطين بالتوازي، وينتظر اكتمال كليهما:

[FunctionName("Example")]
public static async Task Run([OrchestrationTrigger] IDurableOrchestrationContext context)
{
    Task t1 = context.CallActivityAsync<int>("MyActivity", 1);
    Task t2 = context.CallActivityAsync<int>("MyActivity", 2);
    await Task.WhenAll(t1, t2);
}

وبعد بدء هذا التنسيق من قبل عميل، تتم معالجته بواسطة تطبيق الوظائف كتسلسل من عناصر العمل. حيث يقوم كل عنصر عمل مكتمل بتحديث حالة مركز المهام عند التثبيت. هذه هي الخطوات:

  1. كما يطلب العميل بدء تزامن جديد بمعرف المثيل "123". وبعد أن يكمل العميل هذا الطلب، يحتوي مركز المهام على عنصر نائب لحالة التنسيق ورسالة مثيل:

    workitems-illustration-step-1

    تعد التسمية ExecutionStarted واحدة من العديد من أنواع أحداث المحفوظات التي تحدد الأنواع المختلفة من الرسائل والأحداث المشاركة في محفوظات التزامن.

  2. يقوم العامل بتنفيذ عنصر عمل منسق لمعالجة ExecutionStarted الرسالة. يستدعي وظيفة المنسق التي تبدأ في تنفيذ التعليمات البرمجية للتنسيق. تقوم هذه التعليمة البرمجية بجدولة نشاطين ثم تتوقف عن التنفيذ عند انتظار النتائج. وبعد أن يقوم العامل بتثبيت عنصر العمل هذا، يحتوي مركز المهام على

    workitems-illustration-step-2

    تعتبر حالة وقت التشغيل الآن Running، تمت إضافة رسالتين جديدتينTaskScheduled، وتحتوي المحفوظات الآن على الأحداث الخمسة OrchestratorStarted وExecutionStarted وTaskScheduled وTaskScheduled وOrchestratorCompleted. تمثل الأحداث الحلقة الأولى من تنفيذ هذا التنسيق.

  3. ينفذ العامل عنصر عمل نشاط لمعالجة إحدى الرسائل TaskScheduled. يستدعي وظيفة النشاط مع الإدخال "2". وعند اكتمال دالة النشاط، فإنها تنشئ TaskCompleted رسالة تحتوي على النتيجة. وبعد أن يقوم العامل بتثبيت عنصر العمل هذا، يحتوي مركز المهام على

    workitems-illustration-step-3

  4. يقوم العامل بتنفيذ عنصر عمل منسق لمعالجة TaskCompleted الرسالة. إذا كان التنسيق لا يزال مخزنًا مؤقتًا في الذاكرة، فيمكنه فقط استئناف التنفيذ. وإلا، يقوم العامل أولاً بإعادة تشغيل المحفوظات لاسترداد الحالة الحالية للتنسيق . ومن ثم يستمر في التزامن، وتقديم نتيجة النشاط. وبعد تلقي هذه النتيجة، لا يزال التنسيق في انتظار نتيجة النشاط الآخر، لذلك يتوقف مرة أخرى عن التنفيذ. وبعد أن يقوم العامل بتثبيت عنصر العمل هذا، يحتوي مركز المهام على

    workitems-illustration-step-4

    يحتوي محفوظات التنسيق الآن على ثلاثة أحداث أخرى OrchestratorStarted وTaskCompleted وOrchestratorCompleted. تمثل الأحداث الحلقة الثانية من تنفيذ هذا التنسيق.

  5. ويقوم العامل بتنفيذ عنصر عمل نشاط لمعالجة الرسالة المتبقية TaskScheduled. ويستدعي وظيفة النشاط مع الإدخال "1". وبعد أن يقوم العامل بتثبيت عنصر العمل هذا، يحتوي مركز المهام على

    workitems-illustration-step-5

  6. ويقوم العامل بتنفيذ عنصر عمل منسق آخر لمعالجة TaskCompleted الرسالة. وبعد تلقي هذه النتيجة الثانية، يكتمل التنسيق. وبعد أن يقوم العامل بتثبيت عنصر العمل هذا، يحتوي مركز المهام على

    workitems-illustration-step-6

    تعتبر حالة وقت التشغيل الآن Completed، وتحتوي محفوظات التنسيق الآن على أربعة أحداث أخرى OrchestratorStarted وTaskCompleted وExecutionCompleted وOrchestratorCompleted. تمثل الأحداث الحلقة الثالثة والأخيرة من تنفيذ هذا التنسيق.

ثم تحتوي المحفوظات النهائية لتنفيذ هذا التنسيق على 12 حدثًا OrchestratorStarted وExecutionStarted وTaskScheduled وTaskScheduled وOrchestratorCompleted وOrchestratorStarted وTaskCompleted وOrchestratorCompleted وOrchestratorStarted وTaskCompleted وExecutionCompleted وOrchestratorCompleted.

إشعار

الجدول الموضح ليس هو الوحيد: فهناك العديد من الجداول الممكنة المختلفة قليلاً. على سبيل المثال، إذا اكتمل النشاط الثاني في وقت سابق، فقد تتم معالجة كلتا رسالتي المثيلتين TaskCompleted بواسطة عنصر عمل واحد. في هذه الحالة، محفوظات التنفيذ أقصر قليلاً، لأن هناك حلقتين فقط، ويحتوي على 10 أحداث: OrchestratorStarted وExecutionStarted وTaskScheduled وTaskScheduled وOrchestratorCompleted وOrchestratorStarted وTaskCompleted وTaskCompleted وExecutionCompleted وOrchestratorCompleted.

إدارة مركز المهام

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

الإنشاء والحذف

ويتم إنشاء مركز مهام فارغ مع جميع الموارد المطلوبة تلقائيا في التخزين عند بدء تشغيل تطبيق دالة في المرة الأولى.

وإذا كنت تستخدم موفر Azure Storage الافتراضي، فلا يلزم تكوين إضافي. إلا، اتبع الإرشادات لتكوين موفري التخزين للتأكد من أن موفر التخزين يمكنه توفير موارد التخزين المطلوبة لمركز المهام والوصول إليها بشكل صحيح.

إشعار

لا يتم حذف مركز المهام تلقائيا عند إيقاف تطبيق الوظائف أو حذفه. ويجب حذف مركز المهام أو محتوياته أو حساب التخزين الذي يحتوي عليه يدويا إذا لم تعد ترغب في الاحتفاظ بهذه البيانات.

تلميح

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

تطبيقات وظائف متعددة

إذا كانت تطبيقات الدوال المتعددة تشترك في حساب تخزين، يجب تكوين كل تطبيق دالة باسم دوال المهام المنفصلة. ينطبق هذا المطلب أيضًا على فتحات التقسيم المرحلي: يجب تكوين كل فتحة تقسيم مرحلي باسم محور مهام فريد. يمكن أن يحتوي حساب تخزين واحد على عدة محاور مهام. ينطبق هذا التقييد بشكل عام على موفري التخزين الآخرين أيضاً.

يوضح الرسم التخطيطي التالي مركز مهام واحد لكل تطبيق دالة في حسابات تخزين Azure المشتركة والمخصصة.

Diagram showing shared and dedicated storage accounts.

إشعار

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

فحص المحتوى

توجد عدة طرق شائعة لفحص محتويات مركز المهام:

  1. ضمن تطبيق الوظائف، يوفر عنصر العميل أساليب للاستعلام عن مخزن المثيل. ولمعرفة المزيد حول أنواع الاستعلامات المدعومة، راجع مقالة إدارة المثيلات.
  2. بالمثل، تقدم واجهة برمجة تطبيقات HTTP طلبات REST للاستعلام عن حالة التنسيقات والكيانات. انظر مرجع HTTP API لمزيد من التفاصيل.
  3. يمكن لأداة مراقبة الوظائف المتينة فحص مراكز المهام وتقدم خيارات مختلفة للعرض المرئي.

وبالنسبة لبعض موفري التخزين، من الممكن أيضا فحص مركز المهام عن طريق الانتقال مباشرة إلى التخزين الأساسي:

  • إذا كنت تستخدم موفر تخزين Azure، يتم تخزين حالات المثيل في جدول المثيل وجدول المحفوظات الذي يمكن فحصه باستخدام أدوات مثل Azure Storage Explorer.
  • في حالة استخدام موفر تخزين MSSQL، يمكن استخدام استعلامات وأدوات SQL لفحص محتويات مركز المهام داخل قاعدة البيانات.

التمثيل في قاعدة المعارف

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

موفر Azure Storage

يشكل موفر Azure Storage مركز المهام في التخزين باستخدام المكونات التالية:

  • يقوم جدولا Azure بتخزين حالات المثيل.
  • تخزن Azure Queue واحدة رسائل النشاط.
  • تقوم قائمة أو أكثر من Azure Queues بتخزين رسائل المثيل. تمثل كل من قوائم انتظار التحكم هذه قسمًا تم تعيينه لمجموعة فرعية من جميع رسائل المثيل، بناءً على تجزئة معرف المثيل.
  • عدد قليل من حاويات الكائنات الثنائية كبيرة الحجم المستخدمة لتأجير الكائنات الثنائية كبيرة الحجم و/أو الرسائل الكبيرة.

على سبيل المثال، يحتوي مركز المهام المسمى xyz بـ PartitionCount = 4 على قوائم الانتظار والجداول التالية:

Diagram showing Azure Storage provider storage storage organization for 4 control queues.

وبعد ذلك، نصف هذه المكونات والدور الذي تلعبه بمزيد من التفصيل.

ولمزيد من المعلومات حول كيفية تمثيل مراكز المهام بواسطة موفر Azure Storage، راجع وثائق موفر Azure Storage.

موفر تخزين Netherite

يعمل Netherite على تقسيم جميع حالة مركز المهام إلى عدد محدد من الأقسام. وفي التخزين، يتم استخدام الموارد التالية:

  • حاوية Azure Storage blob واحدة التي تحتوي على جميع الكائنات الثنائية كبيرة الحجم، مجمعة حسب القسم.
  • جدول Azure واحد الذي يحتوي على مقاييس منشورة حول الأقسام.
  • مساحة اسم مراكز الأحداث Azure Event Hubs من أجل تسليم الرسائل بين الأقسام.

وعلى سبيل المثال، يتم تمثيل مركز المهام المسمى mytaskhub مع PartitionCount = 32 في التخزين كما يلي:

Diagram showing Netherite storage organization for 32 partitions.

إشعار

ويتم تخزين جميع حالة مركز المهام داخل x-storage حاوية الكائن الثنائي كبير الحجم. يحتوي الجدول DurableTaskPartitions ومساحة اسم EventHubs على بيانات زائدة عن الحاجة: إذا فقدت محتوياتها، يمكن استردادها تلقائيًا. لذلك، ليس من الضروري تكوين مساحة الاسم مراكز الأحداث Azure Event Hubs للاحتفاظ بالرسائل بعد وقت انتهاء الصلاحية الافتراضي.

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

ولمزيد من المعلومات حول مراكز المهام لموفر تخزين Netherite، راجع معلومات مركز المهام لموفر تخزين Netherite.

موفر تخزين MSSQL

يتم تخزين كل بيانات مركز المهام في قاعدة بيانات ارتباطية واحدة، باستخدام عدة جداول:

  • يخزن الجدولين dt.Instances وdt.History حالات المثيل.
  • يخزن الجدول dt.NewEvents رسائل المثيل.
  • يخزن الجدول dt.NewTasks رسائل النشاط.

Diagram showing MSSQL storage organization.

لتمكين مراكز مهام متعددة من التعايش بشكل مستقل في نفس قاعدة البيانات، يتضمن كل جدول عمودًا TaskHub كجزء من مفتاحه الأساسي. وعلى عكس الموفرين الآخرين، لا يمتلك موفر MSSQL مفهوم الأقسام.

لمعلومات أكثر حول مراكز المهام لموفر تخزين MSSQL، راجع معلومات مركز المهام لموفر تخزين Microsoft SQL (MSSQL).

أسماء لوحة الوصل للمهمة

تُعرّف مراكز المهام في تخزين Azure بواسطة اسم يتوافق مع هذه القواعد:

  • يحتوي على أحرف أبجدية رقمية فقط
  • يبدأ بحرف
  • لديه الحد الأدنى من طول 3 أحرف، والحد الأقصى 45 حرفاً

يتم تعريف اسم لوحة الوصل المهمة في host.js على الملف، كما هو موضح في المثال التالي:

host.json (الدوال 2.0)

{
  "version": "2.0",
  "extensions": {
    "durableTask": {
      "hubName": "MyTaskHub"
    }
  }
}

host.json (الدوال 1.x)

{
  "durableTask": {
    "hubName": "MyTaskHub"
  }
}

يمكن أيضًا تكوين مراكز المهام باستخدام إعدادات التطبيق، كما هو موضح فيhost.jsonملف المثال التالي:

host.json (الدوال 1.0)

{
  "durableTask": {
    "hubName": "%MyTaskHub%"
  }
}

host.json (الدوال 2.0)

{
  "version": "2.0",
  "extensions": {
    "durableTask": {
      "hubName": "%MyTaskHub%"
    }
  }
}

سيتم تعيين اسم مركز المهام إلى قيمة MyTaskHub إعداد التطبيق. يوضح local.settings.json التالي كيفية تعريف الإعداد MyTaskHub على أنه samplehubname:

{
  "IsEncrypted": false,
  "Values": {
    "MyTaskHub" : "samplehubname"
  }
}

إشعار

عند استخدام فتحات التوزيع، من الأفضل تكوين اسم مركز المهام باستخدام إعدادات التطبيق. وإذا كنت تريد التأكد من أن فتحة معينة تستخدم دائمًا مركز مهام معينًا، فاستخدم إعدادات تطبيق "فتحة ملصقة".

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

[FunctionName("HttpStart")]
public static async Task<HttpResponseMessage> Run(
    [HttpTrigger(AuthorizationLevel.Function, methods: "post", Route = "orchestrators/{functionName}")] HttpRequestMessage req,
    [DurableClient(TaskHub = "%MyTaskHub%")] IDurableOrchestrationClient starter,
    string functionName,
    ILogger log)
{
    // Function input comes from the request content.
    object eventData = await req.Content.ReadAsAsync<object>();
    string instanceId = await starter.StartNewAsync(functionName, eventData);

    log.LogInformation($"Started orchestration with ID = '{instanceId}'.");

    return starter.CreateCheckStatusResponse(req, instanceId);
}

إشعار

المثال السابق هو ل Durable Functions 2.x. بالنسبة إلى Durable Functions 1.x، يتعين عليك استخدام DurableOrchestrationContext بدلاً من IDurableOrchestrationContext. لمزيدٍ من المعلومات حول الاختلافات بين الإصدارات، راجع مقالة إصدارات Durable Functions.

إشعار

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

يجب أن تبدأ أسماء مركز المهام بحرف وتتكون من أحرف وأرقام فقط. إذا لم يتم تحديد، سيتم استخدام اسم مركز المهام افتراضي كما هو موضح في الجدول التالي:

إصدار الملحق الدائم الاسم الافتراضي لمركز المهام
2.x عند النشر في Azure، يتم اشتقاق اسم مركز المهام من اسم تطبيق الدوال. عند التشغيل خارج Azure، يكون اسم المركز الافتراضي للمهام TestHubName هو.
1.x اسم مركز المهام الافتراضي لكافة البيئات هوDurableFunctionsHub.

لمزيد من المعلومات حول الاختلافات بين الإصدارات، راجع المقالة إصدارات الدالة الدائمة.

إشعار

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

الخطوات التالية