يا جماعة الخير، السلام عليكم ورحمة الله.
خلوني أرجع بالزمن شوي… أذكر مرة، قبل كم سنة، كنا في عز الشغل على مشروع مهم. كان معنا شب جديد بالفريق، خلينا نسميه “سامر”، شب شاطر ونشيط ومليان حماس. رفع سامر أول “طلب سحب” (Pull Request) له، وكان الكود شغال وممتاز من ناحية وظيفية. لكن، يا ويلي شو صار بعدها!
فتح واحد من المبرمجين القدامى، “أبو خليل”، مراجعة الكود. أول تعليق: “ليش مستخدم الفاصلة المنقوطة في آخر الأسطر؟ احنا متفقين نشيلها”. رد سامر: “بس المحرر عندي بضيفها تلقائيًا”. بعد شوي، دخل مبرمج ثالث: “يا جماعة، الأهم من الفاصلة المنقوطة هو استخدام علامات الاقتباس المزدوجة (double quotes) بدل المفردة (single quotes) عشان التناسق!”.
خلال ساعة، كان طلب السحب تبع سامر عبارة عن ساحة حرب. أكثر من 20 تعليق، ولا واحد فيهم بيحكي عن منطق الكود أو أداءه. كلها كانت عن الأسلوب: مسافة زيادة هان، سطر فاضي هناك، قوس لازم ينزل على سطر جديد… حسيت سامر المسكين بده يبكي، وشغفه بلش يطفي. وقتها، وقفت النقاش وقلت لهم: “يا جماعة، هل هذا أفضل استخدام لوقتنا وخبرتنا؟ هل بنراجع كود ولا بنصلّح إملاء؟”.
هذا الموقف، اللي تكرر كثير، كان الشرارة اللي خلتنا نبحث عن حل جذري. حل يحررنا من الجدال البيزنطي ويخلينا نركز على اللي يهم جدًا. الحل كان الأتمتة، وتحديدًا “خطافات ما قبل الدفع” أو الـ Pre-commit Hooks.
مراجعات الكود: بين الجودة والجدال البيزنطي
خلونا نكون صريحين، مراجعة الكود (Code Review) هي حجر الزاوية في أي فريق برمجي محترف. هدفها الأساسي هو:
- اكتشاف الأخطاء المنطقية: العثور على مشاكل في منطق العمل قد لا تكتشفها الاختبارات الآلية.
- تحسين التصميم: اقتراح طرق أفضل لتصميم وهيكلة الكود ليكون أكثر قابلية للصيانة والتوسعة.
- مشاركة المعرفة: فرصة للمبرمجين ليتعلموا من بعضهم البعض ويكتسبوا فهمًا أعمق لأجزاء مختلفة من النظام.
- ضمان الاتساق: الحفاظ على أسلوب برمجي موحد في المشروع بأكمله.
المشكلة بتصير لما البند الأخير (ضمان الاتساق) يطغى على كل شيء ثاني. بنلاقي حالنا بنضيّع ساعات في نقاشات تافهة حول أمور يمكن لأي أداة آلية أن تصلحها في أقل من ثانية. هذا ما يسمى في علم النفس الهندسي بـ “Bikeshedding”، وهو ميلنا لمناقشة الأمور التافهة التي نفهمها جميعًا، وتجنب المواضيع المعقدة التي تتطلب تركيزًا حقيقيًا.
الحل السحري: الأتمتة وخطافات ما قبل الدفع (Pre-commit Hooks)
وهون مربط الفرس. بدل ما نكون احنا الشرطة اللي بتراقب الأسلوب، ليش ما نوكل المهمة هاي لروبوت دقيق ما بتعب ولا بمل؟ هذا بالضبط ما تفعله خطافات Git.
ببساطة، خطافات Git (Git Hooks) هي عبارة عن سكربتات (نصوص برمجية) تعمل تلقائيًا عند وقوع أحداث معينة في مستودع Git الخاص بك. في عنا خطافات بتشتغل قبل الـ commit، وبعد الـ commit، وقبل الـ push، وهكذا.
اللي بهمنا اليوم هو الخطاف pre-commit. هذا الخطاف، كما يوحي اسمه، يعمل قبل أن يتم تسجيل الـ commit بشكل فعلي. وهذا يمنحنا فرصة ذهبية لفحص الكود وتنسيقه وإصلاحه قبل أن يصل حتى إلى سجل المشروع، وقبل أن يراه أي شخص آخر.
لماذا إطار العمل pre-commit هو الأفضل؟
طبعًا، يمكنك كتابة سكربتات الـ pre-commit يدويًا، لكن هذا الأمر معقد وصعب إدارته ومشاركته مع الفريق. لحسن الحظ، هناك إطار عمل رائع اسمه pre-commit (نعم، بنفس الاسم) يجعل هذه العملية سهلة جدًا.
مميزاته:
- سهولة الإعداد: كل ما تحتاجه هو ملف إعداد واحد بصيغة YAML.
- مشاركة سهلة: بمجرد وضع ملف الإعداد في المشروع، يمكن لكل أفراد الفريق استخدامه بنفس الإعدادات.
- متعدد اللغات: يدعم أدوات لمختلف لغات البرمجة (Python, JavaScript, Go, Rust, …إلخ).
- إدارة تلقائية للأدوات: هو يقوم بتنزيل وإدارة الأدوات التي تحددها، مما يضمن أن كل الفريق يستخدم نفس الإصدار.
يلا نشتغل عملي: كيف نطبّق الـ Pre-commit Hooks في مشروعنا؟
كلام النظر حلو، بس الشغل العملي أحلى. تعالوا نشوف كيف ممكن نطبق هذا الكلام خطوة بخطوة في أي مشروع.
الخطوة الأولى: التثبيت
أول شيء، تحتاج إلى تثبيت أداة pre-commit. إذا كان عندك Python و pip، فالأمر بسيط جدًا:
pip install pre-commit
إذا كنت تستخدم نظام تشغيل آخر أو مدير حزم آخر (مثل Homebrew على ماك)، يمكنك مراجعة صفحة التثبيت الرسمية.
الخطوة الثانية: ملف الإعداد
الآن، في المجلد الرئيسي لمشروعك، أنشئ ملفًا جديدًا باسم .pre-commit-config.yaml.
هذا الملف هو قلب النظام. فيه ستحدد الأدوات (الخطافات) التي تريد تشغيلها. لنبدأ بمثال بسيط جدًا، نضيف فيه خطافات أساسية لا غنى عنها في أي مشروع:
# .pre-commit-config.yaml
repos:
- repo: https://github.com/pre-commit/pre-commit-hooks
rev: v4.6.0 # استخدم دائمًا أحدث إصدار مستقر
hooks:
- id: trailing-whitespace # يزيل المسافات الزائدة في نهاية الأسطر
- id: end-of-file-fixer # يضمن وجود سطر فارغ في نهاية كل ملف
- id: check-yaml # يتأكد من سلامة ملفات YAML
- id: check-added-large-files # يمنع إضافة ملفات كبيرة الحجم بالخطأ
لاحظ كيف أن كل خطاف له وظيفة محددة وواضحة. هذه هي الأدوات التي كانت تسبب جدالًا في مراجعات الكود!
الخطوة الثالثة: تفعيل الخطافات
بعد إنشاء ملف الإعداد، كل ما عليك فعله هو تشغيل هذا الأمر مرة واحدة في مشروعك:
pre-commit install
هذا الأمر سيقوم بتثبيت الخطاف في مجلد .git/hooks الخاص بك. الآن، أصبحت الخطافات جاهزة للعمل تلقائيًا.
الخطوة الرابعة: السحر أثناء العمل
الآن، تخيل أنك قمت بتعديل بعض الملفات وتركت بعض المسافات الزائدة في نهاية الأسطر. عندما تحاول تنفيذ أمر git commit، سيحدث التالي:
$ git commit -m "إضافة ميزة جديدة"
Trim Trailing Whitespace.................................................Failed
- hook id: trailing-whitespace
- files were modified by this hook
Fix End of Files.........................................................Passed
Check Yaml...............................................................Passed
Check for added large files..............................................Passed
لاحظ أن الخطاف trailing-whitespace فشل. لماذا؟ لأنه وجد أخطاء وقام بإصلاحها تلقائيًا. وبما أن الملفات تم تعديلها، فإن الـ commit لم يكتمل.
كل ما عليك فعله الآن هو إضافة الملفات التي تم إصلاحها مرة أخرى وتنفيذ الـ commit مجددًا:
$ git add .
$ git commit -m "إضافة ميزة جديدة"
Trim Trailing Whitespace.................................................Passed
Fix End of Files.........................................................Passed
...
[main 1a2b3c4] إضافة ميزة جديدة
2 files changed, 5 insertions(+)
وهكذا، تم إصلاح الكود وتنسيقه قبل أن يغادر جهازك! انتهى الجدال.
مثال متقدم: إضافة أدوات تنسيق خاصة باللغة
القوة الحقيقية تظهر عندما تضيف أدوات خاصة بلغات البرمجة التي تستخدمها. لنقل أن مشروعك يستخدم Python و JavaScript. يمكنك تحديث ملف الإعداد ليصبح كالتالي:
# .pre-commit-config.yaml
repos:
- repo: https://github.com/pre-commit/pre-commit-hooks
rev: v4.6.0
hooks:
- id: trailing-whitespace
- id: end-of-file-fixer
- id: check-yaml
- id: check-added-large-files
# لملفات Python: استخدم أداة Black للتنسيق
- repo: https://github.com/psf/black
rev: 24.4.2
hooks:
- id: black
# لملفات JS, CSS, JSON, MD: استخدم أداة Prettier للتنسيق
- repo: https://github.com/pre-commit/mirrors-prettier
rev: v4.0.0-alpha.8
hooks:
- id: prettier
الآن، قبل كل commit، سيقوم black تلقائيًا بتنسيق كل ملفات Python، وسيقوم prettier بتنسيق كل ملفات الويب. لا مجال للجدال حول الأسلوب بعد اليوم. الأداة هي الحكم.
نصائح من خبرة أبو عمر
نصيحة عملية: عندما تضيف
pre-commitلمشروع قائم ومليء بالملفات غير المنسقة، لا تقم بتشغيل الـ commit مباشرة. استخدم الأمر التالي لتشغيل الخطافات على كل الملفات في المشروع مرة واحدة:pre-commit run --all-filesسيقوم هذا الأمر بإصلاح وتنسيق المشروع بأكمله. بعد ذلك، قم بعمل commit واحد كبير بعنوان “Chore: Format codebase using pre-commit” ثم واصل عملك بشكل طبيعي.
- ابدأ صغيرًا: لا تضف 20 خطافًا من اليوم الأول. ابدأ بالأساسيات (مثل إزالة المسافات الزائدة)، ثم أضف أدوات التنسيق الرئيسية للغات التي تستخدمها.
- الاتفاق أولًا: قبل إضافة أداة تنسيق مثل
blackأوprettier، تأكد من اتفاق الفريق على استخدامها وعلى إعداداتها. الهدف هو توحيد الجهود لا فرض أداة جديدة. - لا تتجاوز الخطافات: يمكنك تجاوز الخطافات باستخدام
git commit --no-verify. لا تفعل هذا إلا في حالات الطوارئ القصوى جدًا. الهدف هو الالتزام بالنظام. - أضفه إلى الـ CI/CD: بالإضافة إلى تشغيله على أجهزة المطورين، قم بإضافة خطوة في نظام التكامل المستمر (CI/CD) الخاص بك لتشغيل
pre-commit run --all-files. هذا يضمن أنه حتى لو قام أحدهم بتجاوز الخطافات، سيتم اكتشاف الكود غير المنسق قبل دمجه.
الخلاصة: ركّز على المهم، ودع الروبوتات تهتم بالتفاصيل 🤖
صدقوني يا جماعة، بعد أن طبقنا نظام الـ pre-commit hooks، تغيرت ثقافة مراجعة الكود في فريقنا 180 درجة. اختفت التعليقات التافهة والمستفزة حول التنسيق، وأصبحنا نركز نقاشاتنا على ما يهم حقًا: هل هذا الكود يحل المشكلة؟ هل هو مكتوب بطريقة فعالة؟ هل هناك تصميم أفضل؟ هل يغطي كافة الحالات الشاذة؟
أصبح المبرمجون الجدد مثل “سامر” يشعرون بالراحة في عرض أعمالهم، لأنهم يعلمون أن الآلة ستتكفل بالتنسيق، والبشر سيتكفلون بتقديم التوجيهات البنّاءة.
نصيحتي الأخيرة لكل فريق برمجي: استثمروا في الأتمتة. حرروا عقولكم من المهام المتكررة والجدالات العقيمة. دعوا الآلات تتعامل مع الأسلوب، وركزوا أنتم على فن بناء البرمجيات الرائعة. وقتكم أثمن من أن يضيع في نقاش حول فاصلة منقوطة.