كنا نغرق في بحر من التنبيهات: كيف أنقذتنا ‘المراقبة القائمة على الأعراض’ مع Prometheus من جحيم الإنذارات عديمة الجدوى؟

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

هذا السيرفر الـ CPU تبعه وصل 95%، وهاي الخدمة استهلاك الـ RAM فيها نطّ للسما، وهذا الـ pod في Kubernetes بعيد تشغيل حاله للمرة العاشرة. قنوات الـ Slack تبعتنا ولّعت باللون الأحمر، والكل بسأل: “يا جماعة الخير، شو القصة؟ وين المشكلة بالضبط؟”.

قضينا ساعات ونحن نركض وراء كل تنبيه، مثل اللي بحاول يطفي حرايق صغيرة متفرقة، وفي الآخر اكتشفنا إنه ما في حريق أصلاً. كان في عملية Batch Job مجدولة بتشتغل بالليل وبتستهلك موارد عالية (وهذا طبيعي)، وبعض الخدمات كانت بتعمل Scale-up بشكل تلقائي (وهذا صحي). كل التنبيهات هاي كانت “صحيحة تقنياً” بس “عديمة الجدوى عملياً”. كانت ضجيج، حكي فاضي بصحّي المهندس المناوب نص الليل على الفاضي.

في هذيك الليلة، واحنا مرهقين ومحبطين، واحد من المهندسين الجداد حكى جملة بسيطة بس عبقرية: “طيب… هل المستخدمين بشتكوا من شي؟”. ساد الصمت للحظة. الجواب كان “لأ”. ومن هنا، بدأت رحلتنا لإعادة التفكير في كل فلسفة المراقبة لدينا، رحلة أنقذتنا من جحيم الإنذارات التافهة وقادتنا إلى مفهوم “المراقبة القائمة على الأعراض”.

الفوضى الخلاّقة: ما هي “المراقبة القائمة على الأسباب” (Cause-Based Monitoring)؟

اللي كنا بنعمله، واللي للأسف كثير فرق بتعمله، اسمه المراقبة القائمة على الأسباب. الفكرة بسيطة ومنطقية ظاهرياً: راقب كل الأسباب المحتملة للمشاكل.

  • استخدام المعالج (CPU Usage)
  • استخدام الذاكرة (RAM Usage)
  • مساحة القرص (Disk Space)
  • ضغط الشبكة (Network I/O)

بنحط تنبيه على كل مؤشر من هدول: “إذا وصل استخدام المعالج إلى 90% لمدة 5 دقائق، أرسل تنبيهًا حرجًا!”. يبدو الأمر سليمًا، أليس كذلك؟ المشكلة إنه هذا النهج يخلط بين “الارتباط” و”السببية”.

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

هذا النهج يؤدي حتمًا إلى ما يسمى بـ “إرهاق التنبيهات” (Alert Fatigue). مع كثرة الإنذارات الكاذبة، يبدأ الفريق تدريجيًا بتجاهل التنبيهات، وحين يأتي التنبيه الحقيقي الذي يشير لمشكلة حقيقية، قد يمر مرور الكرام وسط الضجيج. وهذا أخطر شيء ممكن يصير.

الهدوء الذي يسبق العاصفة الحقيقية: مدخل إلى “المراقبة القائمة على الأعراض” (Symptom-Based Monitoring)

تخيل أنك طبيب. هل تستدعي مريضك في منتصف الليل لأن درجة حرارته ارتفعت 0.1 درجة؟ أم لأن نبضه زاد 5 نبضات في الدقيقة أثناء صعوده الدرج؟ بالطبع لا. أنت كطبيب تهتم بالأعراض التي تؤثر على حياة المريض: صداع شديد، صعوبة في التنفس، ألم مستمر. هذه هي الأعراض.

المراقبة القائمة على الأعراض تطبق نفس المنطق على أنظمتنا. بدلاً من أن نسأل “هل المعالج مشغول؟”، نسأل أسئلة أكثر أهمية:

  • هل الخدمة متاحة؟ (هل ترد على الطلبات بنجاح؟)
  • هل الخدمة سريعة؟ (هل ترد على الطلبات ضمن زمن مقبول؟)
  • هل الخدمة صحيحة؟ (هل ترد بأخطاء كثيرة؟)
  • هل الخدمة قادرة على تلبية الطلب؟ (هل تصل إلى أقصى سعة لها وترفض طلبات جديدة؟)

هذه هي الأعراض التي يشعر بها المستخدم مباشرة. ارتفاع المعالج مجرد تفصيل داخلي قد يؤدي لأحد هذه الأعراض، وقد لا يؤدي. هدفنا هو أن يرن جرس الإنذار فقط عندما يكون هناك “ألم” حقيقي يشعر به المستخدم.

