سجلاتنا كانت مقبرة نصوص: كيف أنقذنا ‘التسجيل المنظم’ (Structured Logging) من جحيم البحث عن إبرة في كومة قش؟

يا جماعة الخير، السلام عليكم ورحمة الله.

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

وبالفعل، كانت مصيبة. النظام الأساسي تبعنا “واقع”، والعملاء بشتكوا، والإدارة بتضغط. فتحت اللابتوب على عجَل، وبدينا رحلة العذاب: البحث في السجلات (Logs).

يا دَخيل الله! شو هاد؟ كل خدمة في النظام بتكتب سجلات على كيفها. هاي بتكتب سطر طويل بدون أي تنسيق، وهذيك بتكتب التاريخ بصيغة مختلفة، والثالثة ما بتسجل أصلاً معلومات كافية. كنا زي اللي بدور على إبرة في كومة قش عملاقة، بس القش كله متشابك ومعقّد. كل واحد فينا فاتح عشرين شاشة طرفية (terminal) وبيعمل `grep` و `awk` و `sed`، وبحاول يفهم شو اللي بصير. بعد ثلاث ساعات من الجحيم، وبشق الأنفس، لقينا المشكلة. كانت بسبب تغيير بسيط في واجهة برمجية خارجية ما حدا انتبه له.

في هذيك الليلة، بعد ما انحلت المشكلة، ما قدرت أنام. مش بسبب التعب، لكن بسبب سؤال كان يلحّ علي: “معقول في 2024 لسا بنتعامل مع السجلات بهالطريقة البدائية؟”. هنا كانت نقطة التحول، اللحظة اللي قررنا فيها ننتقل لعالم “التسجيل المنظم” أو الـ Structured Logging.

مقبرة النصوص: مأساة التسجيل التقليدي (Unstructured Logging)

قبل ما نحكي عن الحل، خلينا نفهم أصل المشكلة. المشكلة كانت في اللي بنسميه “التسجيل غير المنظم”.

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

مثال على سجل غير منظم

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


// JavaScript (Node.js)
console.error("Error processing payment for user " + userId + ". Order ID: " + orderId + ". Reason: " + error.message);

الناتج في ملف السجل بيكون سطر نصي زي هيك:


Error processing payment for user 12345. Order ID: 987-XYZ. Reason: Insufficient funds.

للوهلة الأولى، يبدو هذا السطر واضحاً ومفهوماً للإنسان. لكن ماذا لو أردت أن:

  • أجد كل أخطاء الدفع للمستخدم رقم 12345؟
  • أعدّ كم مرة حدث خطأ “Insufficient funds” خلال الساعة الماضية؟
  • أرسم مخططاً بيانياً يوضح أخطاء الدفع حسب نوعها؟

هنا تبدأ المعاناة. ستضطر لكتابة تعابير نمطية (Regular Expressions) معقدة جداً لمحاولة “استخلاص” المعلومات من هذا النص. وإذا قام مبرمج آخر بتغيير كلمة “user” إلى “customer” في رسالة السجل، فإن كل تحليلاتك ستفشل. باختصار، سجلاتك تحولت إلى مقبرة نصوص، جميلة من بعيد لكن لا فائدة حقيقية منها عند الحاجة.

المنقذ: التسجيل المنظم (Structured Logging) 💡

التسجيل المنظم هو نقلة نوعية في التفكير. الفكرة بسيطة لكن عبقرية: “عامل سجلاتك كبيانات (Data)، وليس كنصوص (Text)”.

بدلاً من كتابة جملة نصية حرة، نقوم بتسجيل الأحداث على شكل أزواج من المفاتيح والقيم (key-value pairs)، وغالباً ما نستخدم تنسيق JSON لأنه معيار مفهوم للآلات وسهل القراءة للبشر.

من نص عادي إلى بيانات منظمة

لنعد كتابة مثالنا السابق باستخدام التسجيل المنظم:


// JavaScript (using a library like "pino")
const logger = require('pino')();

// ... في مكان حدوث الخطأ
logger.error(
  {
    userId: 12345,
    orderId: "987-XYZ",
    errorCode: "INSUFFICIENT_FUNDS",
    traceId: "abc-123-def-456" // معرف فريد لتتبع الطلب عبر الخدمات
  },
  "Payment processing failed" // رسالة صديقة للإنسان
);

الآن، انظر إلى الناتج الذي سيُكتب في السجل:


{"level":50,"time":1678886400000,"pid":123,"hostname":"server-a","userId":12345,"orderId":"987-XYZ","errorCode":"INSUFFICIENT_FUNDS","traceId":"abc-123-def-456","msg":"Payment processing failed"}

يا سلام! الفرق شاسع. الآن كل معلومة لها حقل خاص بها. لم نعد بحاجة لتخمين أو تحليل النصوص. يمكننا الآن أن نسأل نظام السجلات أسئلة دقيقة جداً:

  • SELECT * WHERE level = 'error' AND errorCode = 'INSUFFICIENT_FUNDS'
  • COUNT(*) WHERE userId = 12345 GROUP BY errorCode

