Git dan "Cabang 'x' tidak sepenuhnya digabung" Kesalahan

294

Berikut adalah perintah yang saya gunakan dari cabang utama

git branch experiment
git checkout experiment

Lalu saya membuat beberapa perubahan pada file saya, melakukan perubahan, dan mendorong cabang baru ke GitHub.

git commit . -m 'changed files'
git push -u origin experiment

Kemudian saya memutuskan untuk menggabungkan cabang percobaan saya ke cabang utama.

git checkout master
git merge experiment

Akhirnya saya mendorong perubahan ke GitHub.

git push -u origin master

Semua berjalan dengan baik sampai saya mencoba menghapus cabang percobaan saya menggunakan

git branch -d experiment

Saya mendapat pesan kesalahan yang error: The branch 'experiment' is not fully merged.saya sedikit baru untuk git, dan saya tidak tahu berapa banyak lagi saya bisa menggabungkan dua cabang. Apa yang kulewatkan di sini?

mellowsoon
sumber
2
Apakah posting ini membantu Anda? stackoverflow.com/questions/1710894/…
Chrisdigital
2
Ini muncul kadang-kadang ketika saya sudah melakukangit commit --amend
Arcolye
12
Juga - Ingatlah bahwa pesan ini akan muncul setelah squash: stackoverflow.com/q/41946475/109941
Jim G.
Saya pikir skenario yang paling umum adalah, Anda hanya perlu menarik perubahan yang baru digabungkan sebelum menghapus cabang secara lokal.
RaisinBranCrunch

Jawaban:

313

Catatan Penulisan berubah dalam menanggapi komitmen. Terima kasih @slekse
Itu bukan kesalahan, itu peringatan. Ini berarti cabang yang akan Anda hapus berisi komit yang tidak dapat dijangkau dari: cabang upstreamnya, atau HEAD (saat ini memeriksa revisi). Dengan kata lain, saat Anda mungkin kehilangan komitmen¹.

Dalam praktiknya itu berarti bahwa Anda mungkin diubah, diubah atau disaring melakukan dan tampaknya tidak sama.

Oleh karena itu Anda dapat menghindari peringatan dengan memeriksa cabang yang berisi komit yang tidak Anda rujuk dengan menghapus cabang lainnya.²

Anda akan ingin memverifikasi bahwa Anda sebenarnya tidak kehilangan komitmen penting:

git log --graph --left-right --cherry-pick --oneline master...experiment

Ini akan memberi Anda daftar nonshared antara cabang. Jika Anda penasaran, mungkin ada perbedaan tanpa --cherry-pickdan perbedaan ini bisa menjadi alasan peringatan yang Anda dapatkan:

--cherry-pick

Abaikan setiap komit yang memperkenalkan perubahan yang sama seperti komit lain di "sisi lain" ketika set komit dibatasi dengan perbedaan simetris. Misalnya, jika Anda memiliki dua cabang, A dan B, cara yang biasa untuk membuat daftar semua komit hanya pada satu sisi adalah dengan - kiri-kanan, seperti contoh di atas dalam deskripsi opsi itu. Namun itu menunjukkan komit yang dipetik dari cabang lain (misalnya, "ke-3 pada b" mungkin dipetik dari cabang A). Dengan opsi ini, pasangan komit tersebut dikecualikan dari output.


¹ mereka benar-benar hanya sampah yang dikumpulkan setelah beberapa saat, secara default. Juga, git-branchperintah tidak memeriksa pohon revisi dari semua cabang . Peringatan itu ada untuk menghindari kesalahan yang jelas.

² (Preferensi saya di sini adalah memaksa penghapusan saja, tetapi Anda mungkin ingin memiliki jaminan tambahan).