Prometheus في قلب المعركة: كيف نطبق هذا المفهوم عملياً؟

حسناً يا أبو عمر، كلامك جميل ونظري. كيف نطبقه “من الآخر”؟ هنا يأتي دور أدوات مثل Prometheus، التي تم تصميمها خصيصًا لدعم هذا النوع من الفلسفة. العملية تتم على ثلاث خطوات رئيسية.

الخطوة الأولى: تحديد مؤشرات مستوى الخدمة (SLIs)

الـ SLI أو Service Level Indicator هو مقياس كمي لأحد جوانب الخدمة التي تقدمها. إنه ترجمة “العَرَض” إلى رقم يمكن قياسه. لخدمة ويب نموذجية، أهم ثلاثة SLIs هي:

  • الإتاحة (Availability): نسبة الطلبات الناجحة من إجمالي الطلبات. على سبيل المثال، نسبة الطلبات التي لا تُرجع خطأ من عائلة 5xx.
  • الكمون (Latency): نسبة الطلبات التي تم الرد عليها أسرع من عتبة معينة. على سبيل المثال، 95% من الطلبات يتم الرد عليها في أقل من 500 مللي ثانية.
  • معدل الأخطاء (Error Rate): هو الوجه الآخر للإتاحة، أي نسبة الطلبات التي تفشل.

مع Prometheus، يمكنك حساب هذه المؤشرات بسهولة باستخدام لغة الاستعلام PromQL. على سبيل المثال، لحساب معدل الأخطاء لخدمة معينة خلال آخر 5 دقائق:

# SLI: نسبة الأخطاء (5xx) خلال آخر 5 دقائق
sum(rate(http_requests_total{job="my-app", code=~"5.."}[5m]))
/
sum(rate(http_requests_total{job="my-app"}[5m]))

الخطوة الثانية: وضع أهداف مستوى الخدمة (SLOs)

الـ SLO أو Service Level Objective هو الهدف الذي تضعه للـ SLI الخاص بك على مدى فترة زمنية. الـ SLO هو وعدك لنفسك ولمستخدميك.

  • “يجب أن تكون نسبة الإتاحة لخدمة تسجيل الدخول 99.9% على مدار 30 يومًا.”
  • “يجب أن يتم الرد على 99% من طلبات البحث في أقل من 300ms.”

الـ SLOs هي التي تحدد ما هو “الطبيعي” وما هو “المشكلة”. بدونها، تظل الأرقام مجرد أرقام.

أحد المفاهيم المرتبطة بالـ SLOs هو “ميزانية الخطأ” (Error Budget). إذا كان هدف الإتاحة لديك 99.9%، فهذا يعني أن لديك “ميزانية” قدرها 0.1% من الوقت لتكون فيها الخدمة غير متاحة أو تُرجع أخطاء. هذه الميزانية تسمح لك بالأخطاء الحتمية، وبالصيانة، وبإطلاق الميزات الجديدة التي قد تحمل بعض المخاطر.

الخطوة الثالثة: بناء قواعد تنبيه ذكية (Alerting Rules)

هنا يحدث السحر. بدلاً من التنبيه على ارتفاع المعالج، نقوم الآن بإنشاء تنبيهات تطلق فقط عندما نكون في خطر “خرق الـ SLO”، أي عندما نستهلك “ميزانية الخطأ” بسرعة كبيرة جدًا.

التنبيه لم يعد يقول “المعالج 90%”. أصبح يقول: “معدل الأخطاء الحالي سيؤدي إلى استهلاك كامل ميزانية الخطأ المخصصة للشهر في غضون 4 ساعات فقط!”.

هل ترى الفرق؟ التنبيه الثاني يصرخ: “هناك مشكلة حقيقية تؤثر على المستخدمين، وتحتاج إلى تدخل فوري!”.

إليك مثال لقاعدة تنبيه في Prometheus تفعل ذلك بالضبط. لنفترض أن الـ SLO هو 99.9% إتاحة على مدار 30 يومًا. هذا يمنحنا ميزانية خطأ قدرها 0.1%. يمكننا إنشاء تنبيه يتحقق مما إذا كان معدل الخطأ على مدار الساعة الماضية يستهلك هذه الميزانية بمعدل ينذر بالخطر.

