Yeniden düzenleme ve itilen taahhütleri yeniden sıralama ile ne anlama gelir?


109

Sıklıkla, zaten bastırmış olduğunuz taahhütleri yeniden ödememeniz gerektiği söylenir. Bunun anlamı ne olabilir?

Yanıtlar:


80

ProGit kitap bir sahiptir iyi bir açıklama .

Sorunuzun özel cevabı " Yeniden Satış Tehlikeleri " başlıklı bölümde bulunabilir . O bölümden bir alıntı:

Bir şeyleri yeniden sıraladığınızda, mevcut taahhütleri terk ediyorsunuz ve benzer ancak farklı olan yenilerini oluşturuyorsunuz. Bir yere commit'leri ittirirseniz ve diğerleri onları aşağı çeker ve üzerinde çalışmayı temel alırsa ve daha sonra bu commit'leri git rebase ile yeniden yazar ve onları tekrar yükseltirseniz, işbirlikçilerinizin çalışmalarını yeniden birleştirmeleri gerekecek ve siz denediğinizde işler karışacak işlerini kendinize geri çekin.

Güncelleme:
Aşağıdaki yorumunuza dayanarak, Git iş akışınızda zorluk yaşıyormuşsunuz gibi görünüyor. Yardımcı olabilecek bazı referanslar şunlardır:


Açıklama için teşekkürler. Yani, sadece anlayışımı daha net hale getirmek için, bazı değişiklikleri git rebasezorladıktan sonra, bu geçmişi yeniden yazmak için (--interactive?) Kullanmamalıyım, bu kesin bir başarısızlık reçetesidir. şube (X dalından) ve itin, başka bir geliştirici konu dalını değiştirdikten sonra yeniden taban yapmak tamamen normaldir. Esasen, mergeepeydir kullanıyorum , ancak darwinweb.net/articles/86 ile aynı gemideyiz ve tarih neredeyse kullanılamaz.
Hemant Kumar

@Hemant: Bir kamu deposuna gönderdikten sonra yeniden satış yapmak genellikle kötü bir fikirdir. Bununla birlikte, iş akışınız onlarınkine benziyorsa, alıntı yaptığınız darwinweb makalesindeki tavsiyeler mantıklı geliyor. Yardımcı olabilecek diğer referansların bir listesi için güncellenmiş yanıtıma bakın.
Tim Henigan

"Özel Yönetilen Takımı" hakkında "ProGit" sayfasına bir bağlantı güncelleyin git-scm.com/book/en/...
Eimantas

Yani teknik olarak, git commit'ler aynı kalıyor ama "mevcut commitleri bırakmak ve benzer fakat farklı olan yenilerini yaratmak" farklı sha1 id ile aynı commit mi? Peki, ortak çalışanların neden kendi çalışmalarını yeniden birleştirmek zorunda olduklarını düşünebilmemin tek açık yolu bu olurdu!
Ciasto piekarz

@Ciastopiekarz, bunun nedeni, yukarı akış deposunda geçmişi yeniden yazmanızdır ve diğer geliştiricinin yerel depolarında buna işaretler olabilir. Şimdi işaretçileri bayat: git istemcisinin eski işaretçileri kullanmaktan başka alternatifi yok ve gerisini çözmesi için insana güveniyor. Bu bir yeniden birleştirmedir ve manuel olarak düzenlenmesi gereken birçok kafa karıştırıcı değişiklikle ÇOK karmaşık olabilir! Bu nedenle, halihazırda bir upstream repoya itilmiş herhangi bir şeyi asla geri ödememe tavsiyesi. Bu iyi bir tavsiye ve derin bilgiye sahip bir uzman değilseniz göz ardı edilmemelidir.
Forbin

240

Bunu anlamak için git'in nasıl çalıştığını biraz anlamamız gerekiyor. Git deposu, ağacın düğümlerinin tamamlandığı bir ağaç yapısıdır. İşte çok basit bir havuz örneği: Çatalladığında

ana dalda dört işlemesi vardır ve her işlemenin bir kimliği vardır (bu durumda, a, b, c ve d). D'nin şu anda ana dalın en son kaydı (veya HEAD) olduğunu fark edeceksiniz. görüntü açıklamasını buraya girin

Burada iki şubemiz var: usta ve benim şubem. Ana ve dalımın her ikisinin de a ve b taahhütlerini içerdiğini görebilirsiniz, ancak sonra ayrılmaya başlarlar: ana dal c ve d içerirken, benim-dalım e ve f içerir. b'nin, ana şubeye kıyasla dalımın "birleştirme tabanı" olduğu söylenir - veya daha yaygın olarak, yalnızca "taban". Bu mantıklı: Dalımın önceki bir master sürümüne dayandığını görebilirsiniz.

