Git & GitHub
الـ Commits في Git — دليل شامل 2026
📅 2026-11-23⏱ 7 دقائق قراءة
في المقال السابق، أنشأت أول مستودع وقمت بأول commit. الآن سنتعمق في **Commits** — وهي **الوحدة الأساسية** في Git.
في هذا الدليل العملي، سنأخذك خطوة بخطوة لفهم Commits الاحترافية، مع تمارين وحلول.
## ما هو Commit؟
**Commit** هو **لقطة (Snapshot)** من مشروعك في لحظة معينة.
**تشبيه بسيط:** تخيل أن Commit هو **صورة فوتوغرافية** لمشروعك:
- تُظهر حالة الملفات في لحظة معينة.
- لها **رسالة** تصف ما تغيّر.
- لها **تاريخ** و **مؤلف**.
- يمكنك **الرجوع** إليها في أي وقت.
**كل Commit يحتوي على:**
<table>
<thead>
<tr>
<th>العنصر</th>
<th>الوصف</th>
</tr>
</thead>
<tbody>
<tr>
<td><strong>Hash</strong></td>
<td>معرّف فريد (SHA-1)</td>
</tr>
<tr>
<td><strong>Author</strong></td>
<td>من كتب الكود</td>
</tr>
<tr>
<td><strong>Date</strong></td>
<td>متى كُتب</td>
</tr>
<tr>
<td><strong>Message</strong></td>
<td>وصف التغيير</td>
</tr>
<tr>
<td><strong>Parent</strong></td>
<td>الـ commit السابق</td>
</tr>
<tr>
<td><strong>Changes</strong></td>
<td>الملفات المتغيرة</td>
</tr>
</tbody>
</table>
## كيف تكتب Commit جيد؟
### القواعد الذهبية:
1. **قصير:** لا يزيد عن 50 حرفاً.
2. **واضح:** يصف **ماذا** تغيّر، و**لماذا**.
3. **بصيغة الأمر:** "إضافة"، "إصلاح"، "تحديث".
4. **بالعربية أو الإنجليزية:** اختر واحدة والتزم بها.
### أمثلة:
**✅ جيدة:**
```
إضافة صفحة الاتصال
إصلاح خطأ في تسجيل الدخول
تحديث مكتبة React إلى 19
إزالة الكود المكرر
```
**❌ سيئة:**
```
تعديل
commit
fixed
asdfasdf
تحديثات كثيرة
```
## Conventional Commits
**Conventional Commits** هو **معيار عالمي** لكتابة Commits احترافية.
**الصيغة:**
```
<type>(<scope>): <description>
```
**الأنواع الشائعة:**
<table>
<thead>
<tr>
<th>النوع</th>
<th>الوصف</th>
<th>مثال</th>
</tr>
</thead>
<tbody>
<tr>
<td><strong>feat</strong></td>
<td>ميزة جديدة</td>
<td><code>feat: إضافة تسجيل الدخول</code></td>
</tr>
<tr>
<td><strong>fix</strong></td>
<td>إصلاح خطأ</td>
<td><code>fix: إصلاح خطأ في النموذج</code></td>
</tr>
<tr>
<td><strong>docs</strong></td>
<td>توثيق</td>
<td><code>docs: تحديث README</code></td>
</tr>
<tr>
<td><strong>style</strong></td>
<td>تنسيق (بدون منطق)</td>
<td><code>style: تنسيق الكود</code></td>
</tr>
<tr>
<td><strong>refactor</strong></td>
<td>إعادة هيكلة</td>
<td><code>refactor: تقسيم الدوال</code></td>
</tr>
<tr>
<td><strong>test</strong></td>
<td>اختبارات</td>
<td><code>test: إضافة اختبارات</code></td>
</tr>
<tr>
<td><strong>chore</strong></td>
<td>مهام روتينية</td>
<td><code>chore: تحديث المكتبات</code></td>
</tr>
</tbody>
</table>
**أمثلة كاملة:**
```
feat(auth): إضافة تسجيل الدخول بالبريد
fix(api): إصلاح خطأ في تحميل البيانات
docs(readme): تحديث دليل التثبيت
refactor(utils): تقسيم الدوال المساعدة
chore(deps): تحديث React إلى 19
```
## Commit Message Body
**للـ Commits المعقدة، أضف تفاصيل:**
```bash
git commit -m "feat(auth): إضافة تسجيل الدخول بالبريد" -m "- إضافة صفحة تسجيل الدخول
- ربط API المصادقة
- إضافة التحقق من البيانات
- إضافة معالجة الأخطاء"
```
**النتيجة:**
```
feat(auth): إضافة تسجيل الدخول بالبريد
- إضافة صفحة تسجيل الدخول
- ربط API المصادقة
- إضافة التحقق من البيانات
- إضافة معالجة الأخطاء
```
## عرض السجل
### 1. السجل الكامل
```bash
git log
```
### 2. السجل المختصر
```bash
git log --oneline
```
**النتيجة:**
```
abc1234 feat: إضافة تسجيل الدخول
def5678 fix: إصلاح خطأ في النموذج
ghi9012 docs: تحديث README
```
### 3. السجل المختصر مع الفروع
```bash
git log --oneline --graph --all
```
### 4. سجل ملف معين
```bash
git log --oneline README.md
```
### 5. سجل شخص معين
```bash
git log --author="Ahmed"
```
### 6. سجل فترة زمنية
```bash
git log --since="2 weeks ago"
git log --until="2026-11-01"
```
## تعديل آخر Commit
### 1. تعديل الرسالة فقط
```bash
git commit --amend -m "رسالة جديدة"
```
### 2. إضافة ملفات لآخر Commit
```bash
git add forgotten-file.txt
git commit --amend --no-edit
```
**⚠️ تحذير:** لا تعدّل Commits **مرفوعة** إلى GitHub (إلا إذا كنت وحدك).
## الرجوع إلى Commit سابق
### 1. عرض التغييرات قبل الرجوع
```bash
git log --oneline
```
### 2. الرجوع مع الاحتفاظ بالتغييرات (Soft Reset)
```bash
git reset --soft HEAD~1
```
**النتيجة:** يُلغي آخر commit، لكن التغييرات تبقى في Staging.
### 3. الرجوع مع الاحتفاظ بالملفات (Mixed Reset — افتراضي)
```bash
git reset HEAD~1
```
**النتيجة:** يُلغي آخر commit، والتغييرات تبقى في Working Directory.
### 4. الرجوع مع حذف التغييرات (Hard Reset)
```bash
git reset --hard HEAD~1
```
**⚠️ تحذير:** **يحذف كل التغييرات!**
### 5. الرجوع لـ Commit معين
```bash
git reset --hard abc1234
```
## التراجع عن Commit مرفوع
**استخدم `revert` بدلاً من `reset`:**
```bash
git revert abc1234
```
**النتيجة:** يُنشئ **commit جديد** يُلغي التغييرات.
## استرجاع ملف من Commit قديم
```bash
git checkout abc1234 -- README.md
```
**النتيجة:** يُعيد `README.md` كما كان في commit `abc1234`.
## إلغاء `git add`
```bash
# ملف واحد
git restore --staged file.txt
# كل الملفات
git restore --staged .
```
**أو القديم:**
```bash
git reset HEAD file.txt
```
## حذف ملف من Git (مع الاحتفاظ به محلياً)
```bash
git rm --cached file.txt
```
**الفائدة:** للملفات التي يجب أن تكون في `.gitignore`.
## مثال عملي: مشروع متكامل
### السيناريو: بناء تطبيق مهام
**الخطوة 1: إعداد المشروع**
```bash
mkdir todo-app
cd todo-app
git init
```
**الخطوة 2: إضافة الملفات الأساسية**
```bash
echo "# Todo App" > README.md
git add README.md
git commit -m "docs: إضافة README"
```
**الخطوة 3: إضافة package.json**
```bash
npm init -y
git add package.json
git commit -m "chore: إعداد package.json"
```
**الخطوة 4: إضافة الكود**
```bash
mkdir src
echo "console.log('Hello');" > src/index.js
git add .
git commit -m "feat: إضافة الدالة الرئيسية"
```
**الخطوة 5: إضافة .gitignore**
```bash
echo "node_modules/" > .gitignore
git add .gitignore
git commit -m "chore: إضافة .gitignore"
```
**السجل:**
```bash
git log --oneline
```
**النتيجة:**
```
d4e5f6g chore: إضافة .gitignore
c3d4e5f feat: إضافة الدالة الرئيسية
b2c3d4e chore: إعداد package.json
a1b2c3d docs: إضافة README
```
**🎉 سجل احترافي!**
## تمارين عملية
### تمرين 1: أول Commit
أنشئ ملفاً واعمل commit.
**الحل:**
```bash
echo "مرحباً" > hello.txt
git add hello.txt
git commit -m "feat: إضافة ملف الترحيب"
```
### تمرين 2: Conventional Commit
اكتب commit بصيغة Conventional.
**الحل:**
```bash
git commit -m "feat(auth): إضافة تسجيل الدخول"
```
### تمرين 3: عرض السجل
اعرض آخر 5 commits.
**الحل:**
```bash
git log --oneline -5
```
### تمرين 4: تعديل آخر Commit
عدّل رسالة آخر commit.
**الحل:**
```bash
git commit --amend -m "feat: رسالة جديدة"
```
### تمرين 5: إلغاء `git add`
أضف ملفاً ثم ألغِ الإضافة.
**الحل:**
```bash
git add file.txt
git restore --staged file.txt
```
### تمرين 6: الرجوع
ارجع لـ commit سابق مع الاحتفاظ بالتغييرات.
**الحل:**
```bash
git reset --soft HEAD~1
```
### تمرين 7: استرجاع ملف
استرجع ملفاً من commit قديم.
**الحل:**
```bash
git checkout abc1234 -- README.md
```
### تمرين 8: مشروع كامل
أنشئ مشروعاً مع 5 commits احترافية.
**الحل:** (راجع المثال العملي أعلاه)
## حل المشاكل الشائعة
### 🔴 المشكلة 1: `nothing to commit`
**السبب:** لا توجد تغييرات.
**الحل:** تأكد من تعديل الملفات، ثم:
```bash
git status
```
### 🔴 المشكلة 2: نسيت `-m`
**النتيجة:** سيفتح محرر. اكتب الرسالة، احفظ، وأغلق.
**لتجنب ذلك:**
```bash
git config --global core.editor "code --wait"
```
### 🔴 المشكلة 3: `fatal: not a git repository`
**الحل:**
```bash
git init
```
### 🔴 المشكلة 4: أخطأت في رسالة commit
**الحل:**
```bash
git commit --amend -m "الرسالة الصحيحة"
```
### 🔴 المشكلة 5: أريد حذف آخر commit
**الحل:**
```bash
git reset --hard HEAD~1
```
**⚠️ تحذير:** يحذف التغييرات!
## جدول أوامر Commits
<table>
<thead>
<tr>
<th>الأمر</th>
<th>الوظيفة</th>
</tr>
</thead>
<tbody>
<tr>
<td><code>git commit -m "msg"</code></td>
<td>إنشاء commit</td>
</tr>
<tr>
<td><code>git commit -am "msg"</code></td>
<td>إضافة + commit</td>
</tr>
<tr>
<td><code>git commit --amend</code></td>
<td>تعديل آخر commit</td>
</tr>
<tr>
<td><code>git log</code></td>
<td>عرض السجل</td>
</tr>
<tr>
<td><code>git log --oneline</code></td>
<td>سجل مختصر</td>
</tr>
<tr>
<td><code>git show abc123</code></td>
<td>تفاصيل commit</td>
</tr>
<tr>
<td><code>git reset --soft HEAD~1</code></td>
<td>إلغاء commit (ناعم)</td>
</tr>
<tr>
<td><code>git reset --hard HEAD~1</code></td>
<td>إلغاء commit (قوي)</td>
</tr>
<tr>
<td><code>git revert abc123</code></td>
<td>عكس commit</td>
</tr>
<tr>
<td><code>git restore --staged .</code></td>
<td>إلغاء git add</td>
</tr>
</tbody>
</table>
## قائمة تحقق نهائية
<table>
<thead>
<tr>
<th>المهمة</th>
<th>الحالة</th>
</tr>
</thead>
<tbody>
<tr>
<td>فهم ما هو Commit</td>
<td>⬜</td>
</tr>
<tr>
<td>كتابة commits واضحة</td>
<td>⬜</td>
</tr>
<tr>
<td>Conventional Commits</td>
<td>⬜</td>
</tr>
<tr>
<td>عرض السجل</td>
<td>⬜</td>
</tr>
<tr>
<td>تعديل آخر Commit</td>
<td>⬜</td>
</tr>
<tr>
<td>الرجوع لـ Commit سابق</td>
<td>⬜</td>
</tr>
<tr>
<td>حل التمارين الثمانية</td>
<td>⬜</td>
</tr>
</tbody>
</table>
## ماذا بعد هذا المقال؟
الآن بعد أن أتقنت Commits، أنت جاهز للمقال التالي:
1. **الفروع (Branches)** — العمل على ميزات متعددة.
2. **الدمج (Merge)** — دمج الفروع.
3. **GitHub** — Pull Requests.
## الخلاصة
في هذا المقال، تعلمت:
- ✅ ما هو Commit.
- ✅ كيف تكتب commits احترافية.
- ✅ Conventional Commits.
- ✅ عرض السجل.
- ✅ تعديل آخر Commit.
- ✅ الرجوع لـ Commit سابق.
- ✅ حل 8 تمارين عملية.
**تذكر:** Commit جيد = تاريخ مشروع نظيف = فريق سعيد.