أول Playbook لك: تثبيت البرامج (مثل Nginx و Node) آلياً بلغة YAML

دقائق القراءة: 5

أول Playbook لك: تثبيت البرامج (مثل Nginx و Node.js) آلياً بلغة YAML

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

الفكرة الجوهرية في Playbook هي وصف “الحالة المطلوبة” للخادم بدلاً من تنفيذ أوامر عشوائية. أنت لا تقول: شغّل هذا الأمر ثم ذاك فقط، بل تقول: أريد أن تكون حزمة Nginx مثبّتة، وأريد أن تكون خدمة الويب عاملة، وأريد تثبيت Node.js بنفس السلوك على كل الخوادم المستهدفة.

هذا الأسلوب يجعل أتمتة الإعدادات متوافقة تماماً مع مفاهيم Infrastructure as Code، كما يسهّل دمجها لاحقاً ضمن مسارات CI/CD. وإذا كنت تراجع أساسيات الأتمتة الشاملة، فمقال ما هو DevOps؟ ولماذا تدفع الشركات ثروات لمهندسي الأتمتة السحابية؟ يضع هذا كله في سياقه العملي.

ما الذي نحتاجه قبل كتابة أول Playbook؟

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

لا تشغّل الأتمتة على المستخدم root مباشرة إلا عند الضرورة القصوى. الأفضل استخدام مستخدم إداري محدود مع become لتقليل أثر أي خطأ أو تسريب مفاتيح.

هيكل ملف Playbook وكيف يقرأه Ansible

ملف Playbook مكتوب بلغة YAML، وهي صيغة نصية سهلة القراءة، تعتمد على المسافات البادئة بدقة. كل قسم داخل الملف يعبّر عن مجموعة خوادم مستهدفة ومجموعة مهام يجب تنفيذها عليها.

في السيناريو التالي سنبني ملفاً يثبت Nginx و Node.js على خوادم Ubuntu، مع تحديث فهرس الحزم، وضمان تشغيل خدمة Nginx تلقائياً بعد الإقلاع.

مثال عملي كامل

---
- name: Install Nginx and Node.js on web servers
  hosts: webservers
  become: true

  vars:
    node_package: nodejs
    nginx_package: nginx

  tasks:
    - name: Update apt package cache
      apt:
        update_cache: yes
        cache_valid_time: 3600

    - name: Install Nginx
      apt:
        name: "{{ nginx_package }}"
        state: present

    - name: Install Node.js
      apt:
        name: "{{ node_package }}"
        state: present

    - name: Ensure Nginx service is enabled
      service:
        name: nginx
        enabled: true

    - name: Ensure Nginx service is running
      service:
        name: nginx
        state: started

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

فهم كل جزء من الملف بشكل هندسي

قسم hosts

السطر الخاص بـ hosts يحدد المجموعة المستهدفة من ملف Inventory. إذا كانت لديك بيئة staging وأخرى production، فاختيار المجموعة الصحيحة هنا يمنع تطبيق الإعدادات على الخوادم الخطأ.

قسم become

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

قسم tasks

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

  • تحديث فهرس الحزم يضمن أن المستودعات متزامنة.
  • تثبيت Nginx يوفر طبقة reverse proxy أو خادم ويب أمامي.
  • تثبيت Node.js يجهّز بيئة تشغيل التطبيقات الخلفية.
  • تفعيل الخدمة يضمن استمرارية التشغيل بعد إعادة الإقلاع.

كيف تشغّل الملف عملياً؟

بعد حفظ الملف مثلاً باسم install-nginx-node.yml، يمكنك تشغيله عبر الأمر التالي:

ansible-playbook -i inventory.ini install-nginx-node.yml

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

ansible-playbook -i inventory.ini install-nginx-node.yml --check

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

لا تبدأ تشغيل أي Playbook جديد مباشرة على بيئة production. جرّبه أولاً على خادم تجريبي أو بيئة staging لتجنب downtime أو تثبيت إصدارات غير متوافقة.

لماذا هذا مهم في معمارية النشر الحديثة؟

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

هذا ينسجم مباشرة مع عالم ما هو الـ CI/CD؟ ولماذا نؤتمت عمليات اختبار ونشر الأكواد؟، لأن خادم التطبيق يجب أن يكون قابلاً لإعادة الإنشاء وليس كياناً غامضاً يعتمد على ذاكرة المسؤول التقني. ومع توسع المشروع، يمكن أن يصبح هذا Playbook جزءاً من Pipeline ينفذ بعد نجاح الاختبارات أو قبل النشر.

وإذا كنت تعمل في بيئات هجينة بين الخوادم والحاويات، فستلاحظ أن منطق الأتمتة نفسه يتكرر. الفرق فقط أن بعض الإعدادات ستوضع لاحقاً في Dockerfile أو docker-compose.yml. لهذا يفيدك أيضاً الرجوع إلى كتابة أول ملف docker-compose.yml خطوة بخطوة لفهم كيف تتقاطع لغة YAML في أكثر من أداة.

أفضل الممارسات عند بناء Playbook احترافي

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

ومع نضج البنية لديك، يمكن إدخال هذه الملفات في مسارات تنفيذ آلية باستخدام مقدمة في GitHub Actions: كتابة أول مسار عمل (Workflow) حتى تنتقل من الإدارة اليدوية إلى التشغيل المنهجي القابل للتكرار.

الخلاصة

أول Playbook ليس مجرد ملف لتثبيت Nginx و Node.js، بل هو أول انتقال حقيقي من إدارة الخوادم بالأوامر الفردية إلى إدارة البنية بوصفٍ برمجي واضح وقابل للتكرار. كل سطر في هذا الملف يقلل الاعتماد على الذاكرة البشرية، ويرفع الثبات، ويسهّل التوسع، ويقربك من بيئة DevOps احترافية.

ابدأ بملف صغير، اختبره جيداً، ثم طوّره تدريجياً ليشمل مستخدمين، ملفات إعداد، خدمات، وجدران نارية. عندها ستدرك أن الأتمتة ليست رفاهية، بل أساس هندسي لأي منصة تريد أن تنمو دون فوضى.

8 comments

اترك تعليقاً

لن يتم نشر عنوان بريدك الإلكتروني. الحقول الإلزامية مشار إليها بـ *