Mundarija (38)
- Bu darsda
- 1. Nega bu kerak?
- 2. "Rejected" — GitHub nega rad etadi?
- 2.1 fetch first
- 2.2 non-fast-forward
- 2.3 Holatni ko'rish
- 3. Birlashtirishning uch yo'li
- 3.1 Sozlamasiz git pull nima qiladi?
- 3.2 Merge (--no-rebase)
- 3.3 Faqat fast-forward (--ff-only)
- 3.4 Rebase (--rebase)
- 4. Doimiy sozlama: pull.rebase
- 4.1 Yarim ish bilan pull
- 5. git pull --rebase paytida conflict
- 6. Yuborilgan commitni o'zgartirsangiz
- 7. --force nega xavfli: real voqea
- 7.1 Tuzoq ichidagi tuzoq
- 8. --force-with-lease — xavfsiz majburlash
- 8.1 Qanday ishlaydi?
- 8.2 To'g'ri yo'l: feature branchni yangilash
- 8.3 Lease'ni nima aldaydi?
- 8.4 Qoidalar
- 9. Upstream'ni qo'lda sozlash: git branch -u
- 10. Ko'p uchraydigan xatolar
- 10.1 Ko'r-ko'rona --force
- 10.2 Need to specify how to reconcile divergent branches
- 10.3 Tarixda "Merge branch 'main' of ..." commitlari to'planib qoldi
- 10.4 cannot pull with rebase: You have unstaged changes
- 10.5 Conflict o'rtasida qolib ketish
- 10.6 (forced update) ni e'tiborsiz qoldirish
- 11. Mashqlar
- 1-mashq (oson): Xabarni tarjima qiling
- 2-mashq (o'rta): Bo'sh joylarni to'ldiring
- 3-mashq (qiyin): Kim aybdor va nima qilamiz?
- 4-mashq: Portfolio qadami — GitHub'da tahrir, kompyuterda commit
- 12. Real ishda
- Xulosa
- Manbalar
Git push rejected: ajralgan tarix, git pull --rebase va --force-with-lease
Qisqacha:
! [rejected] ... (non-fast-forward)— GitHub'da sizda yo'q commit bor, oddiy push uni o'chirib yuborardi. Yechim — avval birlashtirish:git pull --rebasesizning yuborilmagan commitlaringizni GitHub'dagilar ustiga qayta teradi va tarix to'g'ri chiziq bo'lib qoladi. Doimiy qilish uchungit config --global pull.rebase true. Tarixni ataylab qayta yozgan bo'lsangiz (amend, rebase),--forceemas,--force-with-leaseishlating: u siz ko'rmagan boshqa odamning commitini o'chirib yubormaydi.
Bu darsda
rejected (fetch first)varejected (non-fast-forward)xatolarini o'qib, sababini tushuntira olasiz.- Ajralgan tarixni uch yo'l bilan — merge, rebase, ff-only — birlashtirasiz va farqini bilasiz.
pull.rebasevapull.ffsozlamalarini tanlab, qo'ya olasiz.git pull --rebasepaytidagi conflictni yechasiz.--forcenega xavfli ekanini real misolda ko'rasiz va--force-with-leasebilan xavfsiz yuborasiz.git branch -ubilan upstream'ni sozlaysiz.
Oldin bilishingiz kerak: Remote: clone, fetch, pull, push, Rebase: tarixni chiziqlash va oltin qoida, Merge: fast-forward va uch tomonlama birlashtirish.
1. Nega bu kerak?
Oldingi darsda hamma narsa silliq o'tdi: Sardor yubordi, Aziz git pull qildi — fast-forward. Chunki ular navbat bilan ishladi. Haqiqiy jamoada esa ikki kishi bir vaqtda commit qiladi.
Dushanba, soat 10:00. Sardor menyuga lag'mon narxini qo'shib, yubordi. Besh daqiqadan keyin Aziz bosh sahifaga ish vaqtini yozdi va u ham yubormoqchi. Endi bitta main ning ikki xil davomi bor — tarix ayrildi.
Bu darsda ayrilgan tarixni qanday birlashtirishni va tarixni qayta yozish kerak bo'lganda boshqalarning ishini qanday buzmaslikni o'rganamiz. Oldingi darslarda — amend, reset va rebase da — "yuborilgan commitga tegmang, bu holatni keyinroq ko'ramiz" degan edik — o'sha "keyinroq" keldi.
Biz darsdagi hamma buyruqni vaqtinchalik sinov reposida, ikki alohida nusxada (Aziz va Sardor) ishga tushirdik. Chiqishlarda repo nomi login/bahor ga almashtirilgan. Sinov reposidagi «Bahor» tarixi qisqa: Birinchi repo darsining dastlabki commitlari, qisqaroq nomlar bilan (Menyu: osh narxi, Aloqa sahifasi). Sizda tarix uzunroq, nomlar va SHA'lar boshqacha — bu darsdagi xabarlar va ularning ma'nosi esa aynan shunday.
2. "Rejected" — GitHub nega rad etadi?
2.1 fetch first
Aziz o'z commitini yubormoqchi:
git pushTo https://github.com/login/bahor.git
! [rejected] main -> main (fetch first)
error: failed to push some refs to 'https://github.com/login/bahor.git'
hint: Updates were rejected because the remote contains work that you do not
hint: have locally. This is usually caused by another repository pushing to
hint: the same ref. If you want to integrate the remote changes, use
hint: 'git pull' before pushing again.
hint: See the 'Note about fast-forwards' in 'git push --help' for details.Tarjimasi: "Rad etildi (avval fetch qiling). Yangilanish rad etildi, chunki remote'da sizda yo'q ish bor. Odatda buning sababi — boshqa repo shu branchga yuborgan. Remote'dagi o'zgarishlarni qo'shmoqchi bo'lsangiz, qayta yuborishdan oldin git pull qiling."
fetch first — Git GitHub'dagi yangi commitni hatto tanimaydi ham: u Azizning kompyuterida yo'q.
2.2 non-fast-forward
Aziz fetch qiladi va yana urinadi:
git fetch
git pushFrom https://github.com/login/bahor
c850598..0e3a9e1 main -> origin/main
To https://github.com/login/bahor.git
! [rejected] main -> main (non-fast-forward)
error: failed to push some refs to 'https://github.com/login/bahor.git'
hint: Updates were rejected because the tip of your current branch is behind
hint: its remote counterpart. If you want to integrate the remote changes,
hint: use 'git pull' before pushing again.
hint: See the 'Note about fast-forwards' in 'git push --help' for details.Endi sabab boshqacha yozilgan: "joriy branchingizning uchi remote'dagi juftidan orqada". Git endi Sardorning commitini taniydi va aniq aytadi: bu yuborish fast-forward emas.
Nima degani? Push faqat GitHub'dagi main ni oldinga surishi mumkin — xuddi fast-forward merge kabi. GitHub'dagi main ning oxirgi commiti sizning tarixingizda bo'lishi kerak. Bu yerda esa u yo'q: Azizning commiti Sardorning commiti ustida emas, yonida turibdi. Oddiy push Sardorning commitini GitHub'dan o'chirib yuborardi — Git bunga yo'l qo'ymaydi.
2.3 Holatni ko'rish
git status
git log --oneline --graph --all -5On branch main
Your branch and 'origin/main' have diverged,
and have 1 and 1 different commits each, respectively.
(use "git pull" if you want to integrate the remote branch with yours)
nothing to commit, working tree clean
* ee392b2 (HEAD -> main) Bosh sahifa: ish vaqtini qo'sh
| * 0e3a9e1 (origin/main, origin/HEAD) Menyu: lag'mon narxini qo'sh
|/
* c850598 Git: .gitattributes qo'sh
* 5221077 Aloqa sahifasi
* 7bb2607 Menyu: osh narxi"Branchingiz va origin/main ayrilgan: mos ravishda 1 va 1 ta farqli commit." Birinchi son — sizda bor, GitHub'da yo'q; ikkinchisi — aksincha.
gitGraph
commit id: "c850598"
branch origin/main
commit id: "0e3a9e1 lag'mon"
checkout main
commit id: "ee392b2 ish vaqti"Nimaga qarang: ikkala commit ham c850598 dan o'sib chiqqan. Birini ikkinchisiga "ulash" kerak — buning uch yo'li bor.
Tekshirib ko'ring:
git statushave 3 and 0 different commits eachdesa-chi? Bunday yozuv chiqmaydi — nega? Uning o'rniga nima chiqadi?
Javob
Ikkinchi son 0 bo'lsa, GitHub'da sizda yo'q commit yo'q — tarix ayrilmagan, siz shunchaki oldindasiz. Status Your branch is ahead of 'origin/main' by 3 commits. deydi va oddiy git push ishlaydi.
3. Birlashtirishning uch yo'li
3.1 Sozlamasiz git pull nima qiladi?
Avval qaysi sozlama borligini ko'ramiz:
git config --show-scope --get-all pull.rebasesystem falseGit'ni o'rnatish darsidagi jadvalni eslang: Git for Windows o'rnatuvchisi system faylga pull.rebase=false yozgan. Shuning uchun Windows'da git pull merge qiladi. macOS va Linux'da bu sozlama odatda yo'q. U yerda Git to'xtaydi va tanlashni so'raydi. Buni system faylni o'chirib ko'rib sinadik:
hint: You have divergent branches and need to specify how to reconcile them.
hint: You can do so by running one of the following commands sometime before
hint: your next pull:
hint:
hint: git config pull.rebase false # merge
hint: git config pull.rebase true # rebase
hint: git config pull.ff only # fast-forward only
hint:
hint: You can replace "git config" with "git config --global" to set a default
hint: preference for all repositories. You can also pass --rebase, --no-rebase,
hint: or --ff-only on the command line to override the configured default per
hint: invocation.
fatal: Need to specify how to reconcile divergent branches.Tarjimasi: "Branchlaringiz ayrilgan, ularni qanday yarashtirishni ko'rsating. Keyingi pull'dan oldin quyidagilardan birini bajaring: merge, rebase yoki faqat fast-forward." Git uch yo'lni aniq sanab berdi. Har birini ko'ramiz.
3.2 Merge (--no-rebase)
Windows'dagi odatiy git pull:
git pullMerge made by the 'ort' strategy.
menyu/index.html | 1 +
1 file changed, 1 insertion(+)Merge commit yaratildi. Undan oldin VS Code xabar oynasini ochadi (core.editor) — tayyor xabarni saqlab, yopasiz. Tarix:
* 4bf0a00 (HEAD -> main) Merge branch 'main' of https://github.com/login/bahor
|\
| * 0e3a9e1 (origin/main, origin/HEAD) Menyu: lag'mon narxini qo'sh
* | ee392b2 Bosh sahifa: ish vaqtini qo'sh
|/
* c850598 Git: .gitattributes qo'shIshladi, lekin Merge branch 'main' of https://... degan commit hech qanday foydali ma'lumot bermaydi. Kuniga besh marta pull qilsangiz — tarixda besh shunday commit. Ko'p jamoalar buni "shovqin" deb hisoblaydi.
(Sinovdan keyin bu merge'ni git reset --hard HEAD~1 bilan bekor qildik — Reset darsidagi usul, chunki u hali yuborilmagan edi.)
3.3 Faqat fast-forward (--ff-only)
git pull --ff-onlyhint: Diverging branches can't be fast-forwarded, you need to either:
hint:
hint: git merge --no-ff
hint:
hint: or:
hint:
hint: git rebase
hint:
hint: Disable this message with "git config set advice.diverging false"
fatal: Not possible to fast-forward, aborting."Fast-forward mumkin emas, to'xtatildi." --ff-only hech narsani birlashtirmaydi: tarix ayrilgan bo'lsa — to'xtaydi va qaror sizga qoladi. Bu "ehtiyot rejimi": siz bilmasdan merge commit paydo bo'lmaydi (Merge darsida --ff-only haqida aytgan edik).
3.4 Rebase (--rebase)
git pull --rebase
git log --oneline --graph -4Successfully rebased and updated refs/heads/main.
* 1ef64f4 (HEAD -> main) Bosh sahifa: ish vaqtini qo'sh
* 0e3a9e1 (origin/main, origin/HEAD) Menyu: lag'mon narxini qo'sh
* c850598 Git: .gitattributes qo'sh
* 5221077 Aloqa sahifasiBu safar merge commit yo'q. git pull --rebase avval fetch qildi, keyin Azizning commitini Sardorning commiti ustiga qayta terdi — Rebase darsidagidek. Commit yangi SHA oldi (ee392b2 → 1ef64f4), tarix — to'g'ri chiziq. Endi bu fast-forward:
git pushTo https://github.com/login/bahor.git
0e3a9e1..1ef64f4 main -> mainOltin qoida buzilmadimi? Yo'q. Qayta yozilgan commit — ee392b2 — hali hech kimga yuborilmagan edi. Rebase faqat sizning yuborilmagan commitlaringizga tegadi, GitHub'dagilari o'zgarmaydi.
| Yo'l | Buyruq | Tarix | Qachon |
|---|---|---|---|
| Merge | git pull --no-rebase |
Ayrilish + merge commit | Jamoa shunday kelishgan bo'lsa |
| Rebase | git pull --rebase |
To'g'ri chiziq | Ko'p jamoalarda odatiy |
| Faqat FF | git pull --ff-only |
Ayrilsa — to'xtaydi | Ehtiyot rejimi |
Tekshirib ko'ring: Nega
git pull --rebasedan keyin Azizning commiti boshqa SHA oldi, Sardorniki esa o'zgarmadi?
Javob
SHA commitning mazmuni va ota commitidan hisoblanadi (Git ichkaridan). Azizning commiti endi boshqa otaga — Sardorning commitiga — ulandi, shuning uchun yangi SHA. Sardorning commiti esa GitHub'dan qanday kelgan bo'lsa, shunday qoldi: rebase faqat lokal, yuborilmagan commitlarni ko'chiradi.
4. Doimiy sozlama: pull.rebase
Har safar --rebase yozmaslik uchun Rebase darsida va'da qilingan sozlamani qo'yamiz:
git config --global pull.rebase true
git config --show-scope --get-all pull.rebase
git config --get pull.rebasesystem false
global true
trueIkki qiymat bor: system'da false, global'da true. Qaysi biri ishlaydi? Git'ni o'rnatish darsidagi qoida: yaqinroq daraja ustun. git config --get buni tasdiqlaydi — natija true. Endi oddiy git pull rebase qiladi.
Muqobili — git config --global pull.ff only: hamma pull faqat fast-forward, ayrilsa — o'zingiz hal qilasiz. Kursda biz pull.rebase true ni tavsiya qilamiz — u eng ko'p tarqalgan.
4.1 Yarim ish bilan pull
Rebase toza ishchi papka talab qiladi. Commit qilinmagan o'zgarish bo'lsa:
error: cannot pull with rebase: You have unstaged changes.
error: Please commit or stash them."Rebase bilan pull qilib bo'lmaydi: commit qilinmagan o'zgarishlar bor. Ularni commit yoki stash qiling." Stash darsidagi yo'l — git stash, git pull, git stash pop. Buni bitta flag qiladi: git pull --rebase --autostash — Git o'zgarishlarni vaqtincha javonga qo'yadi va pull'dan keyin qaytaradi. Doimiy qilish: git config --global rebase.autoStash true.
5. git pull --rebase paytida conflict
Ikkalasi bitta qatorni o'zgartirsa nima bo'ladi? Sardor ish vaqtini 8:00–23:00 qildi va yubordi. Aziz esa o'sha qatorga "har kuni" so'zini qo'shdi. Aziz pull qiladi (endi pull.rebase true):
git pullFrom https://github.com/login/bahor
1ef64f4..9a65906 main -> origin/main
Auto-merging index.html
CONFLICT (content): Merge conflict in index.html
error: could not apply a8549ec... Bosh sahifa: "har kuni" so'zini qo'sh
hint: Resolve all conflicts manually, mark them as resolved with
hint: "git add/rm <conflicted_files>", then run "git rebase --continue".
hint: You can instead skip this commit: run "git rebase --skip".
hint: To abort and get back to the state before "git rebase", run "git rebase --abort".
hint: Disable this message with "git config set advice.mergeConflict false"
Could not apply a8549ec... # Bosh sahifa: "har kuni" so'zini qo'shTanish manzara — Conflictlarni yechish va Rebase darslaridagidek. (Bir lahzaga Rebasing (1/1) yozuvi ham chiqadi — rebase jarayoni hisoblagichi, keyingi qator uni bosib ketadi.) Faylda:
<h1>Bahor choyxonasi</h1>
<a href="aloqa/">Aloqa</a>
<<<<<<< HEAD
<p>Ish vaqti: 8:00–23:00</p>
=======
<p>Ish vaqti: har kuni 7:00–23:00</p>
>>>>>>> a8549ec (Bosh sahifa: "har kuni" so'zini qo'sh)Diqqat: rebase'da HEAD — GitHub'dan kelgan versiya (Sardorniki), pastdagi — siz qayta terayotgan commit. Merge'dagidan teskari tuyuladi, chunki rebase sizning commitingizni boshqaning tarixi ustiga qo'yyapti.
Ikkalasini birlashtiramiz — Sardorning vaqti va Azizning so'zi:
<p>Ish vaqti: har kuni 8:00–23:00</p>git add index.html
git rebase --continue
git push[detached HEAD f42cff1] Bosh sahifa: "har kuni" so'zini qo'sh
1 file changed, 1 insertion(+), 1 deletion(-)
Successfully rebased and updated refs/heads/main.
To https://github.com/login/bahor.git
9a65906..f42cff1 main -> main--continue paytida commit xabarini tasdiqlash uchun muharrir ochiladi — saqlab, yopasiz. Adashib ketsangiz — git rebase --abort: hammasi pull'dan oldingi holatga qaytadi.
6. Yuborilgan commitni o'zgartirsangiz
Endi boshqa vaziyat. Aziz feature/menyu-chegirma branchida commit qilib, uni yubordi. Keyin xabarni yaxshiladi — amend bilan:
git commit --amend -m "Menyu: dushanbalik chegirmani qo'sh"
git status[feature/menyu-chegirma e5e5044] Menyu: dushanbalik chegirmani qo'sh
Date: Thu Oct 22 09:00:00 2026 +0500
1 file changed, 1 insertion(+)
On branch feature/menyu-chegirma
Your branch and 'origin/feature/menyu-chegirma' have diverged,
and have 1 and 1 different commits each, respectively.
(use "git pull" if you want to integrate the remote branch with yours)
nothing to commit, working tree cleanAmend eski commitni almashtirdi — yangi SHA. GitHub'da esa eskisi turibdi. Tarix ayrildi, oddiy push rad etiladi (non-fast-forward). Bu safar git pull ham yechim emas: u eski va yangi commitni birlashtirib, chalkash tarix yasaydi (Rebase darsidagi dublikat commitlar).
Aziz aynan almashtirmoqchi. Buning uchun majburiy push kerak. Lekin qaysi biri?
7. --force nega xavfli: real voqea
Aziz bilmagan narsa: shu orada Sardor ham shu branchga commit qo'shib, yubordi:
To https://github.com/login/bahor.git
a1c2e75..506c0c4 feature/menyu-chegirma -> feature/menyu-chegirmaAvval Aziz to'g'ri buyruqni sinaydi:
git push --force-with-leaseTo https://github.com/login/bahor.git
! [rejected] feature/menyu-chegirma -> feature/menyu-chegirma (stale info)
error: failed to push some refs to 'https://github.com/login/bahor.git'"Rad etildi (eskirgan ma'lumot)." Git aytyapti: "siz oxirgi ko'rgan holat (a1c2e75) va hozirgi GitHub (506c0c4) farq qiladi — kimdir yangi narsa yuborgan". Push to'xtadi. Aziz buni tushunmadi va "kuchliroq" buyruqni yozdi:
git push --forceTo https://github.com/login/bahor.git
+ 506c0c4...e5e5044 feature/menyu-chegirma -> feature/menyu-chegirma (forced update)O'tdi. GitHub'dagi branch endi Azizning e5e5044 ida. Sardorning 506c0c4 commiti GitHub'dan g'oyib bo'ldi. Sardor fetch qiladi:
From https://github.com/login/bahor
+ 506c0c4...e5e5044 feature/menyu-chegirma -> origin/feature/menyu-chegirma (forced update)
On branch feature/menyu-chegirma
Your branch and 'origin/feature/menyu-chegirma' have diverged,
and have 2 and 1 different commits each, respectively.(forced update) — "majburan yangilandi": kimdir tarixni qayta yozgan. Bu yozuvni ko'rsangiz — to'xtang va hamkasbingizdan so'rang.
7.1 Tuzoq ichidagi tuzoq
Sardor odatdagidek git pull --rebase qildi:
Successfully rebased and updated refs/heads/feature/menyu-chegirma.
e5e5044 (HEAD -> feature/menyu-chegirma, origin/feature/menyu-chegirma) Menyu: dushanbalik chegirmani qo'sh
f42cff1 (origin/main, origin/HEAD) Bosh sahifa: "har kuni" so'zini qo'sh
9a65906 (main) Bosh sahifa: ochilish vaqtini 8:00 qilBirinchi qator — rebase natijasi, qolgan uchtasi — git log --oneline -3. Sardorning "chegirma havolasi" commiti endi uning o'zida ham yo'q! Sababi: pull --rebase eslab qolgan edi — bu commit avval GitHub'da bor edi, keyin u yerdan olib tashlandi. Git "demak, ataylab o'chirilgan" deb hisobladi va uni qayta termadi. Majburiy push zarari shunday tarqaladi.
Vahima kerak emas: commit yo'qolmagan. Reflog uni eslaydi:
git reflog -4e5e5044 (HEAD -> feature/menyu-chegirma, origin/feature/menyu-chegirma) HEAD@{0}: pull --rebase (finish): returning to refs/heads/feature/menyu-chegirma
e5e5044 (HEAD -> feature/menyu-chegirma, origin/feature/menyu-chegirma) HEAD@{1}: pull --rebase (start): checkout e5e5044145e9dc6c1126ac2e86765c9c02c2d919
506c0c4 HEAD@{2}: commit: Bosh sahifa: chegirma havolasini qo'sh
a1c2e75 HEAD@{3}: checkout: moving from main to feature/menyu-chegirmaHEAD@{2} — Sardorning commiti, 506c0c4. Uni cherry-pick bilan qaytaramiz va yuboramiz:
git cherry-pick 506c0c4
git push[feature/menyu-chegirma 2b60545] Bosh sahifa: chegirma havolasini qo'sh
Date: Thu Oct 22 09:20:00 2026 +0500
1 file changed, 1 insertion(+)
To https://github.com/login/bahor.git
e5e5044..2b60545 feature/menyu-chegirma -> feature/menyu-chegirmaBu safar omad kulib boqdi: Sardor o'z commitini o'z kompyuterida qutqardi. Agar commit faqat GitHub'da bo'lsa (masalan, Sardor uni boshqa kompyuterdan yuborgan va o'sha nusxa yo'q bo'lsa) — --force uni butunlay yo'qotishi mumkin edi.
8. --force-with-lease — xavfsiz majburlash
8.1 Qanday ishlaydi?
--force — "nima bo'lsa ham, ustidan yoz". --force-with-lease (ijara bilan majburlash) — "GitHub'dagi branch hali ham men oxirgi ko'rgan joyda bo'lsa — yoz; aks holda to'xta".
"Oxirgi ko'rgan joy" — sizdagi origin/feature/..., ya'ni oxirgi fetch yoki push paytidagi surat. Git hujjati buni ijaraga o'xshatadi: siz branchni "ijaraga olasiz" va kimdir o'zgartirmagan ekan, ijara amal qiladi.
flowchart TD
A["git push --force-with-lease"] --> B{"GitHub'dagi branch<br/>= origin/... ?"}
B -->|"ha"| C["Yozadi:<br/>forced update"]
B -->|"yo'q"| D["To'xtaydi:<br/>stale info"]
D --> E["git fetch, ko'rib chiqish,<br/>yangi ishni qo'shish"]
E --> ANimaga qarang: stale info — xato emas, himoya. U sizni boshqa odamning ishini ko'r-ko'rona o'chirishdan to'xtatdi.
8.2 To'g'ri yo'l: feature branchni yangilash
Eng ko'p uchraydigan holat. main ga yangi commit qo'shildi (Sardor aloqa sahifasiga telefon yozdi). Aziz o'z branchini yangi main ustiga ko'chirmoqchi — kodni tekshiradigan hamkasb (reviewer) PR'dan oldin ko'pincha shuni so'raydi (Rebase darsidagi "rebase qilib yuboring").
git pull
git log --oneline --graph --all -6From https://github.com/login/bahor
e5e5044..2b60545 feature/menyu-chegirma -> origin/feature/menyu-chegirma
f42cff1..167fdc7 main -> origin/main
Updating e5e5044..2b60545
Fast-forward
index.html | 1 +
1 file changed, 1 insertion(+)
* 167fdc7 (origin/main, origin/HEAD) Aloqa: telefon raqamini qo'sh
| * 2b60545 (HEAD -> feature/menyu-chegirma, origin/feature/menyu-chegirma) Bosh sahifa: chegirma havolasini qo'sh
| * e5e5044 Menyu: dushanbalik chegirmani qo'sh
|/
* f42cff1 (main) Bosh sahifa: "har kuni" so'zini qo'sh
* 9a65906 Bosh sahifa: ochilish vaqtini 8:00 qil
* 1ef64f4 Bosh sahifa: ish vaqtini qo'shBirinchi qadam — git pull: branchdagi Sardorning commitini olib keldi (va origin/main ni ham yangiladi). Endi Aziz hamma narsani ko'rgan. Rebase:
git rebase origin/main
git statusSuccessfully rebased and updated refs/heads/feature/menyu-chegirma.
On branch feature/menyu-chegirma
Your branch and 'origin/feature/menyu-chegirma' have diverged,
and have 3 and 2 different commits each, respectively.
(use "git pull" if you want to integrate the remote branch with yours)
nothing to commit, working tree cleanIkkala commit qayta terildi — yangi SHA'lar. Ayrilish kutilgan: biz tarixni ataylab qayta yozdik. Oddiy push rad etiladi (non-fast-forward). Endi --force-with-lease:
git push --force-with-lease
git log --oneline --graph -5To https://github.com/login/bahor.git
+ 2b60545...48dc5ec feature/menyu-chegirma -> feature/menyu-chegirma (forced update)
* 48dc5ec (HEAD -> feature/menyu-chegirma, origin/feature/menyu-chegirma) Bosh sahifa: chegirma havolasini qo'sh
* c75c393 Menyu: dushanbalik chegirmani qo'sh
* 167fdc7 (origin/main, origin/HEAD) Aloqa: telefon raqamini qo'sh
* f42cff1 (main) Bosh sahifa: "har kuni" so'zini qo'sh
* 9a65906 Bosh sahifa: ochilish vaqtini 8:00 qilO'tdi: GitHub'dagi branch hali 2b60545 da edi — Aziz ko'rgan joyda. Sardorning commiti ham, Azizniki ham joyida, tarix — to'g'ri chiziq.
8.3 Lease'ni nima aldaydi?
Git hujjati bitta ogohlantirish beradi. Lease sizdagi origin/... suratiga tayanadi. Agar biror dastur fonda o'zi git fetch qilib tursa (masalan, muharrirdagi avtomatik fetch yoqilgan bo'lsa), surat siz bilmasdan yangilanadi. Shunda --force-with-lease siz ko'rmagan commitni ham "ko'rgan" deb hisoblaydi.
Hujjatdagi yechim — qo'shimcha flag:
git push --force-with-lease --force-if-includes--force-if-includes yana bir tekshiruv qo'shadi: GitHub'dagi o'zgarishlar sizning lokal tarixingizga haqiqatan qo'shilganmi. Faqat fonda olib kelingan, lekin siz birlashtirmagan commit bo'lsa — push to'xtaydi.
8.4 Qoidalar
| Branch | Majburiy push |
|---|---|
main va boshqa umumiy branchlar |
Hech qachon |
| O'zingizning feature branchingiz | Faqat --force-with-lease |
| Ikki kishi ishlayotgan feature branch | Avval kelishib olib, keyin --force-with-lease |
main ni GitHub'da texnik jihatdan ham himoyalash mumkin — majburiy push'ni umuman taqiqlash. Buni Branch himoyasi darsida ko'rasiz. Portfolio'ni GitHub'ga ulaganda (Remote darsi) main ga --force-with-lease qildik — bu istisno: tarixni faqat bir marta, ko'rib chiqib almashtirdik va repoda boshqa hech kim ishlamaydi.
Tekshirib ko'ring: Sardor "
--force-with-leaseham rad etdi,--forceqilaman" dedi. Unga nima deysiz?
Javob
stale info — GitHub'da Sardor hali ko'rmagan commit bor degani. --force uni o'chiradi. To'g'ri yo'l: git fetch, git log --oneline --graph --all bilan kim nima yuborganini ko'rish, kerak bo'lsa git pull --rebase yoki git rebase bilan o'sha commitni o'z tarixiga qo'shish, keyin yana --force-with-lease.
9. Upstream'ni qo'lda sozlash: git branch -u
Ba'zan branchning upstream'i yo'qoladi yoki umuman sozlanmagan bo'ladi — masalan, branch -u siz yuborilgan bo'lsa. Ko'rsatish uchun upstream'ni ataylab olib tashlaymiz:
git branch --unset-upstream
git pullThere is no tracking information for the current branch.
Please specify which branch you want to rebase against.
See git-pull(1) for details.
git pull <remote> <branch>
If you wish to set tracking information for this branch you can do so with:
git branch --set-upstream-to=origin/<branch> main
"Joriy branch uchun kuzatuv ma'lumoti yo'q." git status ham ahead/behind ni ko'rsatmay qo'yadi. Tuzatish — Git aytgan buyruq yoki uning qisqa shakli -u:
git branch -u origin/main
git statusbranch 'main' set up to track 'origin/main'.
On branch main
Your branch is up to date with 'origin/main'.
nothing to commit, working tree cleangit push -u — yuborish bilan birga sozlaydi. git branch -u — hech narsa yubormasdan, faqat bog'lanishni yozadi.
10. Ko'p uchraydigan xatolar
10.1 Ko'r-ko'rona --force
Eng xavflisi. Internetdagi maslahat "push o'tmasa, -f qo'shing" deydi — va jamoadoshning ishi yo'qoladi. Majburiy push kerak bo'lsa — faqat --force-with-lease, faqat o'z branchingizda.
10.2 Need to specify how to reconcile divergent branches
macOS/Linux'da sozlama yo'qligi. Bir marta git config --global pull.rebase true.
10.3 Tarixda "Merge branch 'main' of ..." commitlari to'planib qoldi
Windows'dagi pull.rebase=false natijasi. Global pull.rebase true qo'ying. Eski commitlar qoladi — ular allaqachon yuborilgan, ularni qayta yozmang.
10.4 cannot pull with rebase: You have unstaged changes
Commit qiling, git stash qiling yoki --autostash.
10.5 Conflict o'rtasida qolib ketish
git status interactive rebase in progress desa — rebase tugamagan. Yo yeching va git rebase --continue, yo git rebase --abort. Yarim yo'lda yangi commit qilmang.
10.6 (forced update) ni e'tiborsiz qoldirish
Fetch yoki pull chiqishida + ... va (forced update) ko'rsangiz — kimdir tarixni qayta yozgan. O'zingizda shu branchda yuborilmagan commit bo'lsa, pull'dan oldin uning SHA'sini yozib qo'ying (yoki git branch zaxira bilan zaxira branch oching).
11. Mashqlar
1-mashq (oson): Xabarni tarjima qiling
Har bir xabar nimani bildiradi va birinchi qadam qanday?
! [rejected] main -> main (fetch first)Your branch and 'origin/main' have diverged, and have 2 and 3 different commits each! [rejected] fix/telefon -> fix/telefon (stale info)fatal: Not possible to fast-forward, aborting.
Yechim
- GitHub'da sizda yo'q commit bor, Git uni hali tanimaydi. Birinchi qadam —
git pull. - Sizda 2 ta yuborilmagan commit, GitHub'da sizda yo'q 3 ta.
git pull --rebase(yokipull.rebase truebo'lsa —git pull). --force-with-leaseto'xtadi: siz oxirgi ko'rgandan beri branch o'zgargan.git fetchva ko'rib chiqish.--ff-only(yokipull.ff only) bilan pull qildingiz, tarix esa ayrilgan.git pull --rebasebilan birlashtiring.
2-mashq (o'rta): Bo'sh joylarni to'ldiring
Aziz fix/telefon branchini yuborgan, keyin uni yangi main ustiga ko'chirdi:
git switch fix/telefon
git fetch
git origin/main
git push --Barcha repolarda git pull rebase qilishi uchun:
git config --global pull. trueIshora: «To'g'ri yo'l: feature branchni yangilash» va «Doimiy sozlama» bo'limlari.
Yechim
git switch fix/telefon
git fetch
git rebase origin/main
git push --force-with-lease
git config --global pull.rebase trueRebase SHA'larni o'zgartiradi, shuning uchun oddiy push rad etiladi. --force-with-lease — GitHub'dagi branch siz fetch'da ko'rgan joyda bo'lsagina yozadi.
3-mashq (qiyin): Kim aybdor va nima qilamiz?
Ertalab Malika feature/bron-forma branchiga ikki commit yubordi. Tushda Sardor shu branchda git commit --amend qildi, push rad etildi va u git push --force yozdi. Kechqurun Malika git pull qildi va quyidagini ko'rdi:
+ 7a1b2c3...9d8e7f6 feature/bron-forma -> origin/feature/bron-forma (forced update)- GitHub'da nima bo'ldi va kimning ishi xavf ostida?
- Sardor qaysi buyruqni ishlatishi kerak edi va u nima qilardi?
- Malika o'z commitlarini yo'qotmaslik uchun pull'dan oldin nima qilishi kerak edi?
- Commitlar baribir yo'qolgandek ko'rinsa, ularni qanday topadi?
Ishora: «--force nega xavfli», «Tuzoq ichidagi tuzoq» va Reflog darsi.
Yechim
- Sardor GitHub'dagi branchni o'z versiyasi bilan almashtirdi. Malikaning ertalabki ikki commiti, agar Sardorda bo'lmagan bo'lsa, GitHub'dan o'chdi. Xavf ostida — Malikaning ishi.
git push --force-with-lease. Sardor Malikaning commitlarini fetch qilmagan edi — leasestale infobilan to'xtardi va Sardor avval ularni olishi kerakligini bilardi.git fetchvagit statusbilan holatni ko'rish.(forced update)ni ko'rib, zaxira olish:git branch bron-zaxira.git reflog— commitlarning SHA'sini topadi (ular kompyuterida edi), keyingit cherry-pick <sha>va oddiygit push. Va Sardor bilan gaplashish — keyingi safar kelishib olish uchun.
4-mashq: Portfolio qadami — GitHub'da tahrir, kompyuterda commit
Portfolio endi GitHub'da. Ba'zan faylni GitHub saytida to'g'ridan-to'g'ri tahrirlaysiz — shunda tarix ayriladi. Buni xavfsiz sharoitda sinaymiz.
git config --global pull.rebase trueqo'ying vagit config --show-scope --get-all pull.rebasebilan tekshiring.- GitHub'da
login.github.io→sayt/haqimda/index.html→ qalam belgisi (Edit) → bitta gap qo'shing → Commit changes. Xabar:Haqimda: yangi gap qo'sh. - Kompyuterda pull qilmasdan
sayt/aloqa/index.htmlga o'zgarish kiriting va commit qiling:Aloqa: Telegram havolasini yangila. git push— qanday xabar chiqdi?git fetchvagit status— nechta va nechta?git pull, keyingit log --oneline --graph -4vagit push.mashqlar/07/27-ajralgan-tarix/javoblar.mdga 4-qadamdagi xabarni va 5-qadamdagi grafikni yozing. Commit:07/27: ajralgan tarix mashqlari javoblarini qo'sh, keyingit push.
Yechim
git config --global pull.rebase true
git config --show-scope --get-all pull.rebase
cd ~/kurs/portfolio
code sayt/aloqa/index.html
git add sayt/aloqa/index.html
git commit -m "Aloqa: Telegram havolasini yangila"
git push
git fetch
git status
git pull
git log --oneline --graph -4
git push4-qadamda ! [rejected] main -> main (fetch first), fetch'dan keyin have 1 and 1 different commits each. 5-qadamda Successfully rebased, grafik esa to'g'ri chiziq: sizning commitingiz GitHub'dagi tahrir ustida. Push'dan keyin Pages workflow'i ishga tushadi va sayt ikkala o'zgarish bilan yangilanadi.
Agar ikkala tahrir bitta qatorga tushsa — «pull --rebase paytida conflict» bo'limidagi kabi yechasiz. --force bu mashqda umuman kerak emas.
12. Real ishda
- Har kunlik:
pull.rebase truevagit pull— eng ko'p tarqalgan sozlama. Ko'p jamoalar buni yangi xodimga birinchi kuni aytadi. - PR yangilash: "branch'ingizni
mainustiga rebase qiling" — keyin--force-with-lease. Bu Pull Request bilan ishlashning odatiy qismi. - Himoya: jamoalar
mainga majburiy push'ni GitHub sozlamalari bilan taqiqlaydi (Branch himoyasi). VS Code va boshqa vositalarda ham "Force Push" tugmasi odatda lease bilan ishlaydi. - Intervyuda: "
--forceva--force-with-leasefarqi?", "git pullvagit pull --rebasefarqi?", "push rejected bo'lsa nima qilasiz?" — uchala savolga javob shu darsda.
Xulosa
rejected (fetch first)/(non-fast-forward)— GitHub'da sizda yo'q commit bor; avval birlashtiring.have diverged, N and M— ikki tomonda ham yangi commit: merge, rebase yoki ff-only.git pull --rebaseyuborilmagan commitlaringizni yangi tarix ustiga teradi;pull.rebase true— doimiy.- Windows'da system'da
pull.rebase=falsebor — global sozlama uni bosib o'tadi. - Yuborilgan tarixni qayta yozsangiz — faqat
--force-with-lease(kerak bo'lsa--force-if-includes),mainda — hech qachon. - Upstream yo'q bo'lsa —
git branch -u origin/<branch>.
Keyingi dars: GitHub asoslari: repo, README, LICENSE, sozlamalar — repongizni GitHub'da professional ko'rinishga keltiramiz: README, litsenziya, tavsif va sozlamalar.
Manbalar
- Git hujjati: "git-push" (
--force-with-lease,--force-if-includesva "Note about fast-forwards"), "git-pull", "git-config" (pull.rebase,pull.ff,rebase.autoStash) — git-scm.com/docs - GitHub Docs: "Dealing with non-fast-forward errors", "Pushing commits to a remote repository" — docs.github.com
- Pro Git kitobi: "Rebasing" (The Perils of Rebasing) — git-scm.com/book
Izohlar (0)
Izoh yozish uchun kiring.
- Hozircha izoh yo'q. Birinchi bo'ling!