البرنامج التعليمي: تشغيل عبء عمل متوازٍ مع Azure Batch باستخدام واجهة برمجة تطبيقات .NET

استخدم Azure Batch لتشغيل مهام الحوسبة المتوازية وعالية الأداء (HPC) على نطاق واسع بكفاءة في Azure. يستعرض هذا البرنامج التعليمي مثال C # لتشغيل عبء عمل متوازٍ باستخدام Batch. ستتعلم سير العمل الشائع لتطبيق Batch وطريقة التفاعل برمجياً مع موارد Batch وStorage.

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

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

إذا لم يكن لديك اشتراك في Azure، فأنشئ حساب Azure مجاني قبل أن تبدأ.

المتطلبات الأساسية

تسجيل الدخول إلى Azure

سجل الدخول إلى مدخل Azure.

الحصول على حزمة التطبيق

استخدم بوابة Azure لإضافة ffmpeg إلى حساب Batch الخاص بك باعتباره حزمة تطبيق. تساعدك حزم التطبيقات في إدارة تطبيقات المهام وتوزيعها على عقد الحوسبة في مجموعتك.

  1. في مدخل Microsoft Azure، انقر فوق More services>Batch accounts، وحدد اسم حساب Batch الخاص بك.

  2. النقر على Applications>Add.

    Screenshot of the Applications section of the batch account.

  3. أدخل ffmpeg في حقل معرف التطبيق، وإصدار حزمة من 4.3.1 في حقل الإصدار . حدد ملف ffmpeg zip الذي قمت بتنزيله، ثم حدد إرسال. أُضيفت حزمة تطبيق ffmpeg إلى حساب Batch الخاص بك.

    Screenshot of the ID and version fields in the Add application section.

الحصول على بيانات اعتماد الحساب

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

  1. حدد All services>Batch accounts، ثم حدد اسم حساب Batch الخاص بك.

  2. لمشاهدة بيانات اعتماد Batch، حدد Keys. انسخ قيم حساب Batch وعنوان URL ومفتاح الوصول الأساسي إلى محرر نص.

  3. لمشاهدة اسم حساب التخزين ومفاتيحه، حدد حساب التخزين. انسخ قيم اسم حساب التخزين وKey1إلى محرر نص.

تنزيل عينة التطبيق وتشغيلها

تنزيل التطبيق النموذج

قم بتنزيل أو نسخ نموذج التطبيق من GitHub. لنسخ نموذج مستودع التطبيق باستخدام عميل Git، استخدم الأمر التالي:

git clone https://github.com/Azure-Samples/batch-dotnet-ffmpeg-tutorial.git

انتقل إلى الدليل الذي يحتوي على ملف حل Visual Studio BatchDotNetFfmpegTutorial.sln.

افتح ملف الحل في Visual Studio، وقم بتحديث سلاسل بيانات الاعتماد في Program.cs بالقيم التي حصلت عليها لحساباتك. على سبيل المثال:

// Batch account credentials
private const string BatchAccountName = "yourbatchaccount";
private const string BatchAccountKey  = "xxxxxxxxxxxxxxxxE+yXrRvJAqT9BlXwwo1CwF+SwAYOxxxxxxxxxxxxxxxx43pXi/gdiATkvbpLRl3x14pcEQ==";
private const string BatchAccountUrl  = "https://yourbatchaccount.yourbatchregion.batch.azure.com";

// Storage account credentials
private const string StorageAccountName = "yourstorageaccount";
private const string StorageAccountKey  = "xxxxxxxxxxxxxxxxy4/xxxxxxxxxxxxxxxxfwpbIC5aAWA8wDu+AFXZB827Mt9lybZB1nUcQbQiUrkPtilK5BQ==";

إشعار

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

التأكد أيضاً من أن مرجع حزمة تطبيق ffmpeg في الحل يتطابق مع معرف وإصدار حزمة ffmpeg التي حملتها إلى حساب Batch الخاص بك. على سبيل المثال، ffmpeg و 4.3.1.

const string appPackageId = "ffmpeg";
const string appPackageVersion = "4.3.1";

إنشاء النموذج وتشغيله داخلياً

