Fuzionarea unei părți din ramura git în master

Am o ramură simplă cu modificări multiple:

Master ---A---B---C
                   \
              Foo   E---F---G---H

Acum trebuie să mă contopesc în Maestru doar o parte din schimbările mele. Sunt nou în git (în prezent îl folosesc cu SourceCode pe Windows) și mă gândeam să o fac așa:

Master ---A---B---C---?---J---?---?---
                   \     /
              Foo   E---G'
                         \
                    Bar   F'---H'---

Am nevoie doar de anumite piese din ramură. Am lucrat la 4 API-uri de producători diferite de implementat. Acum, doar unul trebuie să intre în producție, iar restul sunt în așteptare. Să presupunem că sunt în total 19 fișiere modificate, dar am nevoie doar de 7 dintre ele. Acum, trebuie să împart acele 7, să sincronizez cu masterul și să împing ca o ramură diferită, astfel încât CTO să le poată îmbina în Master mai târziu.

Acesta este modul de a face asta? Și cum o fac corect?


person Peon    schedule 23.05.2016    source sursă
comment
În imagine, toate modificările au intrat în master. Poate ai vrut doar E F pe Foo, iar G H sa mutat în Bar?   -  person choroba    schedule 23.05.2016
comment
Exact, încă mă lupt cu acest tip de diagrame.   -  person Peon    schedule 23.05.2016
comment
Probabil că poți folosi git --cherry-pick pentru asta   -  person Vishwanath    schedule 23.05.2016
comment
Trecând peste posibilități, cred că acest lucru nu este atât de ușor așa cum am menționat. Modificările pe care trebuie să le commit sunt în mai multe comiteri în ramură, așa că aș avea nevoie de o parte din E, o parte din G și o parte din H pentru a se împărți. Practic, am nevoie de o modalitate de a împinge numai anumite fișiere din ramura mea într-o ramură nouă, care va fi împinsă în master mai târziu în această zi.   -  person Peon    schedule 23.05.2016
comment
git checkout Foo;git reset E --hard;git cherry-pick G;git checkout -b Bar Foo;git cherry-pick F;git cherry pick H Foo este ABCEG', Bar este ABCEG'F'H'.   -  person ElpieKay    schedule 23.05.2016


Răspunsuri (1)


Dacă vă defalcăm problema, trebuie să:

  1. Split 4 (E,F,G,H) comite din Foo în 2 ramuri, Foo va avea doar: E, G, dar Bar va avea toate 4, E -> G -> F -> H.
  2. Eliminați unele comiteri: adică pe Foo, eliminați comiterea F și H.
  3. Nu sunt sigur dacă doriți să „reordonați” comenzile pe bara de ramură, adică să aveți E,G,F,H --> Presupun că acest lucru nu rezolvă niciun scop, așa că o voi lăsa din răspunsul meu.

Există multe moduri de a face acest lucru, dar o voi menține în cel mai simplu flux la care mă pot gândi, deoarece sunteți nou în git. deci, să ne uităm la împărțirea ramurii:

Din Foo actual (cap = H) faceți git checkout -b Bar Acest lucru va crea bara de ramură cu comite E, F, G, H

Acum, există două moduri prin care vă puteți reseta sucursala Foo:
#1 Aruncați Foo și recreați-l git branch -D Foo (pentru a șterge din local) git push origin :Foo (pentru a șterge de la distanță, dacă ați făcut deja a împins-o)

Apoi trebuie să creați un nou Foo din comiterea „C” a maestrului dumneavoastră:

git checkout -b Foo <CommitIdShaForC>

Apoi puteți alege cherry-commit-urile E și G fie din git gui făcând gitk Bar și apoi făcând clic dreapta pe commit și alegând cherry-pick, fie din consolă:

git cherry-pick <Commit Id for E> <Commit Id for G>

În cazul problemelor legate de îmbinare, consultați acest răspuns

#2 Anulați comiterile de la Foo Dacă nu vă deranjează să aveți istoricul F și H în foo, puteți pur și simplu să le anulați în git, în esență, git creează un patch invers al comenzilor dvs. F și H și le aplică ca noi comiteri:

  • Ești pe ramura Foo și are E -> F -> G -> H
  • git revert F
  • Ramura dvs. ar trebui să arate acum E -> F -> G -> H -> F' unde F' anulează ceea ce a adăugat commit-ul F
  • git revert H ar duce la: E -> F -> G -> H -> F' -> H' al cărui rezultat final în codul sursă ar fi: la fel ca a avea doar comite E și G.

Ca alternativă, puteți folosi indicatorul --no-commit pe git revert pentru a reveni atât F, cât și H într-o comitere:

git revert --no-commit F
git revert --no-commit H
git commit -a -m "reverting commits F and H"

Aceasta ar duce la:

E -> F -> G -> H -> I unde I este commit-ul care anulează F și H

#Actualizare 1 După ce am scris un răspuns lung, văd că OP dorește să aibă „o parte din comisioane” în câteva ramuri. Pentru acest caz, aș recomanda cu căldură o rebază interactivă, astfel încât commit-urile să poată fi împărțite. Consultați documentația oficială despre git rebase, în special secțiunea despre „ Împărțirea comisiilor”. De asemenea, cred că veți găsi această întrebare deosebit de utilă

person dubes    schedule 23.05.2016
comment
După cum am scris în comentariu, am nevoie doar de anumite părți din ramură. Am lucrat la 4 API-uri de producători diferite de implementat. Acum, doar unul trebuie să intre în producție, iar restul sunt în așteptare. Să presupunem că sunt în total 19 fișiere modificate, dar am nevoie doar de 7 dintre ele. Acum, trebuie să împart acele 7, să sincronizez cu masterul și să împing ca o ramură diferită, astfel încât CTO să le poată îmbina în Master mai târziu. - person Peon; 23.05.2016
comment
@DainisAbols mi-a actualizat răspunsul cu indicii despre cum puteți împărți comiterile. De asemenea, comentariul dvs. adaugă o claritate semnificativă întrebării dvs., vă rugăm să o editați astfel încât alții să o poată găsi utilă. - person dubes; 23.05.2016
comment
@DainisAbols: aruncați o privire la firul de întrebări pe care l-am atașat, cred că asta este ceea ce doriți să faceți. - person dubes; 23.05.2016
comment
Am ajuns să fac o ramură, din commit E și să o compar cu H. Am luat doar modificările necesare și am făcut o rebase cu ele. În acest fel, am primit datele potrivite într-o ramură separată care a fost îmbinată cu succes în master. Doar anunț. - person Peon; 24.05.2016
comment
A fost greu... situația pe care ați menționat-o a fost într-adevăr una dificilă. Sper că nu trebuie să te confrunți cu mai multe ca ei... dar dacă vine vorba, răspunde la acest comentariu și îl putem muta într-un chat și încercăm să descoperim git interactive rebase - person dubes; 24.05.2016