# ملف قواعد تنبيه Prometheus (alert.rules.yml)
groups:
- name: MyWebAppSLOAlerts
  rules:
  - alert: HighErrorRateBudgetBurn
    # هذا التعبير الرياضي معقد قليلاً، لكنه يقارن معدل الخطأ الحالي
    # بمعدل استهلاك الميزانية المسموح به.
    expr: |
      sum(rate(http_requests_total{job="my-app", code=~"5.."}[1h]))
      / 
      sum(rate(http_requests_total{job="my-app"}[1h]))
      > (14.4 * 0.001) # 14.4 هو معامل استهلاك لـ 30 يومًا، و 0.001 هو ميزانية الخطأ (1-0.999)
    for: 10m
    labels:
      severity: critical
    annotations:
      summary: "استهلاك سريع لميزانية الخطأ في تطبيق 'my-app'"
      description: |
        معدل الأخطاء في تطبيق '{{ $labels.job }}' مرتفع جدًا ({{ $value | humanizePercent }}).
        إذا استمر هذا المعدل، فسنخترق هدف الإتاحة 99.9% لهذا الشهر.
        هذا تنبيه حقيقي ويستدعي التدخل الفوري!

باستخدام هذه القاعدة، لن تستيقظ أبدًا في منتصف الليل بسبب ارتفاع مؤقت في الأخطاء. ستستيقظ فقط عندما يكون هناك نمط خطير ومستمر من الأخطاء يهدد التزامك تجاه المستخدمين.

نصائح من قلب الميدان (من خبرة أبو عمر)

هذا التحول ليس سهلاً دائماً، وهذه بعض الدروس التي تعلمناها بالطريقة الصعبة:

  1. ابدأ بالتدريج وبشكل بسيط: لا تحاول تطبيق هذا على كل خدماتك دفعة واحدة. اختر خدمة واحدة حرجة، حدد لها SLI/SLO بسيط (مثل الإتاحة)، واضبط تنبيهاتك. تعلم وكرر.
  2. المراقبة متعددة الطبقات: هذا لا يعني أننا نتوقف عن جمع بيانات المعالج والذاكرة! على العكس، هذه البيانات تصبح ذهباً عند محاولة تشخيص المشكلة بعد أن يأتيك تنبيه قائم على الأعراض. الفرق هو أننا لا نُطلق تنبيهات عليها مباشرة. التنبيهات القائمة على الأعراض هي لإيقاظك، والبيانات القائمة على الأسباب هي لمساعدتك في التحقيق.
  3. التوثيق هو مفتاح النجاة: يجب أن يحتوي كل تنبيه على رابط لـ “Runbook” أو “Playbook”. هذا المستند يشرح بالضبط ما هي الخطوات الأولى التي يجب على المهندس اتخاذها لتشخيص المشكلة. لا تترك المهندس المناوب وحيداً في العتمة.
  4. اضبط النوافذ الزمنية بحكمة: يمكنك إنشاء تنبيهات متعددة لنفس الـ SLO. تنبيه حرج (Critical) لاستهلاك الميزانية بسرعة على مدى ساعة، وتنبيه تحذيري (Warning) لاستهلاكها ببطء على مدى 24 ساعة.
  5. لا تخف من التعديل: قواعد التنبيه ليست منقوشة على الحجر. إذا كان التنبيه مزعجًا، قم بتعديله. إذا فاتتك مشكلة، اسأل نفسك: “ما هو التنبيه الذي كان يجب أن يكون موجودًا؟” وقم بإنشائه. إنها عملية تحسين مستمرة.

الخلاصة: من الفوضى إلى التركيز 🎯

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

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

أبو عمر

سجل دخولك لعمل نقاش تفاعلي

كافة المحادثات خاصة ولا يتم عرضها على الموقع نهائياً

آراء من النقاشات

لا توجد آراء منشورة بعد. كن أول من يشارك رأيه!

آخر المدونات

التوسع والأداء العالي والأحمال

كانت قاعدة بياناتنا تستغيث: كيف أنقذنا نمط ‘Cache-Aside’ من جحيم اختناق القراءات؟

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

30 أبريل، 2026 قراءة المزيد
ادارة الفرق والتنمية البشرية

رحيل مهندس كاد أن ينسف المشروع: كيف أنقذتنا ‘مصفوفة المهارات’ من جحيم ‘عامل الحافلة’؟

أتذكر جيدًا ذلك اليوم الذي كاد فيه مشروع استراتيجي أن ينهار بسبب استقالة مهندس واحد. في هذه المقالة، أسرد لكم كيف انتقلنا من حافة الهاوية...

30 أبريل، 2026 قراءة المزيد
اختبارات الاداء والجودة

كانت تغطية الاختبارات 100% لكن الثقة 0%: كيف أنقذنا ‘الاختبار الطفري’ (Mutation Testing) من جحيم الاختبارات الوهمية؟

أشارككم قصة من الميدان، يوم اكتشفنا أن تغطية الاختبارات بنسبة 100% كانت مجرد وهم جميل يخفي وراءه كودًا هشًا. سنتعمق في مفهوم "الاختبار الطفري" (Mutation...

30 أبريل، 2026 قراءة المزيد
البودكاست