lihat
sumber
24
Terima kasih. Frasa kuncinya adalah "berisi komit yang tidak dapat dijangkau dari kepala referensi lain". Meskipun saya tidak lagi membutuhkan cabang percobaan, dan telah menggabungkannya menjadi master, dan berencana menghapusnya dari asal, git tidak akan bahagia sampai saya mendorong perubahan untuk bereksperimen ke asal. Saya kira peringatan ini semacam cek kewarasan.
mellowsoon
35
-1 "Ini berarti cabang yang akan Anda hapus berisi komit yang tidak dapat dijangkau dari kepala referensi lain." Ini tidak benar. Peringatan itu berarti bahwa cabang tidak dapat dijangkau dari hulu (jika ada), atau dari KEPALA saat ini. Lihat halaman manual dari git-branch.
sleske
3
@TachyonVortex Tautan bagus. Perintah git branch -vv benar-benar menjelaskan apa yang terjadi pada saya.
Jason Massey
11
@sleske Terima kasih atas komentarnya - jawaban ini harus benar-benar diedit. Sangat disayangkan itu sangat tervvotasikan karena kalimat penjelas utama tidak benar. Saya baru saja mengalami masalah ini dan menghabiskan waktu yang lama untuk mencari tahu apa masalahnya, dan hanya saja cabang pelacak jarak jauh telah dihapus sebagai bagian dari permintaan tarik, dan pada saat itu sejak saya telah menarik perubahan dari master di cabang lokal. Satu-satunya 'masalah' tidak menemukan cabang pelacakan jarak jauh, yang telah dihapus (dan saya mencoba untuk menghapus cabang lokal untuk alasan yang sama).
ely
3
Ya, ini bisa terjadi hanya ketika mencoba untuk menghapus cabang lokal jika Anda berada di cabang yang berbeda dari yang Anda gunakan saat Anda membuatnya. "Komit yang tidak dapat dijangkau dari referensi lain" tidak benar dan menakutkan!
Amalgovinus
80

Seperti yang ditunjukkan oleh Drew Taylor, penghapusan cabang dengan -d hanya mempertimbangkan HEAD saat ini dalam menentukan apakah cabang tersebut "sepenuhnya digabung". Ini akan mengeluh bahkan jika cabang tersebut digabung dengan beberapa cabang lainnya. Pesan kesalahan pasti bisa lebih jelas dalam hal ini ... Anda bisa checkout cabang gabungan sebelum menghapus, atau cukup gunakan git branch -D. Capital -D akan mengganti cek sepenuhnya.

drwowe
sumber
2
Bagian tentang KEPALA saat ini memperbaikinya untuk saya. Tuan saya berbeda dari cabang fitur yang saya buat cabang yang bertentangan: D
viki.omega9
1
Untuk seseorang yang belajar git, kata "saat ini" tampaknya berlebihan dengan "KEPALA"? Tidak ada hal seperti KEPALA uncurrent - HEAD oleh definisi adalah yang saat ini cabang. Apakah saya melewatkan sesuatu? Saya kira Anda bisa mengatakan "cabang saat ini" atau "KEPALA" tetapi tidak "KEPALA saat ini".
Mark Lakata
Apakah ada cara untuk mengubah / mengkonfigurasi ini (mis., Apakah selalu mengeceknya origin/master?) Saya kira memeriksa origin/masterdulu tidak terlalu berat, tetapi rasanya seperti aliran aneh - mengapa saya perlu memeriksa origin/mastersecara lokal hanya untuk Anda memverifikasi bahwa perubahan saya digabung di sana?
Alec
15

Saya mencoba jawaban sehe dan tidak berhasil.

Untuk menemukan komit yang belum digabungkan cukup gunakan:

git log feature-branch ^master --no-merges
qwertzguy
sumber
14

Saya memiliki ini terjadi pada saya hari ini, karena saya menggabungkan cabang fitur pertama saya kembali ke master. Seperti yang dikatakan beberapa orang di utas lain tentang SO, triknya beralih kembali ke master sebelum mencoba menghapus cabang. Setelah kembali menjadi master, git dengan senang hati menghapus cabang tanpa peringatan.

Drew Taylor
sumber
7
Tidak terlihat seperti itu masalah khusus di sini, tapi saya mengalami masalah yang Anda jelaskan tadi, jadi terima kasih!
Daniel Buckmaster
4

Git memperingatkan bahwa Anda mungkin kehilangan riwayat dengan menghapus cabang ini. Meskipun itu tidak akan langsung menghapus komit, beberapa atau semua komit di cabang akan menjadi tidak terjangkau jika mereka bukan bagian dari cabang lain juga.

Agar cabang experimentdapat "sepenuhnya digabung" ke cabang lain, ujung komitnya harus merupakan leluhur dari ujung cabang lainnya, membuat komit dalam experimentsubset cabang lainnya. Ini membuatnya aman untuk dihapus experiment, karena semua komitnya akan tetap menjadi bagian dari sejarah repositori melalui cabang lain. Itu harus "sepenuhnya" digabung, karena mungkin sudah digabung beberapa kali, tetapi sekarang telah menambahkan komitmen sejak penggabungan terakhir yang tidak terdapat di cabang lain.

Git tidak memeriksa setiap cabang lain di repositori; hanya dua:

  1. Cabang saat ini (KEPALA)
  2. Cabang hulu, jika ada

"Cabang hulu" untuk experiment, seperti dalam kasus Anda, mungkin origin/experiment. Jika experimentsepenuhnya digabung dalam cabang saat ini, maka Git menghapusnya tanpa keluhan. Jika tidak, tetapi sepenuhnya digabung dalam cabang hulu, maka Git melanjutkan dengan peringatan yang tampak seperti:

warning: deleting branch 'experiment' that has been merged
to 'refs/remotes/origin/experiment', but not yet merged to
HEAD.
Deleted branch experiment (was xxxxxxxx).

Di mana xxxxxxxxmenunjukkan id komit. Digabung penuh di hulu menunjukkan bahwa komit experimenttelah didorong ke repositori asal, sehingga bahkan jika Anda kehilangannya di sini, mereka setidaknya dapat disimpan di tempat lain.

Karena Git tidak memeriksa cabang lain, mungkin aman untuk menghapus cabang karena Anda tahu itu sepenuhnya digabung menjadi cabang lain; Anda dapat melakukan ini dengan -Dopsi seperti yang ditunjukkan, atau beralih ke cabang itu terlebih dahulu dan biarkan Git mengkonfirmasi status yang sepenuhnya digabung untuk Anda.

Troore
sumber
1
Kuncinya adalah "sepenuhnya digabung dalam cabang saat ini ". Saya memiliki cabang X 'dari X sepenuhnya digabung kembali menjadi X dan sudah menghapus asal / X'. Tetapi dengan Y memeriksa saya mendapat peringatan ini. Ketika saya memeriksa XI saya bisa menghapus X '. Agak bodoh, saya pikir.
Lawrence Dol
2
Jawaban ini dijiplak dari sini tanpa atribusi chimera.labs.oreilly.com/books/1230000000561/…
Mark Lakata
3

untuk melihat perubahan yang tidak digabungkan, saya melakukan ini:

git checkout experiment
git merge --no-commit master

git diff --cached

Catatan: Ini menunjukkan perubahan masteryang tidak ada di experiment.

Jangan lupa untuk:

git merge --abort

Setelah selesai, lihatlah.

ThorSummoner
sumber
@IgorGanapolsky Entahlah, meskipun biasanya man git-resetdan perintah git reset sudah cukup untuk pulih dari masalah negara.
ThorSummoner
3

Solusi termudah dengan Penjelasan (solusi dua kali lipat) (menghadapi masalah sebelumnya)

Masalahnya adalah:

1- Saya tidak bisa menghapus cabang

2- Terminal terus menampilkan pesan peringatan bahwa ada beberapa komit yang belum disetujui

3 - mengetahui bahwa saya memeriksa master dan cabang dan semuanya identik (terkini)

larutan:

git checkout master
git merge branch_name
git checkout branch_name
git push
git checkout master
git branch -d branch_name

Penjelasan:

ketika cabang Anda terhubung ke cabang jarak jauh hulu (di Github, bitbucket atau apa pun), Anda perlu menggabungkan (mendorong) ke master, dan Anda perlu mendorong perubahan baru (berkomitmen) ke repo jarak jauh (Github, bitbucket atau terserah) dari cabang,

apa yang saya lakukan dalam kode saya adalah bahwa saya beralih ke master, kemudian menggabungkan cabang ke dalamnya (untuk memastikan mereka identik pada mesin lokal Anda), kemudian saya beralih ke cabang lagi dan mendorong pembaruan atau perubahan ke online jarak jauh repo menggunakan "git push".

setelah itu, saya beralih ke master lagi, dan mencoba menghapus cabang, dan masalah (pesan peringatan) hilang, dan cabang berhasil dihapus

Elta3lab
sumber
3

Anda cukup mencari tahu:

git log - master master ... eksperimental

--cherry Opsi adalah sinonim untuk --right-only --cherry-mark --no-merges

halaman manual git-log berkata

itu berguna untuk membatasi output pada komit di pihak kita dan menandai yang telah diterapkan pada sisi lain dari sejarah bercabang dengan git log --cherry upstream ... mybranch, mirip dengan git cherry upstream mybranch.

FYI. --cherry-pickmenghilangkan komitmen yang setara tetapi --cherry-markstidak. Sangat berguna untuk menemukan rebase dan memaksa perubahan yang diperbarui antara cabang publik upstream dan co-working

yongbin
sumber
1

Saya tidak memiliki cabang hulu di git lokal saya. Saya telah membuat cabang lokal dari master, git checkout -b mybranch. Saya membuat cabang dengan bitbucket GUI di hulu git dan mendorong cabang lokal saya (mybranch) ke cabang hulu itu. Setelah saya melakukan git mengambil git lokal saya untuk mengambil cabang hulu, saya bisa melakukan cabang git -d mybranch.

edW
sumber
0

Saya percaya bendera --forceadalah apa yang benar-benar Anda cari. Cukup gunakan git branch -d --force <branch_name>untuk menghapus cabang secara paksa.

Sergey Samoylenko
sumber