Domanda

Prendete il caso seguente:

Ho un po 'di lavoro in un ramo argomento e ora sono pronto per unire di nuovo da padroneggiare:

* eb3b733 3     [master] [origin/master]
| * b62cae6 2   [topic]
|/  
* 38abeae 1

I eseguire l'unione da maestro, risolvere i conflitti e ora ho:

*   8101fe3 Merge branch 'topic'  [master]
|\  
| * b62cae6 2                     [topic]
* | eb3b733 3                     [origin/master]
|/  
* 38abeae 1

Ora, l'unione mi ha preso un po 'di tempo, così faccio un altro a prendere e notare che il ramo master remoto ha nuove modifiche:

*   8101fe3 Merge branch 'topic'  [master]
|\  
| * b62cae6 2                     [topic]
| | * e7affba 4                   [origin/master]
| |/  
|/|   
* | eb3b733 3
|/  
* 38abeae 1

Se provo 'origine git rebase / master' da padrone, sono costretto a risolvere ancora una volta tutti i conflitti, e ho anche perso l'unione commit:

* d4de423 2       [master]
* e7affba 4       [origin/master]
* eb3b733 3
| * b62cae6 2     [topic]
|/  
* 38abeae 1

C'è un modo pulito per rebase l'unione commettere così finisco con una storia come quella che vi mostro qui di seguito?

*   51984c7 Merge branch 'topic'  [master]
|\  
| * b62cae6 2                     [topic]
* | e7affba 4                     [origin/master]
* | eb3b733 3
|/  
* 38abeae 1
È stato utile?

Soluzione

Ci sono due opzioni qui.

Una è quello di fare un rebase interattivo e modificare l'unione commit, rifare l'unione manualmente e continuare la rebase.

Un altro è quello di utilizzare l'opzione -p su git rebase, che è descritta come segue dal manuale: "Invece di ignorare le unioni, cercare di ricreare loro" Questa domanda spiega ulteriormente: Che cosa significa esattamente "rebase di git --preserve-merge" fanno (e perché?)

Altri suggerimenti

Ok, questa è una vecchia questione ed è già risposta accettata da @siride , ma che la risposta non era abbastanza in il mio caso, mentre le forze --preserve-merges a risolvere tutti i conflitti seconda volta. La mia soluzione basata sull'idea da @Tobi B ma con esatta passo-passo i comandi

Quindi inizieremo a tale stato sulla base di esempio nella domanda:

*   8101fe3 Merge branch 'topic'  [HEAD -> master]
|\  
| * b62cae6 2                     [topic]
| |
| | * f5a7ca8 5                   [origin/master]
| | * e7affba 4
| |/  
|/|   
* | eb3b733 3
|/  
* 38abeae 1

Si noti che abbiamo 2 commit avanti maestri, in modo da cherry-pick non funzionerebbe.

  1. Prima di tutto, creiamo la storia giusta che vogliamo:

    git checkout -b correct-history # create new branch to save master for future
    git rebase -s ours -p origin/master
    

    mezzi -p --preserve-merges, lo usiamo per salvare il nostro merge commit nella storia mezzi -s ours --strategy=ours, lo usiamo per ignorare tutti i conflitti di unione, come non ci importa di quello che i contenuti saranno in quel merge commit, abbiamo solo bisogno di storia piacevole ora.

    La storia ci assomiglia che (master ignorando):

    *   51984c7 Merge branch 'topic'  [HEAD -> correct-history]
    |\  
    | * b62cae6 2                     [topic]
    * | f5a7ca8 5                     [origin/master]
    * | e7affba 4
    * | eb3b733 3
    |/  
    * 38abeae 1
    
  2. Let 's Get indice corretto ora.

    git checkout master # return to our master branch
    git merge origin/master # merge origin/master on top of our master
    

    possiamo ottenere alcuni conflitti di unione aggiuntivi qui, ma questo è solo sarebbe conflitti da file modificati tra 8101fe3 e f5a7ca8, ma non include già risolto i conflitti da topic

    La storia si presenta così (ignorando corretta-storia):

    *   94f1484 Merge branch 'origin/master'  [HEAD -> master]
    |\  
    * | f5a7ca8 5                   [origin/master]
    * | e7affba 4
    | *   8101fe3 Merge branch 'topic'
    | |\  
    | | * b62cae6 2                     [topic]
    |/ /
    * / eb3b733 3
    |/  
    * 38abeae 1
    
  3. L'ultima fase è quella di combinare la nostra filiale con la storia corretta e filiale con indice corretto

    git reset --soft correct-history
    git commit --amend
    

    Usiamo reset --soft per ripristinare la nostra filiale (e la storia) per correggere-storia, ma lasciare indice e albero di lavoro come è. Poi usiamo commit --amend per riscrivere il nostro merge commit, che usato per avere un indice non corretto, con il nostro indice di buona da padrone.

    Alla fine avremo tale stato (nota un altro ID del top commit):

    *   13e6d03 Merge branch 'topic'  [HEAD -> master]
    |\  
    | * b62cae6 2                     [topic]
    * | f5a7ca8 5                     [origin/master]
    * | e7affba 4
    * | eb3b733 3
    |/  
    * 38abeae 1
    

Dato che ho appena perso un giorno cercando di capire questo e in realtà trovato una soluzione con l'aiuto di un collega, ho pensato di carillon.

Abbiamo una grande base di codice e abbiamo a che fare con 2 ramo pesantemente sta modificando allo stesso tempo. C'è un ramo principale e un ramo secondario se che.

Mentre io unire il ramo secondario nel ramo principale, si continua a lavorare nel ramo principale e per il momento ho finito, non riesco a spingere i miei cambiamenti, perché sono incompatibili.

Ho quindi bisogno di "rebase" mio "merge".

Questo è il modo in cui finalmente fatto:

1) Prendere nota del CSA. Es .: c4a924d458ea0629c0d694f1b9e9576a3ecf506b

git log -1

2) Creare la storia corretta, ma questo si romperà l'unione.

git rebase -s ours --preserve-merges origin/master

3) Prendere nota del CSA. Es .: 29dd8101d78

git log -1

4) Ora ripristinare dove eravate prima

git reset c4a924d458ea0629c0d694f1b9e9576a3ecf506b --hard

5) A questo punto unire il master corrente nel vostro lavoro ramo

git merge origin/master
git mergetool
git commit -m"correct files

6) Ora che avete i file giusti, ma la storia sbagliata, ottenere il giusto Storia sulla parte superiore del cambiamento con:

git reset 29dd8101d78 --soft

7) E poi --amend i risultati nella stampa originale impegnano

git commit --amend

Voila!

Sembra che ciò che si vuole fare è rimuovere il prima unione. Si potrebbe seguire la seguente procedura:

git checkout master      # Let's make sure we are on master branch
git reset --hard master~ # Let's get back to master before the merge
git pull                 # or git merge remote/master
git merge topic

che si darebbe quello che vuoi.

  • Dal merge commit
  • cherry-pick il nuovo cambiamento che dovrebbe essere facile
  • copiare la tua roba
  • rifare l'unione e risolvere i conflitti, semplicemente copiando i file dalla vostra copia locale;)
Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top