Öyleyse, benim şubemin eskimiş olduğunu ve onu master'ın en son sürümü ile güncellemek istediğinizi varsayalım. Başka bir deyişle, dalımın c ve d içermesi gerekir. Birleştirme yapabilirsiniz, ancak bu, dalın, çekme isteğini gözden geçirmeyi çok daha zor hale getiren garip birleştirme taahhütleri içermesine neden olur. Bunun yerine bir geri ödeme yapabilirsiniz.

görüntü açıklamasını buraya girin

Rebase yaptığınızda, git dalınızın tabanını bulur (bu durumda, b), o taban ile HEAD arasındaki tüm işlemleri bulur (bu durumda, e ve f) ve bu taahhütleri şubenin HEAD'inde yeniden oynatır geri dönüyorsunuz (bu durumda, usta) Git aslında, yaptığınız değişikliklerin master üzerinde nasıl göründüğünü temsil eden yeni commit'ler yaratır: diyagramda, bu kayıtlara e ′ ve f ′ denir. Git önceki taahhütlerinizi silmiyor: e ve f'ye dokunulmadan kalır ve yeniden temelde bir şeyler ters giderse, eskiden olduğu gibi geri dönebilirsiniz.

Bir proje üzerinde birçok farklı kişi benzer şekilde çalışırken, çekme talepleri hızlı bir şekilde geçerliliğini yitirebilir. "Eski" bir çekme isteği, ana geliştirme hattıyla artık güncel olmayan bir taleptir ve projeyle birleştirilmeden önce güncellenmesi gerekir. Çekme isteklerinin eskimiş olmasının en yaygın nedeni çakışmalardır: iki çekme isteğinin ikisi de aynı dosyadaki benzer satırları değiştirir ve bir çekme isteği birleştirilirse, birleştirilmemiş çekme isteğinde artık bir çakışma olacaktır. Bazen, bir çekme isteği çakışma olmadan eskimiş olabilir: belki kod tabanındaki farklı bir dosyadaki değişiklikler çekme isteğinizde yeni mimariye uymak için karşılık gelen değişiklikleri gerektirebilir veya belki de dal, biri başarısız olan birim testlerini yanlışlıkla ana şube. Sebep ne olursa olsun,


68

Yeniden kaplama, geçmişi yeniden yazar. Bu tarihi kimse bilmiyorsa, o zaman bu tamamen iyidir. Bununla birlikte, bu tarih herkes tarafından biliniyorsa, Git'te tarihi yeniden yazmak gerçek dünyada olduğu gibi çalışır: bir komploya ihtiyacınız var.

Komploların bir arada tutulması gerçekten zordur, bu yüzden ilk etapta kamu şubelerini yeniden düzenlemekten kaçınmalısınız.

Orada unutmayın şunlardır : Başarılı komplolar örnekleri puJunio C. Hamano en git depo dalı (Git SCM resmi deposu) sık sık rebased. Bunun çalışma şekli, kullanan hemen hemen herkesin puaynı zamanda Git geliştirici posta listesine abone olması ve puşubenin yeniden yayınlanması gerçeği posta listesinde ve Git web sitesinde yaygın olarak duyuruluyor.


4
+1. Bence pugit.git şubesi, (genel) bir iş akışında rebase'in nasıl kullanılacağına dair son derece yararlı bir örnek. Buna aşina olmayanlar için genel fikir, herhangi bir taahhüdü olmayan konu dallarını next(ana ile birleştirmeden hemen önce istikrarsız dal) yeniden tabanlamak, ardından tüm konu dallarını pusıfırlayarak nextve birleştirerek şubeyi yeniden oluşturmaktır . (Kaynak: Documentation / howto / protect-git.txt git.kernel.org/?p=git/git.git;a=blob;f=Documentation/howto/… )
Cascabel

25
"Git'te tarihi yeniden yazmak için +1 gerçek dünyada olduğu gibi çalışır: bir komploya ihtiyacınız var"
Sleeper Smith

"Pu, yukarıda açıklandığı gibi, bir atılan dal olduğu için halka açık bir duyuru gerekli değildir." git-scm.com/docs/gitworkflows İşte benzer bir şey yapıyoruz, "TEMP-en son bir şey", en son değişikliklerin birleşimi olan bir daldır, birden fazla özellik dalının birleşmesi olabilir, silinebilir ve herhangi bir zamanda yeniden yaratılmalı ve geliştirilmemelidir.
pilkch

6

Yeniden ödeme, deponuzun geçmişini değiştirir. Taahhütleri dünyaya yayarsanız, yani başkalarına açık hale getirirseniz ve sonra taahhüt tarihine ilişkin görüşünüzü değiştirirseniz, eski geçmişinize sahip herhangi biriyle çalışmak zorlaşır.

Zararlı olarak kabul edilen yeniden temelin iyi bir genel bakış olduğunu düşünüyorum.

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.