إنشاء التطبيق وتشغيله في Visual Studio، أو في سطر الأوامر باستخدام الأمرين dotnet build وdotnet run. بعد تشغيل التطبيق، يرجى مراجعة الكود لمعرفة ما يفعله كل جزء من التطبيق. على سبيل المثال: في Visual Studio:

  1. انقر بزر الماوس الأيمن فوق الحل في مستكشف الحلول وحدد Build Solution.

  2. تأكد من استعادة أي حزم NuGet، إذا تمت مطالبتك. عند الحاجة إلى تنزيل الحزم المفقودة، فيجب التأكد من تثبيت NuGet Package Manager.

  3. قم بتشغيل الحل. عند تشغيل التطبيق النموذجي، يكون إخراج وحدة التحكم مشابهاً لما يلي. أثناء التنفيذ، تواجه توقفاً مؤقتاً عند Monitoring all tasks for 'Completed' state, timeout in 00:30:00... أثناء بدء عقد حساب التجمع.

Sample start: 11/19/2018 3:20:21 PM

Container [input] created.
Container [output] created.
Uploading file LowPriVMs-1.mp4 to container [input]...
Uploading file LowPriVMs-2.mp4 to container [input]...
Uploading file LowPriVMs-3.mp4 to container [input]...
Uploading file LowPriVMs-4.mp4 to container [input]...
Uploading file LowPriVMs-5.mp4 to container [input]...
Creating pool [WinFFmpegPool]...
Creating job [WinFFmpegJob]...
Adding 5 tasks to job [WinFFmpegJob]...
Monitoring all tasks for 'Completed' state, timeout in 00:30:00...
Success! All tasks completed successfully within the specified timeout period.
Deleting container [input]...

Sample end: 11/19/2018 3:29:36 PM
Elapsed time: 00:09:14.3418742

الانتقال إلى حساب Batch في مدخل Microsoft Azure لمراقبة المجموعة وعقد الحساب والوظيفة والمهام. على سبيل المثال، لمشاهدة خريطة التمثيل اللوني لعقد الحوسبة في مجموعتك، النقر على المجموعات >WinFFmpegPool.

عند تشغيل المهام، تكون خريطة التمثيل اللوني مشابهة لما يلي:

Screenshot of the pool heat map in the Azure portal.

يبلغ وقت التنفيذ المعتاد حوالي 10 دقائق عند تشغيل التطبيق في تهيئته الافتراضية. يستغرق إنشاء المجموعة معظم الوقت.

استرجاع ملفات الإخراج

يمكنك استخدام مدخل Azure لتنزيل ملفات MP3 الناتجة عن مهام ffmpeg.

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

Download output file

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

مراجعة الرمز

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

مصادقة عملاء Blob وBatch

للتفاعل مع حساب التخزين المرتبط، يستخدم التطبيق Azure Storage Client Library لـ .NET. يقوم بإنشاء مرجع للحساب باستخدام CloudStorageAccount، مصادقة باستخدام مصادقة المفتاح المشترك. ثم إنشاء CloudBlobClient.

// Construct the Storage account connection string
string storageConnectionString = String.Format("DefaultEndpointsProtocol=https;AccountName={0};AccountKey={1}",
                                StorageAccountName, StorageAccountKey);

// Retrieve the storage account
CloudStorageAccount storageAccount = CloudStorageAccount.Parse(storageConnectionString);

CloudBlobClient blobClient = storageAccount.CreateCloudBlobClient();

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

BatchSharedKeyCredentials sharedKeyCredentials = new BatchSharedKeyCredentials(BatchAccountUrl, BatchAccountName, BatchAccountKey);

using (BatchClient batchClient = BatchClient.Open(sharedKeyCredentials))
...

تحميل ملفات الإدخال

يمرر التطبيق كائن الـ blobClient إلى أسلوب CreateContainerIfNotExistAsync لإنشاء حاوية تخزين لملفات الإدخال (تنسيق MP4) وحاوية لإخراج المهمة.

CreateContainerIfNotExistAsync(blobClient, inputContainerName);
CreateContainerIfNotExistAsync(blobClient, outputContainerName);

بعد ذلك، يتم تحميل الملفات إلى حاوية الإدخال من مجلد InputFiles المحلي. يتم تعريف الملفات المخزنة على أنها كائنات مجمعة ResourceFile والتي يمكن لـ Batch تنزيلها لاحقاً إلى عقد الحساب.

هناك طريقتان في Program.cs تشاركان في تحميل الملفات:

  • UploadFilesToContainerAsync: إرجاع مجموعة من ResourceFile الكائنات واستدعاءات UploadResourceFileToContainerAsync داخلية لتحميل كل ملف يتم تمريره في المعلمة inputFilePaths .
  • UploadResourceFileToContainerAsync: تحميل كل ملف على هيئة blob إلى حاوية الإدخال. بعد تحميل الملف، يحصل على توقيع وصول مشترك (SAS) للكائن الثنائي كبير الحجم ويعيد كائنا ResourceFile لتمثيله.
