git bisect: كيف أنقذنا من لغز “أي تحديث كسر كل شيء؟”

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

المشكلة؟ هذه الميزة كانت تعمل زي الحلاوة الأسبوع الماضي. ما الذي تغير؟ نظرنا إلى سجل الـ commits، ويا لهول ما رأينا. أكثر من 150 commit تم دمجها على الفرع الرئيسي منذ آخر مرة تأكدنا فيها أن كل شيء سليم. بدأت عملية البحث اليدوي المُرعبة: “جرّب هذا الـ commit”، “لأ، ارجع للي قبله بثلاثة”، “يمكن المشكلة من تحديث المكتبة الفلانية؟”. ساعات من التوتر والقهوة الباردة، وكل محاولة كانت تزيد الطين بلة. شعرتُ أننا في حلقة مفرغة، وكأننا نبحث عن إبرة في كومة قش عملاقة.

في لحظة يأس، وقبل أن يقترح أحدهم إعادة كتابة المشروع من الصفر (وهو اقتراح يظهر دائماً في هذه المواقف!)، وقفت وقلت: “يا جماعة، هَدّوا شوي. فيه أداة في Git مخصصة لهيك حكايات بالزبط. خلونا نجرب الـ git bisect“.

ما هي أداة “git bisect” السحرية؟

ببساطة شديدة، git bisect هي أداة بحث ثنائي (Binary Search) مدمجة في Git، مصممة خصيصاً لتحديد الـ commit الدقيق الذي أدخل خطأً (bug) إلى الكود. الفكرة عبقرية في بساطتها.

بدلاً من أن تمر على الـ 150 commit واحداً تلو الآخر (وهو ما قد يستغرق يوماً كاملاً)، تقوم git bisect بالقفز إلى منتصف هذه الـ commits (عند الـ commit رقم 75 مثلاً). ثم تسألك سؤالاً واحداً: “هل الخطأ موجود هنا؟”.

  • إذا قلت “نعم، الخطأ موجود” (bad)، فهي تعلم أن المشكلة حدثت في النصف الأول من الـ commits (من 1 إلى 75).
  • إذا قلت “لا، كل شيء يعمل” (good)، فهي تعلم أن المشكلة حدثت في النصف الثاني (من 76 إلى 150).

ثم تكرر العملية، فتقفز إلى منتصف النطاق الجديد، وتطرح نفس السؤال. بهذه الطريقة، ومع كل خطوة، يتم تقليص عدد الـ commits المشتبه بها إلى النصف. بالنسبة لـ 150 commit، قد تحتاج إلى 7 أو 8 خطوات فقط للوصول إلى الجاني، بدلاً من 150 خطوة يدوية!

الدليل العملي: رحلة صيد الخطأ خطوة بخطوة

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

الخطوة الأولى: بدء عملية البحث

أولاً، تحتاج إلى إخبار Git أنك ستبدأ عملية “التقسيم الثنائي”. تفتح الطرفية (Terminal) في مجلد مشروعك وتكتب:

git bisect start

بهذا الأمر، يدخل Git في وضع خاص، جاهزاً لتلقي التعليمات.

الخطوة الثانية: تحديد “السيئ” و “الجيد”

الآن، تحتاج إلى إعطاء Git نقطتي بداية:

  1. الـ Commit السيئ (Bad): وهو الـ commit الحالي الذي يحتوي على الخطأ. عادةً ما يكون هذا هو رأس الفرع (HEAD).
  2. الـ Commit الجيد (Good): وهو آخر commit أنت متأكد 100% أن الكود كان يعمل فيه بشكل سليم.

نحن على الـ commit المعطوب حالياً، فنكتب:

git bisect bad

بعد ذلك، نحتاج إلى العثور على commit قديم كان كل شيء فيه على ما يرام. يمكنك الحصول على الـ “هاش” (hash) الخاص به من خلال git log، أو من واجهة GitHub/GitLab، أو ربما يكون لديك tag لإصدار سابق مثل v1.2.0.