لقد تحولت سجلاتنا من مقبرة نصوص إلى قاعدة بيانات غنية بالمعلومات وجاهزة للتحليل.

كيف نبدأ بالتسجيل المنظم؟ خطوات عملية من خبرتي

الانتقال للتسجيل المنظم ليس معقداً. هذه هي الخطوات التي اتبعناها والتي أنصح بها أي فريق.

1. اختر التنسيق المناسب (JSON هو الملك)

لا تفكر كثيراً، استخدم JSON. هو المعيار العالمي المدعوم من كل لغات البرمجة ومنصات تجميع السجلات. لا تحاول اختراع العجلة.

2. استخدم المكتبة الصحيحة

كل لغة برمجة لها مكتبات قوية للتسجيل المنظم. لا تقم ببناء مُنشئ JSON الخاص بك يدوياً! هذه المكتبات توفر ميزات هائلة مثل الأداء العالي، والمستويات المختلفة للسجلات (debug, info, warn, error)، وإضافة الحقول السياقية تلقائياً.

  • Node.js: Pino (مفضلتي بسبب سرعتها)، Winston.
  • Python: structlog.
  • Java: Logback مع Logstash-logback-encoder.
  • Go: Zerolog, Logrus.

3. وحّد الحقول الأساسية (الأهم على الإطلاق)

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

بعض الحقول المقترحة:

  • timestamp: زمن حدوث الحدث (بالتوقيت العالمي المنسق UTC).
  • level: مستوى السجل (e.g., “info”, “error”).
  • service.name: اسم الخدمة أو التطبيق الذي أصدر السجل.
  • message: رسالة نصية قصيرة وواضحة للإنسان.
  • trace.id / correlation.id: أهم حقل في عالم الخدمات المصغرة (Microservices). يسمح لك بتتبع رحلة طلب واحد عبر عدة خدمات.
  • user.id: معرف المستخدم (إن وجد).
  • error.message / error.stack: لتسجيل تفاصيل الأخطاء.

4. اجمع سجلاتك في مكان واحد (Centralize Your Logs)

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

  • ELK Stack: (Elasticsearch, Logstash, Kibana) – حل مفتوح المصدر وقوي جداً.
  • Loki & Grafana: حل آخر مشهور في مجتمع المصادر المفتوحة.
  • خدمات سحابية: مثل Datadog, New Relic, Logz.io.

عندما تكون سجلاتك المنظمة في مكان واحد، يمكنك البحث والتحليل وإنشاء لوحات المراقبة والتنبيهات بسهولة لا تصدق.

الخلاصة: لا تنتظر المصيبة! ✅

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

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

مستقبلك (ومستقبل فريقك) سيشكرك في أول حالة طوارئ تمر عليكم. صدقني!

والله ولي التوفيق.

أبو عمر

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

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

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

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

آخر المدونات

التوظيف وبناء الهوية التقنية

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

أشارككم قصتي مع الإحباط في البحث عن وظيفة وكيف كان بناء موقع شخصي احترافي هو نقطة التحول التي أنقذت هويتي التقنية من الضياع بين آلاف...

18 أبريل، 2026 قراءة المزيد
التوسع والأداء العالي والأحمال

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

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

18 أبريل، 2026 قراءة المزيد
التكنلوجيا المالية Fintech

بياناتنا المالية كانت سجينة: كيف أنقذتنا ‘الخدمات المصرفية المفتوحة’ (Open Banking) من جحيم العزلة الرقمية؟

كنا نعاني من تشتت بياناتنا المالية بين البنوك المختلفة، حتى أتت ثورة "الخدمات المصرفية المفتوحة" (Open Banking). في هذه المقالة، أسرد لكم تجربتي كمبرمج مع...

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

اجتماعاتنا الفردية كانت جحيمًا: كيف أنقذنا إطار عمل 1:1 من دوامة تقارير الحالة؟

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

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

إعداد المشاريع كان يلتهم أيامنا: كيف أنقذتنا ‘حاويات التطوير’ (Dev Containers) من جحيم ‘لكنه يعمل على جهازي!’؟

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

18 أبريل، 2026 قراءة المزيد
أتمتة العمليات

مهامنا الروتينية كانت تلتهم وقتنا: كيف أنقذتنا ‘أتمتة العمليات الروبوتية’ (RPA) من جحيم العمل اليدوي الممل؟

أنا أبو عمر، مبرمج فلسطيني، وأروي لكم كيف كنا نغرق في بحر من المهام اليدوية المتكررة حتى اكتشفنا "أتمتة العمليات الروبوتية" (RPA). في هذه المقالة،...

18 أبريل، 2026 قراءة المزيد
​معمارية البرمجيات

المونوليث كان وحشًا لا يمكن المساس به: كيف أنقذنا ‘نمط الخانق’ من جحيم التجميد التطويري؟

في هذه المقالة، أشارككم قصة حقيقية من قلب المعركة مع نظام موروث "مونوليث" كاد أن يشلّ فريقنا بالكامل. سأشرح لكم بالتفصيل نمط "الخانق" (Strangler Fig...

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