string inputPath = Path.Combine(Environment.CurrentDirectory, "InputFiles");

List<string> inputFilePaths = new List<string>(Directory.GetFileSystemEntries(inputPath, "*.mp4",
    SearchOption.TopDirectoryOnly));

List<ResourceFile> inputFiles = await UploadFilesToContainerAsync(
  blobClient,
  inputContainerName,
  inputFilePaths);

للحصول على تفاصيل حول رقع الملفات كنقاط كبيرة إلى حساب تخزين باستخدام .NET، يرجى مراجعة الرفع والتنزيل وإدراج البيانات الثنائية الكبيرة باستخدام .NET .

قم بإنشاء مجموعة من العقد الحسابية

بعد ذلك، يُنشئ النموذج مجموعة من عُقد الحساب في حساب Batch مع استدعاء CreatePoolIfNotExistAsync. تستخدم هذه الطريقة المحددة طريقة BatchClient.PoolOperations.CreatePool لتعيين عدد العقد وحجم الجهاز الظاهري وتكوين التجمع. هنا، يحدد كائن VirtualMachineConfigurationImageReference لصورة Windows Server المنشورة في Azure Marketplace. Batch يدعم مجموعة كبيرة من صور VM في Azure Marketplace، بالإضافة إلى صور VM المخصصة.

يتم تحديد عدد العقد وحجم VM باستخدام ثوابت محددة. تدعم المجموعة العقد المخصصة والعقد الموضعية، ويمكنك استخدام أحدهما أو كليهما في مجموعاتك. تُحجز العقد المخصصة للمجموعة الخاص بك. يتم تقديم العقد الموضعية بسعر مخفض من سعة VM الزائدة في Azure. تصبح العقد الموضعية غير متوفرة إذا لم يكن لدى Azure سعة كافية. يُنشئ النموذج افتراضياً مجموعة تحتوي على 5 عقد موضعية فقط بحجم Standard_A1_v2.

إشعار

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

يُنشر تطبيق ffmpeg على عُقد الحوسبة عن طريق إضافة ApplicationPackageReference إلى تكوين التجمع.

تُرسل طريقة CommitAsync بإرسال مستودع التخزين إلى خدمة Batch.

ImageReference imageReference = new ImageReference(
    publisher: "MicrosoftWindowsServer",
    offer: "WindowsServer",
    sku: "2016-Datacenter-smalldisk",
    version: "latest");

VirtualMachineConfiguration virtualMachineConfiguration =
    new VirtualMachineConfiguration(
    imageReference: imageReference,
    nodeAgentSkuId: "batch.node.windows amd64");

pool = batchClient.PoolOperations.CreatePool(
    poolId: poolId,
    targetDedicatedComputeNodes: DedicatedNodeCount,
    targetLowPriorityComputeNodes: LowPriorityNodeCount,
    virtualMachineSize: PoolVMSize,
    virtualMachineConfiguration: virtualMachineConfiguration);

pool.ApplicationPackageReferences = new List<ApplicationPackageReference>
    {
    new ApplicationPackageReference {
    ApplicationId = appPackageId,
    Version = appPackageVersion}};

await pool.CommitAsync();  

قم بإنشاء وظيفة

تحدد وظيفة Batch مخزناً لتشغيل المهام عليه وإعدادات اختيارية مثل الأولوية والجدول الزمني للعمل. يُنشئ النموذج وظيفة باستدعاء CreateJobAsync. تستخدم هذه الطريقة المحددة طريقة BatchClient.JobOperations.CreateJob لإنشاء وظيفة في مجموعتك.

تُرسل طريقة CommitAsync الوظيفة إلى خدمة المجموعة. في البداية المهمة ليس لها مهام.

CloudJob job = batchClient.JobOperations.CreateJob();
job.Id = JobId;
job.PoolInformation = new PoolInformation { PoolId = PoolId };

await job.CommitAsync();

إنشاء مهام

ينشئ النموذج مهام في الوظيفة باستدعاء طريقة AddTasksAsync، والتي تُنشئ قائمة بكائنات CloudTask. يُشغل كل CloudTask ffmpeg لمعالجة كائن إدخال ResourceFile باستخدام خاصية CommandLine. سبق تثبيت ffmpeg على كل عقدة عند إنشاء المجموعة. هنا، يقوم سطر الأوامر بتشغيل ffmpeg لتحويل كل ملف إدخال MP4 (فيديو) إلى ملف MP3 (صوتي).

