2013-01-09 14 views
7

Supponiamo che io ho una storia git lineare di 8 commit e un ramo (master):L'applicazione di git si commette sull'albero di lavoro non aggiunto?

1 -> 2 -> 3 -> 4 -> 5 -> 6 -> 7 -> [8=master] 

voglio passare master 4 (che posso fare con git branch -f master 4):

1 -> 2 -> 3 -> [4=master] -> 5 -> 6 -> 7 -> 8 

Ora l'albero di lavoro è in stato 4.

Ora desidero applicare le modifiche da 4 -> 8 al mio albero di lavoro come patch.

Cioè, senza alterare lo stato della cartella .git, voglio applicare le modifiche da 4->8 non attive al mio albero di lavoro. Dopo questo l'albero di lavoro dovrebbe essere nello stato 8 ma lo stato impegnato e il ramo principale dovrebbero essere nello stato 4.

Un altro modo per dirlo: fingere dopo aver spostato il master a 4, ho apportato le modifiche da 4 a 8 manualmente al mio albero di lavoro senza aggiungerli all'indice. Il risultato dovrebbe essere lo stesso.

Qual è il modo più semplice per farlo?

risposta

1

Nel tuo caso, se in realtà non si preoccupano il bit "non è stato classificato", la cosa più semplice da fare è probabilmente

git checkout 8 -- . 

Questo aggiornerà il vostro albero e l'indice a corrispondere a quello di impegnarsi 8, senza cambiare la cronologia dei commit. È quindi possibile git reset eliminare le modifiche dell'indice.

Se davvero si desidera lasciare il file indice indisturbato, è leggermente più complicato, dato che git aggiorna sempre l'albero di lavoro dall'indice. Si potrebbe fare qualcosa di simile

GIT_INDEX_FILE=/tmp/foo git checkout 8 -- . 

Questa utilizzerà il percorso /tmp/foo come file indice temporaneo solo per questo comando. Potresti quindi voler cancellare questo file in seguito.


In una situazione più complicata in cui si desidera riapplicare le patch, che non sarebbe in realtà si riportano al preciso stato di commettere 8, è possibile utilizzare git cherry-pick --no-commit commit1 commit2 ... per applicare i commit in sequenza. Questo modificherà comunque l'indice, naturalmente.

3
git format-patch 4..8 | xargs git apply 

[edit: questo prossimo dal commento qui sotto salta facendo file di patch individuali]

git diff 4..8 | git apply 
+1

O, ugualmente, 'git diff 4..8 | git apply' – cmbuckley

+0

Mi piace il tuo meglio. – jthill

0
git checkout [email protected]{1} -- . 

è tutto ciò che serve. Legge "verifica i file che il commit su cui puntava il master un tempo fa". Effettua il check-out git reflog per vedere come funziona.

Inoltre, non si dovrebbe forzare nuovamente il ramo come si faceva. Ciò consentirà a git di tenere traccia di tutti i luoghi a cui il maestro puntava. Utilizzare

git stash -u 

nel caso in cui si abbia un po 'di lavoro nel lavoro dir.Poi

git reset --hard master^^^^ 

o

git reset --hard master~4 
+0

_ "Ciò consentirà a git di tenere traccia di tutti i luoghi a cui il master puntava." _ - come intendi? Potresti spiegare un po 'di più questo tracciamento? –

+0

Ha detto che voleva applicare le modifiche non effettuate. Checkout li metterà in scena. – jthill

0
git cherry-pick master~4 master~5 master~6 master~7 master~8 

vostro albero di lavoro deve essere pulito se

git help cherry-pick 
11

So di essere in ritardo alla festa, ma per gli altri di riferimento, ho pensare il modo più semplice è semplicemente:

git cherry-pick --no-commit 4..8

+1

Inoltre 'git reset' dopo di ciò per ottenere le modifiche non previste. –

Problemi correlati