Introduzione

Quando lavori con Git, potresti voler annullare l'ultimo commit. Un commit è un'istantanea di un repository Git in un dato momento. Git ha una variabile di riferimento chiamata HEAD che punta all'ultimo commit nel ramo di lavoro corrente. Per annullare un commit, tutto ciò che devi fare è puntare la variabile HEAD allo snapshot precedente.

Questa guida spiega come annullare l'ultimo commit Git su Linux.

Non è consigliabile annullare un commit già inviato a un repository condiviso. Se desideri modificare solo il messaggio di commit, consulta questo articolo.

Architettura Git Three-Tree (a tre alberi)

In Git puoi annullare le modifiche utilizzando il comando git reset seguito dall'identificatore di commit.

git reset accetta argomenti aggiuntivi che ti consentono di controllare il comportamento del comando. Per capire meglio come funziona reset parliamo dei tre diversi trees (alberi) di Git. L'architettura a tre trees è il concetto chiave del sistema di gestione Git. Sono chiamati trees perché rappresentano raccolte di file.

Git gestisce e manipola i seguenti three trees (tre alberi):

  • La directory di lavoro (The Working Directory): una directory che include tutte le sottodirectory e i file sul file system locale associato al repository. Viene spesso definito "albero di lavoro" (working tree). La directory di lavoro è qualcosa come una sandbox in cui è possibile testare le modifiche prima di eseguirne il commit nell'indice di staging.
  • L'indice (The Index): questo albero tiene traccia dei file nuovi o modificati che sono stati aggiunti all'indice con git add, da includere nel commit successivo. Viene spesso definito "area di staging" o "indice di staging".
  • The HEAD- Un puntatore al tuo ultimo commit sul ramo corrente.

Il comando git reset ha tre argomenti che corrispondono ai tre alberi:

  • --soft - Aggiorna il puntatore HEAD al commit specificato. La directory di lavoro e l'indice non vengono modificati.
  • --mixed - Aggiorna il puntatore HEAD e reimposta l'Indice al commit specificato. La directory di lavoro non viene toccata. Questa è la modalità operativa predefinita del comando reset.
  • --hard - Aggiorna il puntatore HEAD e reimposta l'indice e la directory di lavoro sul commit specificato. Fai molta attenzione quando usi questa opzione poiché tutte le modifiche locali che non hai eseguito verranno sovrascritte e perse.

Annullare l'ultimo commit

Per annullare l'ultimo commit senza perdere le modifiche apportate ai file locali e all'indice, invoca git reset con l'opzione --soft seguita da HEAD~1:

git reset --soft HEAD~1

HEAD~1 è una variabile che punta al commit precedente. Il comando precedente sposta il ramo corrente indietro di un commit, annullando di fatto l'ultimo commit. Se esegui il comando git status, vedrai che i file modificati sono elencati come modifiche non salvate.

Per aggiornare il puntatore HEAD per reimpostare l'indice, esegui git reset con --mixed o senza un'opzione:

git reset --mixed HEAD~1
git reset HEAD~1

I file modificati vengono mantenuti, ma a differenza dell'esempio precedente, ora le modifiche non vengono preparate per il commit.

Se non desideri conservare le modifiche apportate ai file, richiama il comando git reset con l'opzione --hard:

git reset --hard HEAD~1

Prima di eseguire un hard reset, assicurati di non aver più bisogno delle modifiche.

Annullare più commit

Con git reset, puoi tornare a qualsiasi commit precedente.

Ad esempio, per spostare il ramo corrente indietro di tre commit, dovresti usare:

git reset --hard HEAD~3

Dal momento che stiamo utilizzando --hard, il comando sopra rimuoverà le ultime tre istantanee dalla cronologia di commit.

Un altro modo per tornare a un commit specifico è passare l'ID del commit al comando git reset.

Utilizzare git log --oneline per trovare gli ID commit:

git log --oneline

Il comando mostrerà un elenco di tutti i commit, incluso l'ID e la prima riga del messaggio di commit:

42912333 (HEAD -> master) Update changelog
6505778c adding new tests
650862ab new blog post
85a63416 sort configuration file
152032c4 Refactor User class
...

Una volta che conosci l'ID del commit a cui vuoi reimpostare, passa l'ID al comando git reset:

git reset --hard 85a63416

Conclusione

Per annullare l'ultimo commit, usa il comando git reset. Non reimpostare i commit trasferiti in quanto potrebbe potenzialmente causare molti problemi al tuo team.