2010-10-19 10 views
294

Ho finito con una testa staccata oggi, lo stesso problema come descritto in: git push says everything up-to-date even though I have local changesPerché il mio repository Git è entrato in uno stato HEAD distaccato?

Per quanto ne so, non ho fatto niente di straordinario, solo impegna e spinge dal mio repo locale.

Quindi come sono finito con un detached HEAD?

+11

Estrazione di una filiale remota sembra come il modo più comune per farlo accidentalmente, un altro modo comune è di controllare "nome-ramo @ {n}", l'ennesima posizione precedente di "nome-ramo". Ma non importa cosa, a un certo punto ci deve essere . stato un 'git checkout ' Se questo non suonare un campanello, allora probabilmente avete fatto quello che sarà ricordato - è tentato di fare '' git checkout ed è riuscito a indicare una revisione per caso – Cascabel

+2

per annullare uno stato HEAD distaccato,. vedi [Fix a Git detached head?] (htt p: //stackoverflow.com/q/10228760/456814). –

+0

Il mio repo è finito in questo stato quando sono stati riscontrati conflitti durante la ridefinizione. Fortunatamente Git mi ha detto cosa fare quando ho eseguito 'git status':' tutti i conflitti risolti: esegui "git rebase --continue" ' – Paul

risposta

213

Qualsiasi checkout di un commit che non è il nome di uno dei numeri dei tuoi rami ti darà un HEAD distaccato. Un SHA1 che rappresenta la punta di un ramo darebbe comunque un TESTO distaccato. Solo il checkout di una filiale locale nome evita tale modalità.

Vedi committing with a detached HEAD

quando la testa si stacca, commette funzionerà come normale, tranne che nessun ramo di nome viene aggiornato. (Si può pensare a questo come un ramo anonimo.)

alt text

Ad esempio, se si verifica un "ramo remoto" senza seguire in primo luogo, si può finire con una testa staccata.

Vedi git: switch branch without detaching head

+12

Un altro modo in cui puoi inserire lo stato della testa staccata è se sei nel mezzo di un rebase interattivo e si desidera modificare uno dei commit. Quando Git ti lascia al commit per la modifica, ti ritroverai in uno stato di testa distaccato fino al termine del rebase. –

+0

In questa guida visiva, c'è questa spiegazione: 'git commit files crea un nuovo commit contenente il contenuto dell'ultimo commit, più un'istantanea di file presi dalla directory di lavoro. Inoltre, i file vengono copiati sullo stage. Che cosa significa "i file vengono copiati sullo stage"? Ho pensato che i file siano stati commessi, il che significa che il palco è stato cancellato? – max

+0

@max: questo estratto si menziona per un 'git commit -a': lo stage non è tanto 'cancellato' quanto 'reso * identico * al nuovo commit', il che significa che qualsiasi nuova modifica verrà rilevata in un 'git diff', perché git diff confronta l'albero di lavoro con l'indice. Ecco perché la [pagina man di '' git commit' (http://git-scm.com/docs/git-commit) descrive l'opzione '-a' come" Comunica al comando di mettere automaticamente in scena i file che sono stati modificati e cancellato " – VonC

8

Può facilmente accadere se si tenta di annullare le modifiche apportate dai file re-check-out e non del tutto ottenere la giusta sintassi.

È possibile osservare l'output di git log - è possibile incollare la coda del registro qui dall'ultimo commit riuscito, e tutti abbiamo potuto vedere cosa avete fatto. Oppure potresti incollarlo e chiedergli gentilmente in #git su IRC freenode.

68

Ho riprodotto questo proprio ora per caso:

  1. elenca le filiali remote

    git branch -r 
         origin/Feature/f1234 
         origin/master 
    
  2. voglio alla cassa uno a livello locale, così ho tagliato pasta:

    git checkout origin/Feature/f1234 
    
  3. Presto!Staccata Head State

    You are in 'detached HEAD' state. [...]) 
    

Soluzione # 1:

Non includere origin/ nella parte anteriore del mio ramo spec al momento del check it out:

git checkout Feature/f1234 

Soluzione n. 2:

Aggiungere -b parametro che crea una filiale locale dal telecomando

git checkout -b origin/Feature/f1234 o

git checkout -b Feature/f1234 cadrà di nuovo all'origine automaticamente

+7

Questa è quasi una grande risposta, ma non riesce a spiegare perché sei entrato in uno stato di testa distaccato. – Goose

+2

Sono d'accordo ma fornisce la soluzione che stavo cercando. Grazie!! – Kilmazing

+0

Ho visto in questa [altra risposta] (https://stackoverflow.com/a/5772882) che 'git checkout -b Feature/f1234' <=>' git branch Feature/f1234' e 'git checkout Feature/f1234'. – Armfoot

7

provare

git reflog 

questo ti dà una storia di come il tuo HEAD e ramificazioni puntatori dove spostato nel passato.

ad es. :

88ea06b HEAD @ {0}: cassa: lo spostamento dallo sviluppo alla telecomandi/origine/SomeNiceFeature e47bf80 HEAD @ {1}: tirare origine SVILUPPO: Avanti veloce

parte superiore di questa lista è uno reasone uno potrebbe incontrare uno stato DETACHED HEAD ... controllando un ramo di monitoraggio remoto.

1

L'altro modo per entrare in uno stato di testa separato da git è provare a eseguire il commit su un ramo remoto. Qualcosa di simile:

git fetch 
git checkout origin/foo 
vi bar 
git commit -a -m 'changed bar' 

Si noti che se si esegue questa operazione, ogni ulteriore tentativo di checkout origine/pippo vi porterà in uno stato di testa staccata!

La soluzione è creare il proprio ramo foo locale che traccia origine/foo, quindi opzionalmente premere.

Questo probabilmente non ha nulla a che fare con il tuo problema originale, ma questa pagina è in cima ai risultati di google per "git detached head" e questo scenario è severamente poco documentato.

1

Un modo semplice accidentale è quello di fare un git checkout head come un errore di HEAD.

Prova questo:

git init 
touch Readme.md 
git add Readme.md 
git commit 
git checkout head 

che dà

Note: checking out 'head'. 

You are in 'detached HEAD' state. You can look around, make experimental 
changes and commit them, and you can discard any commits you make in this 
state without impacting any branches by performing another checkout. 

If you want to create a new branch to retain commits you create, you may 
do so (now or later) by using -b with the checkout command again. Example: 

    git checkout -b <new-branch-name> 

HEAD is now at 9354043... Readme 
+0

Ho dimenticato la testa minuscola. +1. Vedi https://stackoverflow.com/a/4381549/6309 – VonC

+0

Inoltre citato in https://longair.net/blog/2012/05/07/the-most-confusing-git-terminology/ (cerca "" HEAD "E" head "") – VonC

+0

@VonC: grazie per questo link. Sto preparando un allenamento Git e voglio anche sottolineare perché a volte è così confuso. Ho già un sacco di esempi (come 'checkout -b' che sembra un checkout ma in realtà si dirama) ma un altro elenco è solo benvenuto. –

1

Può succedere se si dispone di un tag di nome stesso di un ramo.

Esempio: se "rilascio/0.1" è il nome di tag, quindi

git checkout release/0.1 

produce testa staccata a 'rilasciare/0.1'. Se vi aspettate rilasciare/0.1 a essere un nome ramo, quindi si ottiene confuso.

Problemi correlati