يقوم النموذج بإنشاء كائن OutputFile لملف MP3 بعد تشغيل سطر الأوامر. تُحمل ملفات إخراج كل مهمة (ملف واحد، في هذه الحالة) إلى حاوية في حساب التخزين المرتبط، باستخدام خاصية OutputFiles الخاصة بالمهمة. في نموذج التعليمات البرمجية سابقاً، تم الحصول على عنوان URL لتوقيع الوصول المشترك (outputContainerSasUrl) لتوفير إذن وصول الإضافة والحذف إلى حاوية الإخراج. تُلاحظ الشروط المعينة على كائن outputFile. يُحمل ملف ناتج من مهمة إلى الحاوية فقط بعد اكتمال المهمة بنجاح (OutputFileUploadCondition.TaskSuccess). يرجى مراجعة نموذج الشفرة الكامل على GitHub للحصول على مزيد من تفاصيل التنفيذ.

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

استبدل مسار ملف الملف القابل للتنفيذ باسم الإصدار الذي قمت بتنزيله. يستخدم نموذج التعليمات البرمجية هذا المثال ffmpeg-4.3.1-2020-11-08-full_build.

 // Create a collection to hold the tasks added to the job.
List<CloudTask> tasks = new List<CloudTask>();

for (int i = 0; i < inputFiles.Count; i++)
{
    string taskId = String.Format("Task{0}", i);

    // Define task command line to convert each input file.
    string appPath = String.Format("%AZ_BATCH_APP_PACKAGE_{0}#{1}%", appPackageId, appPackageVersion);
    string inputMediaFile = inputFiles[i].FilePath;
    string outputMediaFile = String.Format("{0}{1}",
        System.IO.Path.GetFileNameWithoutExtension(inputMediaFile),
        ".mp3");
    string taskCommandLine = String.Format("cmd /c {0}\\ffmpeg-4.3.1-2020-09-21-full_build\\bin\\ffmpeg.exe -i {1} {2}", appPath, inputMediaFile, outputMediaFile);

    // Create a cloud task (with the task ID and command line)
    CloudTask task = new CloudTask(taskId, taskCommandLine);
    task.ResourceFiles = new List<ResourceFile> { inputFiles[i] };

    // Task output file
    List<OutputFile> outputFileList = new List<OutputFile>();
    OutputFileBlobContainerDestination outputContainer = new OutputFileBlobContainerDestination(outputContainerSasUrl);
    OutputFile outputFile = new OutputFile(outputMediaFile,
       new OutputFileDestination(outputContainer),
       new OutputFileUploadOptions(OutputFileUploadCondition.TaskSuccess));
    outputFileList.Add(outputFile);
    task.OutputFiles = outputFileList;
    tasks.Add(task);
}

// Add tasks as a collection
await batchClient.JobOperations.AddTaskAsync(jobId, tasks);
return tasks

مراقبة المهام

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

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

TaskStateMonitor taskStateMonitor = batchClient.Utilities.CreateTaskStateMonitor();
try
{
    await taskStateMonitor.WhenAll(addedTasks, TaskState.Completed, timeout);
}
catch (TimeoutException)
{
    batchClient.JobOperations.TerminateJob(jobId);
    Console.WriteLine(incompleteMessage);
    return false;
}
batchClient.JobOperations.TerminateJob(jobId);
 Console.WriteLine(completeMessage);
...

تنظيف الموارد

بعد تشغيل المهام، يحذف التطبيق تلقائياً حاوية تخزين الإدخال التي أنشأها، ويمنحك خيار حذف مجموعة Batch والوظيفة. لكل من فئتي BatchClient:JobOperations وPoolOperations طرق حذف متطابقة، والتي تُستدعى في حالة تأكيد الحذف. على الرغم من أنك لا تتكلف رسوماً مقابل الأعمال والمهام نفسها، إلا أنك تتحمل تكلفة العقد الحسابية. وبالتالي، نوصي بتخصيص تجمعات حسب الحاجة فقط. عند حذف التجمع، يتم حذف كافة إخراج المهام على العقد. ومع ذلك، تبقى ملفات الإدخال والإخراج في حساب التخزين.

عند عدم الحاجة، احذف مجموعة الموارد وحساب الدفعة وحساب التخزين. للقيام بذلك في مدخل Microsoft Azure، تحديد مجموعة الموارد لحساب Batch والنقر على Deleteresource group.

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

في هذا البرنامج التعليمي، نتعلم طريقة القيام بما يأتي:

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

لمزيد من الأمثلة على استخدام واجهة برمجة تطبيقات .NET لجدولة أحمال عمل Batch ومعالجتها، راجع نماذج Batch C# على GitHub.