Git'te yanlış bir kesinleştirme mesajını nasıl düzenlerim (ittiğim)?


152

Tarihin derinliklerinde bir taahhüt mesajını değiştirmek istiyorum ve birçok yeni taahhütte bulundum.

Teslim mesajını nasıl değiştirebilirim? Mümkün mü?

Yanıtlar:


125

Linus Torvalds'ın mesajı sorunuza cevap verebilir:

Eski tamamlama mesajlarını değiştirme / düzenleme

Kısa cevap: Yapamazsınız (itilirse).


özü (Linus, BitKeeper'ı BK olarak ifade eder):

Yan not, sadece tarihsel ilgi dışında: BK'de bunu yapabilirsiniz.

Ve eğer alışkınsanız (benim gibi) gerçekten pratikti. Andrew'dan bir yama bombası uygulardım, bir şeylerin yanlış olduğunu fark ettim ve itmeden önce onu düzenledim.

Git için de aynısını yapabilirdim. Sadece taahhüt mesajının adın bir parçası olmamasını sağlamak ve tarihin el değmemiş olduğunu garanti etmek ve "yorumları daha sonra düzelt" işlemine izin vermek yeterince kolay olurdu.

Ama etmedim.

Bunun bir kısmı tamamen "iç tutarlılık" tır. Git, SHA1 korumalı her şey ve nesne türünden bağımsız olarak tüm nesnelerin aynı şekilde işlenmesi sayesinde daha temiz bir sistemdir. Evet, dört farklı nesne türü vardır ve hepsi gerçekten farklıdır ve aynı şekilde kullanılamazlar, ancak aynı zamanda kodlamaları diskte farklı olsa bile, kavramsal olarak hepsi tam olarak çalışır aynısı.

Ancak iç tutarlılık, esnek olmamanın bir mazereti değildir ve hataları meydana geldikten sonra düzeltebilmemiz açıkça çok esnek olacaktır. Yani bu gerçekten güçlü bir argüman değil.

Gerçek yolu, mesajları güvenebileceği: Neden git çok basit olarak sona mesajı uçlarını işlemek değiştirmeye izin vermez. Daha sonra kişilerin bunları değiştirmesine izin verdiyseniz, mesajlar doğal olarak çok güvenilir değildir.


Tam olması için, olabilir gibi, ne istediğini yansıtmak için yerel taahhüt tarihi yeniden Sýkora önerdiği (bazı rebase ile ve, gasp --hard reset!)

Bununla birlikte, gözden geçirilmiş geçmişinizi tekrar yayınladığınızda (a ile git push origin +master:master, +"hızlı ileri alma" taahhüdü ile sonuçlanmasa bile, itme işleminin gerçekleşmesini zorunlu kılan işaret) bazı sorunlar yaşayabilirsiniz .

Bu diğer SO sorusundan alıntı:

Aslında bir kez --force ile git.git deposuna ittim ve Linus BIG TIME tarafından azarlandım. Diğer insanlar için çok fazla sorun yaratacaktır. Basit bir cevap "yapma".


iyi cevap. Git'in daha yeni sürümlerinde zaten aktarılan tamamlama mesajlarını değiştirip değiştiremeyeceğinizi biliyor musunuz? '09'da yayınlandığından beri bir şey değişti mi?
David West

@DavidWest prensibi geçerlidir: geçmişinizi yeniden yazabilir ve bir itme zorlayabilirsiniz.
VonC

2
İşleri daha spesifik hale getirmek için, değişiklik / rebase taahhütlerini yerine getirirseniz, bunların taahhüt tanımlayıcıları (git dizinindeki onaltılık karmalar) kaçınılmaz olarak değişir; yani düzenlenen taahhütler git VCS tarihindeki eski taahhütlerinden farklı olarak ele alınır. Bununla birlikte, dev ekip üyeleriniz maalesef eski taahhütleri çekmişse, düzenlenmiş, yeni taahhütleri çekmek ve yerel çalışma kopyalarında eski ve yeni arasında birleştirme yapmakla yükümlüdürler.
Shigerello

1
İş arkadaşlarınız için kolaylık sağlamak amacıyla düzenlenmiş taahhütleri yeniden zorlamak daha iyidir, böylece iş arkadaşlarınızın çalışma kopyalarında birleştirme ihtiyacını olumlu bir şekilde ortadan kaldırır.
Shigerello

28

Şu anda git yerine hile yapabilir.

Ayrıntılı olarak: Geçici bir çalışma dalı oluşturun

git checkout -b temp

Değiştirme taahhüdüne sıfırla

git reset --hard <sha1>

Taahhüdü doğru mesajla değiştirin

git commit --amend -m "<right message>"

Eski taahhüdü yenisiyle değiştirin

git replace <old commit sha1> <new commit sha1>

bulunduğunuz şubeye geri dönün

git checkout <branch>

geçici dalı kaldır

git branch -D temp

it

guess

yapılır.


11
@Jonah: Uzak şubeye doğru itmeye çalıştığımda "Her şey güncel" mesajı alıyorum
Simon Kagwi

1
Başka bir cevapta belirtildiği gibi: rebase -i'yi geri sarmalı kullanın. Ve tarihi yeniden yazacak.
Sylvain

Aradığım çözüm için teşekkür ederim. Benim zamanımı kurtar!
Tomasz Kuter

1
@Jonah - Bir sorunum var ... çözümünüz taahhüt günlüklerimi yerel olarak güncelledi, ancak uzaktan değil. Onları oraya nasıl itebiliriz?
Tomasz Kuter

1
@TomaszKuter, seninle aynı sorunu yaşadım. Taahhüt iletim uzaktan güncellenmedi. GitHub'dan aşağıdaki yardımı kullanarak çözdüm : help.github.com/articles/changing-a-commit-message . Aşağıdakileri izleyin: Eski veya birden çok kesin ileti mesajını değiştirme bölümü. Temel olarak user987419 tarafından verilen aşağıdan gelen cevaptır Eğer taahhüt mesajını zaten değiştirdiyseniz, tekrar değiştirmeden seçim yapabilir ve kaydedebilirsiniz.
evaldeslacasa

19

Sen kullanabilirsiniz git rebase -iinteraktif için 'i' (aralarından kollara şube karşı).

Değiştirmek pickistediğiniz tamamlama açıklamasının yanını değiştirin r(veya reword), kaydedin ve çıkın ve bunu yaptıktan sonra düzenleme yapabilirsiniz.

git push bir kez daha ve işiniz bitti!


1
Bu, birinin birleştirme taahhütlerinde mesajları düzenlemesine izin vermez. Bu komutun bazı varyantlarında bu mümkün mü?
Andrew Mao

1
Hangi rezervlerin birleştiği -pargümanını deneyin . rebasep
Kaktüs

3
Bu prosedürü beğendim, ama ilk başta cevabı tam olarak anlamadım. Birinin bu konuda yardıma ihtiyacı olması durumunda, Githulb Yardım sayfası bu konuda iyi bilgiler sunar: help.github.com/articles/changing-a-commit-message
evaldeslacasa

15

Diyelim ki böyle bir ağacınız var:

dd2e86 - 946992 - 9143a9 - a6fd86 - 5a6057 [master]

İlk olarak, checkoutgeçici bir dal:

git checkout -b temp

On tempdalı, reset --hardbir sen (olduğunu taahhüt örneğin mesajını değiştirmek istediğinizi işlemeye 946992):

git reset --hard 946992

amendMesajı değiştirmek için kullanın :

git commit --amend -m "<new_message>"

Bundan sonra ağaç şöyle görünecek:

dd2e86 - 946992 - 9143a9 - a6fd86 - 5a6057 [master]
           \
            b886a0 [temp]

Sonra, cherry-pickbütün bu ilerisinde olduğunu taahhüt 946992gelen masteretmek tempve, kullanım bunları işlemek amendsen de onların mesajlarını değiştirmek isterseniz:

git cherry-pick 9143a9
git commit --amend -m "<new_message>
...
git cherry-pick 5a6057
git commit --amend -m "<new_message>

Ağaç şimdi şöyle görünüyor:

dd2e86 - 946992 - 9143a9 - a6fd86 - 5a6057 [master]
               \
                b886a0 - 41ab2c - 6c2a3s - 7c88c9 [temp]

Şimdi geçici dalı uzaktan kumandaya zorla:

git push --force origin temp:master

Son adım, şubeyi sunucudan çekmek için şubedeki masteryerel şubeyi silin , sonra şubeye geçin ve şubeyi silin .git fetch originmastermastertemp

Artık hem yerel hem de uzaktan kumandanız tüm mesajları güncelleyecek.


5

Dükkanımızda, yanlış mesajlarla taahhütlere tanınabilir olarak adlandırılan ek açıklama etiketleri ekleme ve ek açıklamayı değiştirme olarak kullanma kuralını tanıttım.

Bu, sıradan "git log" komutlarını çalıştıran kişilere yardımcı olmasa da, yorumlarda yanlış hata izleyici referanslarını düzeltmek için bir yol sağlar ve tüm oluşturma ve bırakma araçlarım kuralı anlar.

Bu açık bir şekilde genel bir cevap değildir, ancak bu kişilerin belirli topluluklar tarafından benimseyebileceği bir şey olabilir. Eminim bu daha büyük bir ölçekte kullanılıyorsa, bunun için bir çeşit porselen desteği ortaya çıkabilir, sonunda ...


3
"git notları" benzer bir amaca hizmet edebilir
Christian Goetze

2

(Http://git.or.cz/gitwiki/GitTips#head-9f87cd21bcdf081a61c29985604ff4be35a5e6c0 adresinden )

Nasıl değiştirilir tarihte daha derinden taahhüt eder

Git'teki tarih değişmez olduğundan, en son taahhüt (şube başkanı olmayan taahhüt) dışında herhangi bir şeyi düzeltmek, tarihin değiştirilen taahhüt ve ilerlemeden yeniden yazılmasını gerektirir.

Bunun için StGIT'i kullanabilir, gerekirse şubeyi başlatabilir, değiştirmek istediğiniz taahhüdü kaldırabilir, gerekirse pop yapabilir, bir değişiklik yapabilir ve düzeltme ekini yenileyebilirsiniz (kesinleştirme mesajını düzeltmek istiyorsanız -e seçeneği ile), ardından her şey ve stg taahhüt.

Ya da bunu yapmak için rebase kullanabilirsiniz. Yeni geçici dal oluşturun, git reset --hard'ı kullanarak değiştirmek istediğiniz komuta geri sarın, bu komutu değiştirin (geçerli başlığın üstünde olacaktır), sonra git rebase --onto kullanarak şubeyi değiştirilen tamamlamanın üstüne yeniden dayandırın.

Ya da yama yeniden sıralama, daraltma, ... gibi çeşitli değişikliklere izin veren git rebase - interactive kullanabilirsiniz.

Bunun sorunuzu cevaplaması gerektiğini düşünüyorum. Ancak, not olduğunu size varsa itilen uzak bir depo kodu ve insanlar o zaman bu onların kod geçmişleri yanı sıra yaptıklarını işin yukarı karışıklık oluyor, ondan çekti. Bu yüzden dikkatlice yapın.


Teoride iyi cevap, pratikte güçlü tehlikeli: bkz. Stackoverflow.com/questions/253055#432518
VonC

0

Git Uzantıları kullanıyorsanız: Tamamlama ekranına gidin, aşağıda görülebileceği gibi alt kısımda "Tamamlama Değişikliği" yazan bir onay kutusu olmalıdır:

resim açıklamasını buraya girin


@KrunalPandya evet, ya da sadece taahhüt ve basın basın
batsheva
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.