
البدء باستخدام Git: أنشئ أول مستودع لك
يصبح Git أسهل بكثير عندما تتوقف عن التعامل معه على أنه قائمة أوامر منفصلة، وتبدأ بالنظر إليه بوصفه مسار عمل متكاملًا. يُنشأ الملف أو يُعدّل داخل مجلد العمل، ثم تُحدَّد نسخته عبر منطقة التجهيز، وبعد ذلك تُسجَّل ضمن تاريخ المستودع.
يحوّل هذا الدليل الفكرة السابقة إلى تمرين عملي متكامل. ستنشئ مشروعًا صغيرًا، وتبدأ مستودع Git، وتفحص حالات الملفات، وتجهز التغييرات، وتنشئ الالتزامات، وتتجاهل الملفات الناتجة تلقائيًا، وتقارن الإصدارات، ثم تتأكد من أن المستودع في حالة نظيفة.
الهدف ليس حفظ الأوامر، بل فهم ما الذي يتغير داخل Git بعد كل أمر تنفذه.
ما الذي سنبنيه؟
سننشئ مشروعًا صغيرًا يعمل من سطر الأوامر باسم Task Notes. سيبدأ المشروع بملف README وقائمة مهام نصية بسيطة.
سيكون الشكل النهائي للمشروع كما يلي:
task-notes/
├── .gitignore
├── README.md
├── notes/
│ └── tasks.txt
└── src/
└── app.txt
خلال هذا التطبيق ستتعلم كيفية:
إنشاء مجلد جديد للمشروع.
بدء مستودع Git.
فحص مجلد
.gitالمخفي.قراءة مخرجات
git status.فهم حالات الملفات: غير المتتبعة، والمتتبعة، والمعدلة، والمجهزة، والمسجلة في التزام.
تجهيز ملفات منفردة أو مجموعات من الملفات.
إنشاء التزامات واضحة ومحددة الهدف.
استخدام
git diffقبل إنشاء الالتزام.تجاهل الملفات المؤقتة والحساسة.
إيقاف تتبع ملف في Git دون حذف نسخته المحلية.
عرض سجل مختصر لتاريخ المشروع.
التأكد من أن شجرة العمل نظيفة.
المتطلبات المسبقة
قبل المتابعة، تأكد من أن Git مثبت وأن هويتك مضبوطة:
git --version
git config --get user.name
git config --get user.email
يجب أن يعرض أمرا الاسم والبريد الإلكتروني الهوية التي تريد تسجيلها داخل الالتزامات الجديدة.
إذا كانت إحدى القيمتين مفقودة، فاضبطها:
git config --global user.name "Jane Developer"
git config --global user.email "jane@example.com"
تحقق أيضًا من اسم الفرع الأولي الافتراضي:
git config --get init.defaultBranch
إذا لم تظهر أي قيمة، يمكنك بدء المشروع صراحة باستخدام git init -b main، أو ضبط القيمة الافتراضية العامة:
git config --global init.defaultBranch main
طريقتان للحصول على مستودع Git
توجد طريقتان أساسيتان لبدء العمل على مستودع Git:
بدء Git داخل مشروع محلي جديد أو موجود.
استنساخ مستودع موجود من مكان آخر.
يركز هذا الدليل على الطريقة الأولى لأنها تعرض مسار العمل كاملًا، بدءًا من مجلد عادي وصولًا إلى أول التزام.
سنتناول الاستنساخ لاحقًا عند شرح المستودعات البعيدة والعمل التعاوني.
الخطوة 1: إنشاء مجلد المشروع
على macOS أو Linux أو Git Bash
mkdir task-notes
cd task-notes
على PowerShell
New-Item -ItemType Directory task-notes
Set-Location task-notes
في هذه اللحظة، لا يزال task-notes مجلدًا عاديًا فقط، ولا يقوم Git بتتبعه.
تحقق من المسار الحالي:
pwd
في PowerShell، يعرض الأمر Get-Location المعلومة نفسها:
Get-Location
تأكد من أنك داخل مجلد المشروع المقصود قبل بدء Git. قد يؤدي تشغيل git init داخل مجلد خاطئ إلى جعل Git يراقب ملفات لم تكن تنوي إضافتها.
الخطوة 2: بدء المستودع
نفّذ:
git init -b main
ستشير النتيجة الناجحة إلى إنشاء مستودع Git فارغ.
إذا كان إصدار Git لديك أو بيئة العمل لا تدعم الخيار -b، فنفّذ:
git init
ثم تحقق من اسم الفرع الأولي:
git branch --show-current
قبل إنشاء أول التزام، قد تصف بعض الأوامر الفرع بأنه غير مولود unborn، لأن اسم الفرع موجود من الناحية المنطقية لكنه لا يشير بعد إلى أي التزام.
ماذا يفعل git init فعليًا؟
ينشئ git init مجلدًا مخفيًا باسم .git داخل المشروع. يحتوي هذا المجلد على البيانات الداخلية التي يحتاج إليها Git لإدارة المستودع.
ويتضمن بنى خاصة بـ:
الكائنات التي تمثل محتوى المشروع والالتزامات.
مراجع الفروع والعلامات.
إعدادات خاصة بالمستودع.
منطقة التجهيز، التي تُسمّى أيضًا الفهرس
index.السجلات والبيانات الوصفية المستخدمة في عمليات Git.
تبقى ملفات المشروع الظاهرة داخل مجلد العمل، بينما يخزن Git بيانات المستودع الوصفية بصورة منفصلة داخل .git.
فحص المجلد المخفي
على macOS أو Linux أو Git Bash:
ls -la
على PowerShell:
Get-ChildItem -Force
يُفترض أن ترى المجلد .git.
لا تعدّل الملفات الموجودة داخل .git يدويًا ولا تحذفها إلا إذا كنت تفهم بنية Git الداخلية ولديك خطة استعادة. يؤدي حذف هذا المجلد إلى إزالة تاريخ المستودع وإعداداته من مجلد العمل.
هل يمكن تشغيل git init مرة أخرى؟
عادةً ما يعيد تشغيل git init داخل مستودع موجود تهيئة المستودع دون حذف تاريخ الالتزامات. لكن لا حاجة إلى تشغيله بصورة متكررة، ولن ينشئ مستودعًا متداخلًا جديدًا إلا إذا شغلته داخل مجلد فرعي منفصل.
الخطوة 3: فحص الحالة الأولية للمستودع
نفّذ:
git status
يُفترض أن توضح النتيجة أنك على الفرع الأولي، وأنه لا توجد التزامات بعد، ولا يوجد حاليًا شيء يحتاج إلى الالتزام.
يُعد git status من أهم الأوامر اليومية في Git. فهو يجيب عن أسئلة مثل:
على أي فرع أعمل؟
ما الملفات غير المتتبعة؟
ما الملفات المتتبعة التي تم تعديلها؟
ما التغييرات المجهزة للالتزام التالي؟
هل شجرة العمل نظيفة؟
شغّل هذا الأمر باستمرار. فهو أمر آمن للفحص فقط ولا يغيّر الملفات أو تاريخ المستودع.
مخرجات الحالة المختصرة
يوفر Git أيضًا صيغة مختصرة:
git status --short
في هذه المرحلة، يجب ألا يعرض الأمر أي نتيجة لأن المجلد لا يحتوي على ملفات مشروع.
الخطوة 4: إنشاء أول ملف في المشروع
على macOS أو Linux أو Git Bash
cat > README.md <<'EOF'
# Task Notes
مشروع صغير للتدرب على مسار العمل الأساسي في Git.
## الميزات
- حفظ ملاحظات المهام
- تنظيم ملفات المشروع
- التدرب على إنشاء التزامات Git مفهومة
EOF
على PowerShell
@"
# Task Notes
مشروع صغير للتدرب على مسار العمل الأساسي في Git.
## الميزات
- حفظ ملاحظات المهام
- تنظيم ملفات المشروع
- التدرب على إنشاء التزامات Git مفهومة
"@ | Set-Content README.md
الآن نفّذ:
git status
يُفترض أن يضع Git الملف README.md تحت قسم Untracked files.
ما الملف غير المتتبع؟
الملف غير المتتبع هو ملف موجود داخل مجلد العمل، لكنه لم يصبح بعد جزءًا من التاريخ الذي يتتبعه Git.
يعرف Git أن الملف موجود، لكنه لن يضيفه تلقائيًا إلى أي التزام.
هذه ميزة أمان مهمة؛ فقد يحتوي مجلد المشروع على ملفات مؤقتة، أو سجلات، أو مخرجات مولدة، أو بيانات اعتماد، أو إعدادات شخصية للمحرر. لذلك يطلب Git منك اختيار الملفات الجديدة التي يجب تتبعها بصورة مقصودة.
تظهر الملفات غير المتتبعة في مخرجات الحالة المختصرة باستخدام علامتي استفهام:
git status --short
النتيجة المتوقعة:
?? README.md
الخطوة 5: تجهيز ملف README
نفّذ:
git add README.md
ثم افحص الحالة مرة أخرى:
git status
يُفترض أن يظهر الملف الآن تحت قسم Changes to be committed.
في الصيغة المختصرة:
A README.md
يعني الحرف A أن الملف أُضيف إلى منطقة التجهيز.
ما معنى git add؟
يؤدي git add وظيفتين مترابطتين:
بدء تتبع ملف جديد.
تحديث النسخة المجهزة من ملف متتبع.
لا ينشئ هذا الأمر التزامًا، بل يجهز المحتوى الدقيق الذي سيسجله الالتزام التالي.
يمكنك تصور المسار بهذه الصورة:
مجلد العمل
|
| git add README.md
v
منطقة التجهيز
|
| git commit
v
تاريخ المستودع
منطقة التجهيز لقطة محتوى وليست قائمة ملفات
يتخيل المبتدئون منطقة التجهيز غالبًا على أنها قائمة بأسماء الملفات. لكن بصورة أدق، فهي تحتوي على نُسخ الملفات التي تم اختيارها للالتزام التالي.
هذا الفرق مهم؛ فقد تجهز ملفًا ثم تعدله مرة أخرى. سيحتفظ Git بالنسخة التي جُهزت للالتزام، بينما تبقى التعديلات الأحدث داخل مجلد العمل كتغييرات غير مجهزة.
سترى هذا السلوك عمليًا لاحقًا في التمرين.
الخطوة 6: مراجعة التغيير المجهز
نفّذ:
git diff --staged
قد ترى أيضًا الصيغة المكافئة:
git diff --cached
تعرض النتيجة ما الذي سيحتويه الالتزام التالي مقارنة بالالتزام الحالي. ولأن المستودع لا يحتوي على التزام سابق، يعرض Git الملف الجديد كاملًا على أنه محتوى مضاف.
استخدم هذا الأمر قبل الالتزامات المهمة، فهو يساعدك على اكتشاف:
شيفرة تصحيح أخطاء أُضيفت بالخطأ.
تغييرات لا علاقة لها بالمهمة.
بيانات اعتماد أو معلومات خاصة.
فروقات تنسيق غير ضرورية.
ملفات جُهزت بالخطأ.
يخبرك git status بالمسارات التي جرى تجهيزها، بينما يعرض git diff --staged المحتوى الفعلي سطرًا بسطر.
الخطوة 7: إنشاء أول التزام
نفّذ:
git commit -m "إنشاء ملف README للمشروع"
يتيح الخيار -m كتابة رسالة الالتزام مباشرة داخل سطر الأوامر.
ينشئ الالتزام الناجح أول لقطة مسجلة داخل المستودع.
تحقق من الحالة:
git status
النتيجة المتوقعة:
On branch main
nothing to commit, working tree clean
قد تختلف الصياغة قليلًا بحسب إصدار Git، لكن المعنى واحد: مجلد العمل ومنطقة التجهيز متطابقان مع أحدث التزام.
ما الذي يحتويه أول التزام؟
يخزن الالتزام:
النسخة المجهزة من
README.md.هوية المؤلف ومنشئ الالتزام.
التاريخ والوقت.
الرسالة
إنشاء ملف README للمشروع.معرّفًا فريدًا للالتزام.
مرجعًا إلى لقطة المشروع.
لا يملك الالتزام الأول التزامًا أبًا، لأنه يبدأ تاريخ المشروع.
الخطوة 8: عرض تاريخ الالتزامات
نفّذ:
git log
تعرض النتيجة معرّف الالتزام والمؤلف والتاريخ والرسالة.
لعرض تاريخ مختصر:
git log --oneline
مثال:
7a93c2e إنشاء ملف README للمشروع
سيختلف المعرّف لديك.
لفحص أحدث التزام والتغييرات التي يحتويها:
git show --stat
git show --oneline
يثبت نجاح أول التزام أن Git مثبت ومضبوط وقادر على تسجيل التاريخ بصورة صحيحة.
الخطوة 9: إضافة مجلدات وملفات المشروع
على macOS أو Linux أو Git Bash
mkdir -p notes src
cat > notes/tasks.txt <<'EOF'
[ ] تعلم git status
[ ] تعلم git add
[ ] تعلم git commit
EOF
cat > src/app.txt <<'EOF'
تطبيق Task Notes
الإصدار: 0.1.0
EOF
على PowerShell
New-Item -ItemType Directory notes, src
@"
[ ] تعلم git status
[ ] تعلم git add
[ ] تعلم git commit
"@ | Set-Content notes/tasks.txt
@"
تطبيق Task Notes
الإصدار: 0.1.0
"@ | Set-Content src/app.txt
نفّذ:
git status --short
بحسب الطريقة التي يلخص بها Git المجلدات غير المتتبعة، قد ترى:
?? notes/
?? src/
يتتبع Git الملفات، وليس المجلدات الفارغة. ولا يظهر المجلد في تاريخ المستودع إلا من خلال ملف متتبع بداخله.
تجهيز ملف واحد أو مجلد أو الشجرة الحالية
يمكنك تجهيز ملف محدد:
git add notes/tasks.txt
ويمكنك تجهيز جميع التغييرات المناسبة داخل مجلد:
git add src/
ويمكنك تجهيز التغييرات الموجودة تحت المجلد الحالي:
git add .
كما يمكنك تجهيز تحديثات المستودع كاملة باستخدام:
git add -A
المهم للمبتدئ ليس حفظ كل صيغة، بل تجنب التجهيز العشوائي دون مراجعة.
بعد أمر واسع مثل git add .، راجع دائمًا:
git status
git diff --staged
يوفر التجهيز الواسع الوقت، لكنه قد يضيف ملفات لم تكن تقصد تضمينها في الالتزام.
الخطوة 10: إنشاء التزام ثانٍ محدد الهدف
جهّز قائمة المهام فقط:
git add notes/tasks.txt
تحقق من الحالة:
git status --short
يُفترض أن ترى ملف المهام مجهزًا، بينما يبقى مجلد المصدر غير متتبع.
راجع المحتوى المجهز:
git diff --staged
أنشئ الالتزام:
git commit -m "إضافة مهام التعلم الأولية"
الآن جهّز وصف التطبيق وسجله في التزام مستقل:
git add src/app.txt
git commit -m "إضافة معلومات إصدار التطبيق"
بهذا تنشئ التزامين محددين بدل التزام واسع يضم أفكارًا غير مترابطة.
اعرض التاريخ:
git log --oneline
مثال:
ca52d10 إضافة معلومات إصدار التطبيق
34e8c91 إضافة مهام التعلم الأولية
7a93c2e إنشاء ملف README للمشروع
لماذا تهم الالتزامات المركزة؟
يجب أن يمثل الالتزام وحدة عمل واحدة يسهل فهمها.
تسهّل الالتزامات المركزة:
المراجعة.
الشرح.
الاختبار.
البحث داخل التاريخ.
التراجع عند ظهور مشكلة.
نقل التغييرات بين الفروع لاحقًا.
لا يقدم التزام واحد باسم تحديث المشروع يغيّر التوثيق ومنطق التطبيق والتنسيق والإعدادات تاريخًا مفيدًا.
أما التاريخ الجيد فيوضح كيف تطور المشروع من خلال خطوات مقصودة.
الخطوة 11: تعديل ملف متتبع موجود
أضف قسمًا جديدًا إلى README.md.
على macOS أو Linux أو Git Bash
cat >> README.md <<'EOF'
## الاستخدام
افتح `notes/tasks.txt` وحدّث حالة المهام.
EOF
على PowerShell
@"
## الاستخدام
افتح `notes/tasks.txt` وحدّث حالة المهام.
"@ | Add-Content README.md
نفّذ:
git status --short
النتيجة المتوقعة:
M README.md
موضع الحرف مهم في مخرجات الحالة المختصرة. هنا يوجد التغيير داخل مجلد العمل لكنه لم يُجهز بعد.
الخطوة 12: فحص التغييرات غير المجهزة
نفّذ:
git diff
من دون خيارات إضافية، يعرض git diff التغييرات الموجودة داخل مجلد العمل والتي لم تُجهز بعد.
أي أنه يقارن بين:
مجلد العمل ومنطقة التجهيز
أما:
git diff --staged
فيقارن بين:
منطقة التجهيز وأحدث التزام
فهم هذا الفرق أساسي.
| الأمر | ما الذي يعرضه؟ |
|---|---|
git status | ملخص حالات الملفات |
git diff | التغييرات غير المجهزة سطرًا بسطر |
git diff --staged | التغييرات المجهزة للالتزام التالي سطرًا بسطر |
git log --oneline | تاريخ مختصر للالتزامات |
git show | تفاصيل التزام أو كائن Git آخر |
الخطوة 13: رؤية نسخة مجهزة وأخرى غير مجهزة من الملف نفسه
جهّز النسخة الحالية من README:
git add README.md
الآن أضف سطرًا جديدًا دون تجهيزه.
على macOS أو Linux أو Git Bash
echo "" >> README.md
echo "يُستخدم هذا المشروع للتدرب على Git." >> README.md
على PowerShell
"" | Add-Content README.md
"يُستخدم هذا المشروع للتدرب على Git." | Add-Content README.md
نفّذ:
git status --short
يُفترض أن ترى:
MM README.md
يعني الحرف M الأول أن نسخة معدلة جرى تجهيزها. ويعني الحرف M الثاني أن مجلد العمل يحتوي على تعديل إضافي غير مجهز.
افحص كل طبقة:
# يعرض السطر الإضافي غير المجهز
git diff
# يعرض تغيير README الذي جرى تجهيزه سابقًا
git diff --staged
يوضح هذا المثال لماذا تُعد منطقة التجهيز لقطة مستقلة. عند تشغيل git add README.md التقط Git الملف كما كان في تلك اللحظة، ولم تحدث التعديلات اللاحقة النسخة المجهزة تلقائيًا.
لتضمين أحدث نسخة من مجلد العمل في الالتزام، جهّز الملف مرة أخرى:
git add README.md
الآن يجب ألا يعرض:
git diff
أي فرق غير مجهز، بينما يعرض:
git diff --staged
تحديث README كاملًا.
أنشئ الالتزام:
git commit -m "توثيق الاستخدام الأساسي للمشروع"
الخطوة 14: إنشاء ملف .gitignore
تُنتج المشاريع عادة ملفات لا ينبغي إدخالها إلى إدارة الإصدارات، مثل السجلات، والمخرجات المؤقتة، وملفات البيئة المحلية، ومجلدات الاعتماديات، وملفات التخزين المؤقت الخاصة بالمحرر.
أنشئ بعض الملفات التي يجب أن تبقى محلية.
على macOS أو Linux أو Git Bash
mkdir logs
echo "مخرجات مؤقتة للتطبيق" > logs/app.log
echo "APP_SECRET=لا-تسجل-هذا" > .env
echo "ملاحظات مؤقتة" > scratch.tmp
على PowerShell
New-Item -ItemType Directory logs
"مخرجات مؤقتة للتطبيق" | Set-Content logs/app.log
"APP_SECRET=لا-تسجل-هذا" | Set-Content .env
"ملاحظات مؤقتة" | Set-Content scratch.tmp
تحقق من الحالة:
git status --short
يُفترض أن يعرض Git المسارات الجديدة غير المتتبعة.
أنشئ ملف .gitignore.
على macOS أو Linux أو Git Bash
cat > .gitignore <<'EOF'
# أسرار البيئة المحلية
.env
.env.*
# سجلات التطبيق
logs/
*.log
# الملفات المؤقتة
*.tmp
# ملفات شائعة خاصة بأنظمة التشغيل
.DS_Store
Thumbs.db
EOF
على PowerShell
@"
# أسرار البيئة المحلية
.env
.env.*
# سجلات التطبيق
logs/
*.log
# الملفات المؤقتة
*.tmp
# ملفات شائعة خاصة بأنظمة التشغيل
.DS_Store
Thumbs.db
"@ | Set-Content .gitignore
نفّذ:
git status --short
يُفترض أن تختفي الملفات المتجاهلة من مخرجات الحالة العادية. ويبقى ملف .gitignore نفسه ظاهرًا لأنه يجب تسجيله كجزء من سياسة المشروع.
جهّزه وسجله:
git add .gitignore
git commit -m "تجاهل الأسرار المحلية والسجلات والملفات المؤقتة"
كيف تعمل أنماط .gitignore؟
تشمل الأنماط الشائعة:
# تجاهل ملف محدد
.env
# تجاهل جميع ملفات .log
*.log
# تجاهل مجلد ومحتوياته
logs/
# تجاهل الملفات المؤقتة في أي مكان
*.tmp
# تجاهل ملف موجود فقط في جذر المستودع
/config.local.php
# تجاهل كل شيء داخل build مع إبقاء ملف مطلوب
build/*
!build/.gitkeep
يُتجاهل السطر الفارغ، وتُعد الأسطر التي تبدأ بـ # تعليقات ما لم يُستخدم رمز الهروب.
يجب أن يصف ملف .gitignore على مستوى المستودع قواعد المشروع المشتركة. ويمكن حفظ أنماط المحرر ونظام التشغيل الشخصية داخل ملف تجاهل عام يخص مطورًا واحدًا.
.gitignore لا يؤثر في الملفات المتتبعة
هذه من أكثر النقاط التي تفاجئ المبتدئين.
إذا كان الملف متتبعًا بالفعل، فإن إضافة اسمه إلى .gitignore لن تزيله من تاريخ Git ولن تمنع Git من ملاحظة تعديلاته المستقبلية.
تنطبق قواعد التجاهل على الملفات المقصود إبقاؤها غير متتبعة.
لإيقاف تتبع ملف مع إبقائه داخل مجلد العمل:
git rm --cached path/to/file
ثم سجّل عملية إزالته من فهرس المستودع.
ولمجلد كامل:
git rm -r --cached path/to/directory
استخدم هذه الأوامر بحذر وراجع النتيجة المجهزة قبل الالتزام.
تشخيص قاعدة تجاهل
إذا لم تفهم لماذا يتجاهل Git ملفًا معينًا، فاستخدم:
git check-ignore -v logs/app.log
تعرض النتيجة ملف التجاهل والنمط المسؤول عن التطابق.
لعرض الملفات المتجاهلة داخل مخرجات الحالة:
git status --ignored --short
يفيد هذا الأمر عندما يبدو أن ملفًا مطلوبًا مفقود من المستودع.
الخطوة 15: إضافة مهمة أخرى وتسجيلها
حدّث notes/tasks.txt.
على macOS أو Linux أو Git Bash
cat > notes/tasks.txt <<'EOF'
[x] تعلم git status
[x] تعلم git add
[x] تعلم git commit
[ ] تعلم فروع Git
EOF
على PowerShell
@"
[x] تعلم git status
[x] تعلم git add
[x] تعلم git commit
[ ] تعلم فروع Git
"@ | Set-Content notes/tasks.txt
راجع التغيير:
git status
git diff
جهّزه:
git add notes/tasks.txt
راجع بدقة ما جرى تجهيزه:
git diff --staged
أنشئ الالتزام:
git commit -m "تحديث مهام تعلم Git المكتملة"
الخطوة 16: إعادة تسمية ملف متتبع
أعد تسمية src/app.txt إلى src/version.txt.
استخدم أمر النقل في Git:
git mv src/app.txt src/version.txt
تحقق من الحالة:
git status --short
يُفترض أن يعرض Git إعادة تسمية مجهزة، ويُعبَّر عنها غالبًا بالحرف R.
أنشئ الالتزام:
git commit -m "إعادة تسمية ملف معلومات التطبيق"
هل يخزن Git عمليات إعادة التسمية مباشرة؟
يسجل Git اللقطات عادة، ثم يكتشف عمليات إعادة التسمية لاحقًا من خلال مقارنة تشابه المحتوى. ويُعد git mv اختصارًا عمليًا يجمع بين نقل الملف داخل نظام الملفات وتجهيز عملية الحذف والإضافة المرتبطة به.
يمكنك أيضًا إعادة تسمية الملف بأمر من نظام التشغيل ثم تجهيز التغييرات. وقد يتعرف Git على النتيجة باعتبارها إعادة تسمية.
الخطوة 17: حذف ملف متتبع
لأغراض الشرح، أنشئ ملفًا قديمًا وسجله أولًا.
على macOS أو Linux أو Git Bash
echo "مسودة قديمة" > old-notes.txt
git add old-notes.txt
git commit -m "إضافة مسودة مؤقتة للمشروع"
على PowerShell
"مسودة قديمة" | Set-Content old-notes.txt
git add old-notes.txt
git commit -m "إضافة مسودة مؤقتة للمشروع"
الآن احذفه من خلال Git:
git rm old-notes.txt
يحذف هذا الأمر الملف من مجلد العمل ويجهز عملية الحذف.
راجع:
git status
git diff --staged
أنشئ الالتزام:
git commit -m "إزالة مسودة المشروع القديمة"
يمكن أيضًا حذف ملف متتبع باستخدام أمر من نظام التشغيل، لكن يجب تجهيز الحذف بعد ذلك.
فهم دورة حياة الملف
يمكن أن ينتقل الملف بين عدة حالات:
ملف جديد
|
v
غير متتبع
|
| git add
v
مجهز
|
| git commit
v
متتبع ومسجل
|
| تعديل الملف
v
متتبع ومعدل
|
| git add
v
مجهز من جديد
|
| git commit
v
نسخة جديدة مسجلة
يمكن أيضًا حذف الملف المتتبع أو إعادة تسميته أو إزالته عمدًا من الفهرس.
| الحالة | المعنى | الإجراء التالي المعتاد |
|---|---|---|
| Untracked | الملف موجود لكن Git لا يتتبعه | استخدام git add أو إضافة قاعدة تجاهل |
| Modified | ملف متتبع يختلف عن نسخته المجهزة | مراجعته باستخدام git diff |
| Staged | النسخة المحددة جاهزة للالتزام التالي | المراجعة ثم الالتزام |
| Committed | النسخة مسجلة داخل تاريخ المستودع | متابعة التطوير |
| Ignored | مسار غير متتبع يطابق قاعدة تجاهل | تركه محليًا عادة |
قراءة git status --short
تستخدم الصيغة المختصرة عمودين للحالة:
XY PATH
X: الفرق بين أحدث التزام ومنطقة التجهيز.
Y: الفرق بين منطقة التجهيز ومجلد العمل.
أمثلة شائعة:
?? file.txt ملف غير متتبع
A file.txt ملف جديد مجهز
M file.txt ملف متتبع معدل لكنه غير مجهز
M file.txt نسخة معدلة مجهزة
MM file.txt تغيير مجهز مع تغيير إضافي غير مجهز
D file.txt حذف مجهز
R old -> new إعادة تسمية مجهزة
تُعد مخرجات الحالة الطويلة أسهل للمبتدئين، بينما تصبح الصيغة المختصرة مفيدة للفحص اليومي السريع والسكربتات.
أوامر مفيدة لمسارات محددة
لفحص ملف واحد فقط:
git status --short README.md
لعرض التغييرات غير المجهزة في ملف واحد:
git diff -- README.md
لعرض التغييرات المجهزة في ملف واحد:
git diff --staged -- README.md
لتجهيز مجلد واحد:
git add notes/
تفصل علامتا الشرطة بين خيارات الأمر والمسارات. ويصبح ذلك مفيدًا خصوصًا عندما يشبه اسم الملف أحد الخيارات أو عندما تصبح صياغة الأمر أكثر تعقيدًا.
ما الذي قد يضيفه git add . بالخطأ؟
الأمر:
git add .
مريح، لكنه قد يجهز:
مخرجات تصحيح الأخطاء.
ملفات مؤقتة.
مخرجات بناء مولدة.
ملفات كبيرة.
إعدادات محلية.
بيانات اعتماد لم تُضف إلى التجاهل.
تعديلات لا علاقة لها بالمهمة الحالية.
استخدم التسلسل الآمن التالي:
git status
git add .
git status
git diff --staged
git commit -m "صِف التغيير المنطقي"
لا تفترض أبدًا أن أمر تجهيز واسع اختار الملفات التي تقصدها فقط.
لا تسجل الأسرار داخل Git
قبل أول التزام، وقبل إضافة ملفات إعداد جديدة، تحقق من عدم وجود:
كلمات مرور.
مفاتيح API.
سلاسل اتصال بقواعد البيانات.
بيانات اعتماد الخدمات السحابية.
مفاتيح SSH خاصة.
رموز وصول.
ملفات بيئة إنتاج حقيقية.
تساعد إضافة .env إلى .gitignore على منع تتبعه بالخطأ، لكن قواعد التجاهل ليست نظام حماية. راجع المحتوى المجهز قبل الالتزام.
إذا سُجل سر حقيقي داخل التزام، فإن حذفه في التزام لاحق لا يجعل القيمة القديمة آمنة. قم بتدوير السر أو إلغائه فورًا، ثم نظّف التاريخ باستخدام إجراء مناسب.
فحص المستودع النهائي
نفّذ:
git status
git log --oneline --decorate
يُفترض أن تعرض الحالة شجرة عمل نظيفة.
افحص الملفات المتتبعة:
git ls-files
المحتوى المتتبع المتوقع:
.gitignore
README.md
notes/tasks.txt
src/version.txt
يجب ألا تظهر الملفات المتجاهلة .env وlogs/app.log وscratch.tmp.
افحص الملفات المتجاهلة بصورة منفصلة:
git status --ignored --short
اعرض التاريخ على شكل رسم:
git log --oneline --graph --decorate --all
لأنه لا توجد فروع متباعدة حتى الآن، سيظهر الرسم كسلسلة مستقيمة من الالتزامات.
تتبع يدوي: ما الذي تغيّر بعد كل أمر؟
يلخص التتبع التالي الحالة الداخلية خلال التمرين.
1. قبل git init
مجلد العمل: موجود
مجلد .git: غير موجود
تاريخ المستودع: غير موجود
منطقة التجهيز: غير موجودة
2. بعد git init -b main
مجلد العمل: موجود
مجلد .git: أُنشئ
الفرع الحالي: main
الالتزامات: لا توجد
منطقة التجهيز: فارغة
3. بعد إنشاء README.md
README.md: غير متتبع
منطقة التجهيز: فارغة
الالتزامات: لا توجد
4. بعد git add README.md
README.md: متتبع ومجهز
منطقة التجهيز: تحتوي على لقطة README.md
الالتزامات: لا توجد
5. بعد أول git commit
README.md: متتبع ومسجل
أحدث التزام: إنشاء ملف README للمشروع
منطقة التجهيز: مطابقة لأحدث التزام
شجرة العمل: نظيفة
6. بعد تعديل README.md
النسخة المسجلة: محفوظة كما هي
النسخة المجهزة: ما زالت مطابقة للنسخة المسجلة
نسخة العمل: معدلة
git diff: يعرض التعديل الجديد
7. بعد التجهيز ثم التعديل مرة أخرى
النسخة المسجلة: المحتوى الأصلي المسجل
النسخة المجهزة: التعديل الجديد الأول
نسخة العمل: التعديل الأول مع التعديل الثاني
git diff --staged: يعرض التعديل الأول
git diff: يعرض التعديل الثاني
8. بعد التجهيز مرة أخرى ثم الالتزام
النسخة المسجلة: تحتوي على التعديلين
منطقة التجهيز: مطابقة لأحدث التزام
مجلد العمل: مطابق لمنطقة التجهيز
شجرة العمل: نظيفة
هذا هو نموذج Git الأساسي أثناء العمل.
أخطاء شائعة لدى المبتدئين
تشغيل git init داخل المجلد الخطأ
تحقق دائمًا من المسار الحالي قبل التهيئة. قد يبدأ مستودع أُنشئ في مستوى مرتفع من نظام الملفات بمراقبة ملفات لا علاقة لها بالمشروع.
افتراض أن git add ينشئ التزامًا
يجهز git add المحتوى، بينما يسجله git commit في التاريخ.
افتراض أن git commit يشمل كل الملفات المعدلة
يسجل الالتزام العادي المحتوى المجهز فقط. وتبقى التغييرات غير المجهزة والملفات غير المتتبعة خارج الالتزام.
استخدام git add . دون مراجعة
قد يضيف التجهيز الواسع ملفات غير مرتبطة أو حساسة. افحص الحالة والفرق المجهز معًا.
إنشاء “التزام أولي” ضخم دون فحص
حتى الالتزام الأول يجب أن يستبعد الملفات المولدة والاعتماديات والسجلات والأسرار والإعدادات المحلية.
إضافة ملف سري متتبع إلى .gitignore
لا توقف قواعد التجاهل Git عن تتبع ملف موجود بالفعل في التاريخ.
تعديل الملفات داخل .git
يمثل مجلد .git البنية الداخلية للمستودع. تعامل معه على أنه جزء داخلي ما لم تكن تدرس بنية Git عن قصد.
كتابة رسائل التزام بلا معنى
لا توضح رسائل مثل تغييرات أو تحديث أو إصلاح الغرض من اللقطة.
خلط عدة مهام داخل التزام واحد
يُفضّل فصل التوثيق وإعادة الهيكلة وإصلاح الأخطاء والميزات الجديدة عندما تمثل تغييرات منطقية مختلفة.
أفضل الممارسات لأول مستودعاتك
ابدأ Git في جذر المشروع.
أنشئ
.gitignoreقبل تجهيز مشروع كبير.شغّل
git statusبصورة متكررة.راجع العمل غير المجهز باستخدام
git diff.راجع الالتزام التالي باستخدام
git diff --staged.جهّز الملفات بوعي.
اجعل الالتزامات محددة الهدف.
اكتب رسائل التزام واضحة وموجهة إلى الفعل.
لا تسجل الأسرار أبدًا.
حاول إنهاء كل مهمة مكتملة بشجرة عمل نظيفة عندما يكون ذلك عمليًا.
مرجع الأوامر المستخدمة في هذا الدليل
| الأمر | الغرض |
|---|---|
git init -b main | بدء مستودع بفرع أولي اسمه main |
git status | عرض معلومات تفصيلية عن شجرة العمل ومنطقة التجهيز |
git status --short | عرض رموز الحالة المختصرة |
git add file | تجهيز النسخة الحالية من ملف واحد |
git add . | تجهيز التغييرات المناسبة تحت المجلد الحالي |
git diff | عرض التغييرات غير المجهزة |
git diff --staged | عرض التغييرات المجهزة للالتزام التالي |
git commit -m "message" | إنشاء التزام من المحتوى المجهز |
git log --oneline | عرض تاريخ الالتزامات بصورة مختصرة |
git show | فحص أحدث التزام بصورة افتراضية |
git check-ignore -v path | توضيح قاعدة التجاهل التي تطابق المسار |
git mv old new | نقل ملف أو إعادة تسميته وتجهيز النتيجة |
git rm file | إزالة ملف متتبع وتجهيز الحذف |
git ls-files | عرض الملفات التي يتتبعها الفهرس حاليًا |
قائمة التحقق للبدء
قبل الانتقال إلى المقالة الأكثر تعمقًا حول التجهيز والالتزامات، تأكد من أنك تستطيع:
إنشاء مجلد مشروع.
بدء مستودع باستخدام
git init.شرح وظيفة مجلد
.git.تمييز ملف غير متتبع.
تجهيز ملف محدد.
إنشاء التزام برسالة واضحة.
تمييز الفرق بين
git diffوgit diff --staged.شرح كيف يمكن لملف مجهز أن يحتوي أيضًا على تغييرات غير مجهزة.
إنشاء ملف
.gitignoreواختباره.إدراك أن الملفات المتتبعة لا تتأثر بقواعد التجاهل الجديدة.
قراءة رموز الحالة المختصرة الشائعة.
التحقق من أن المستودع يملك شجرة عمل نظيفة.
الأسئلة الشائعة
هل يمكن تشغيل git init داخل مشروع موجود؟
نعم. يمكن بدء Git داخل مجلد مشروع موجود. أنشئ ملف .gitignore مناسبًا وافحص جميع الملفات غير المتتبعة قبل تجهيز أول التزام.
هل يرفع git init المشروع إلى الإنترنت؟
لا. ينشئ مستودعًا محليًا فقط. يتطلب رفع الالتزامات أو مشاركتها مستودعًا بعيدًا وعملية push لاحقة.
هل يتتبع Git المجلدات الفارغة؟
لا. يتتبع Git محتوى الملفات. تضع المشاريع أحيانًا ملفًا مثل .gitkeep داخل مجلد فارغ، لكن هذا الاسم لا يملك معنى خاصًا مدمجًا في Git.
ما الفرق بين git add وgit commit؟
يجهز git add نُسخ الملفات المحددة داخل منطقة التجهيز، بينما يسجل git commit اللقطة المجهزة داخل تاريخ المستودع.
لماذا لا يعرض git diff شيئًا بعد git add؟
يعرض git diff العادي التغييرات غير المجهزة فقط. بعد التجهيز، استخدم git diff --staged لفحص المحتوى المعد للالتزام التالي.
هل يمكن تسجيل ملف واحد فقط؟
نعم. جهّز ذلك الملف وحده، وراجع الفرق المجهز، ثم أنشئ الالتزام.
هل يجب استخدام git add . دائمًا؟
لا. هو مريح عندما تنتمي جميع التغييرات الحالية إلى المهمة نفسها، لكن تجهيز مسارات محددة أو استخدام التجهيز التفاعلي يمنحك تحكمًا أفضل عندما تختلط عدة مهام.
لماذا لا يزال الملف المتجاهل متتبعًا؟
غالبًا تم تسجيل الملف أو تجهيزه قبل إضافة قاعدة التجاهل. لا تؤثر أنماط التجاهل في الملفات المتتبعة بالفعل.
ما معنى “Working Tree Clean”؟
يعني أن Git لا يرى تعديلات متتبعة أو فروقات مجهزة أو ملفات غير متتبعة قابلة للإبلاغ مقارنة بالالتزام الحالي وقواعد التجاهل.
هل يمكن حذف مجلد .git؟
يعيد حذفه مجلد العمل إلى مجلد عادي ويزيل بيانات المستودع المحلية وتاريخه. افعل ذلك فقط عندما يكون هذا مقصدك الصريح، وبعد التأكد من حفظ أي تاريخ مطلوب في مكان آمن آخر.
الخلاصة
يعرض أول مستودع Git لك مسار العمل الأساسي كاملًا: بدء المشروع، وإنشاء الملفات، وفحص حالاتها، وتجهيز النسخ المحددة، ومراجعة المحتوى المجهز، وتسجيل التزامات واضحة.
أهم درس هو أن Git يدير عدة حالات في الوقت نفسه. يحتوي مجلد العمل على التعديلات الحالية، وتحتوي منطقة التجهيز على اللقطة المقترحة للالتزام التالي، بينما يخزن المستودع التاريخ المسجل. وتكشف أوامر مثل git status وgit diff وgit diff --staged الفروق بين هذه الحالات.
مسار العمل المنظم بسيط: افحص الحالة، وعدّل، وافحص مجددًا، وجهّز بوعي، وراجع الفرق المجهز، وأنشئ التزامًا برسالة مفهومة، ثم تحقق من الحالة النهائية.
ستتناول المقالة التالية التجهيز والالتزامات بمزيد من التفصيل، بما يشمل التجهيز الجزئي، وإخراج التغييرات من منطقة التجهيز، وتعديل الالتزامات، وبنية رسائل الالتزام، واستراتيجيات إنشاء تاريخ نظيف ومفيد.
المراجع الرسمية ومواد إضافية للقراءة