لنفترض أن الـ commit الجيد كان يحمل الهاش a1b2c3d. نكتب الأمر التالي:

git bisect good a1b2c3d

بمجرد تنفيذ هذا الأمر، يبدأ السحر. سيقوم Git بالقفز إلى commit في منتصف المسافة بين a1b2c3d والـ commit السيئ، وسيظهر لك رسالة شبيهة بهذه:

Bisecting: 75 revisions left to test after this (roughly 7 steps)

الخطوة الثالثة: دورة الاختبار (good أم bad؟)

الآن، مهمتك بسيطة ومكررة. Git قام بتحديث ملفات مشروعك إلى حالة الـ commit الذي اختاره. كل ما عليك فعله هو:

  1. اختبر الكود: شغّل التطبيق، واذهب إلى الميزة التي كانت معطلة، وجربها.
  2. أخبر Git بالنتيجة:
    • إذا كان الخطأ لا يزال موجوداً، اكتب: git bisect bad
    • إذا كانت الميزة تعمل بشكل سليم (الخطأ غير موجود)، اكتب: git bisect good

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

الخطوة الرابعة: العثور على الجاني!

بعد بضع خطوات (7 خطوات في مثالنا)، ستنتهي دورة الاختبار. سيطبع Git رسالة تفصيلية يخبرك فيها بالـ commit الأول الذي أدخل الخطأ. ستبدو الرسالة هكذا:

f9d9a9e is the first bad commit
commit f9d9a9e0a8b1c2d3e4f5a6b7c8d9e0a1b2c3d4e5
Author: زميلك في الفريق <colleague@example.com>
Date:   Wed Oct 26 10:30:00 2023 +0300

    feat: Refactor payment gateway logic

    تمت إعادة هيكلة منطق بوابة الدفع ليكون أسرع.

هذه هي لحظة “وجدتها!”. الآن أنت تعرف بالضبط أي commit تسبب في المشكلة، ومن قام به، وحتى رسالة الـ commit التي تشرح “النية” من ورائه. في حالتنا، كان التعديل يهدف إلى تحسين الأداء، لكنه تسبب في أثر جانبي غير متوقع.

الخطوة الخامسة: تنظيف وإنهاء العملية

بعد أن وجدت ضالتك، لا تنسَ أن تخرج من وضع الـ bisect لتعود إلى حالتك الطبيعية. الأمر بسيط جداً:

git bisect reset

سيقوم هذا الأمر بإعادتك إلى الـ commit الذي بدأت منه (HEAD)، ويمكنك الآن تحليل الـ commit المذنب وإصلاح المشكلة وأنت تعرف مصدرها بالضبط.

نصائح من خبرة أبو عمر 🧔

استخدام git bisect بفعالية يتجاوز مجرد حفظ الأوامر. إليك بعض الأسرار التي تعلمتها مع كثرة الاستخدام:

h3>التشغيل التلقائي مع `git bisect run`

ماذا لو كان لديك اختبارات تلقائية (automated tests) يمكنها كشف الخطأ؟ هنا تظهر القوة الحقيقية. يمكنك أن تطلب من Git أن يقوم بعملية الاختبار بنفسه!

اكتب سكربت بسيط (مثلاً test-bug.sh) يقوم بتشغيل الاختبارات. هذا السكربت يجب أن:

  • يخرج بحالة نجاح (exit code 0) إذا كان الكود “جيداً” (good).
  • يخرج بحالة فشل (exit code غير الصفر، مثلاً 1) إذا كان الكود “سيئاً” (bad).

مثال على سكربت بسيط:

#!/bin/sh
npm install && npm test # أو أي أمر اختبار خاص بمشروعك
# إذا نجح الاختبار، سيخرج الكود 0 تلقائياً
# إذا فشل، سيخرج الكود غير الصفر

بعدها، يمكنك تشغيل عملية الـ bisect بأكملها بأمر واحد:

git bisect start
git bisect bad HEAD
git bisect good a1b2c3d
git bisect run ./test-bug.sh

والآن، اذهب وحضّر فنجان قهوة آخر. عندما تعود، سيكون Git قد وجد الـ commit المذنب بنفسه. هذا شيء يغير قواعد اللعبة تماماً.

h3>ماذا لو كان الـ commit لا يعمل أساساً؟

أحياناً، قد يقفز git bisect إلى commit لا يمكنك اختباره (مثلاً، الكود لا يعمل “compile” أو التطبيق ينهار عند التشغيل). هذا الـ commit ليس “جيداً” ولا “سيئاً”، بل هو ببساطة غير قابل للاختبار.

في هذه الحالة، استخدم الأمر:

git bisect skip

سيقوم Git بتجاهل هذا الـ commit واختيار commit آخر قريب منه ليكمل البحث.

h3>الـ Commits الذرية (Atomic Commits) هي صديقك

فعالية git bisect تعتمد بشكل كبير على نظافة سجل الـ commits. إذا كان كل commit يقوم بتغيير صغير ومركز ومحدد (مثلاً: “إضافة زر تسجيل الدخول” بدلاً من “تعديلات شاملة على الواجهة والمخدم”)، فإن git bisect سيشير إلى سبب المشكلة بدقة ليزرية.

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

الخلاصة: أداة لا تقدر بثمن

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

git bisect ليست مجرد أمر تقني، بل هي ثقافة عمل. إنها تعزز الثقة في التعامل مع الأخطاء، وتحول لحظات الذعر إلى تحدٍ منهجي يمكن حله. المرة القادمة التي تجد فيها نفسك وفريقك في جحيم “أي تحديث كسر كل شيء؟”، تذكر صديقك أبو عمر وهذه الأداة. لا داعي للذعر، فقط ابدأ بالتقسيم! 🚀

أبو عمر

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

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

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

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

آخر المدونات

برمجة وقواعد بيانات

تحديثات قاعدة البيانات بدون توقف: كيف أنقذنا نمط التوسيع والتعاقد (Expand/Contract) من جحيم التوقفات المجدولة؟

هل سئمت من إيقاف الخدمة مع كل تحديث لهيكلة قاعدة البيانات؟ أشارككم قصة حقيقية وكيف أنقذنا نمط التوسيع والتعاقد (Expand/Contract) من ليالي النشر الطويلة والمُجهدة،...

4 يونيو، 2026 قراءة المزيد
الشبكات والـ APIs

كانت إعادة المحاولة كارثة: كيف أنقذتنا مفاتيح عدم تكرار العمليات (Idempotency Keys) من جحيم الفواتير المزدوجة؟

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

4 يونيو، 2026 قراءة المزيد
الحوسبة السحابية

من التوقف التام إلى النجاة: كيف أنقذتنا استراتيجية “الضوء المرشد” (Pilot Light) يوم انقطعت السحابة؟

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

4 يونيو، 2026 قراءة المزيد
التوظيف وبناء الهوية التقنية

كانت مهمتي البرمجية للاختبار مجرد كود: كيف أنقذني توثيق القرارات من جحيم الصمت بعد المقابلة؟

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

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

من الانتظار لأيام إلى الدفع في ثوانٍ: كيف أنقذتنا شبكات الدفع الفوري من جحيم التحويلات البنكية؟

أسرد لكم من واقع تجربتي كـ "أبو عمر"، كيف عانينا من بطء وتكلفة التحويلات البنكية الدولية، وكيف جاءت شبكات الدفع الفوري ومعيار ISO 20022 لتكون...

4 يونيو، 2026 قراءة المزيد
البنية التحتية وإدارة السيرفرات

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

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

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

كانت تغطية الاختبارات 100% لكن الأخطاء تتسرب: كيف أنقذنا “الاختبار الطفري” من جحيم الثقة الزائفة؟

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

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