git reset

Cofa HEAD do wskazanego commita, opcjonalnie modyfikując poczekalnię i drzewo robocze.

git reset to scyzoryk do cofania historii i odsztaplowywania zmian w lokalnym repozytorium. Przesuwa wskaźnik HEAD (a z nim aktualną gałąź) na wskazany commit i — zależnie od trybu — decyduje, co zrobić z poczekalnią (indeksem) oraz drzewem roboczym. Używasz go, gdy chcesz wycofać git add, sklejić kilka świeżych commitów w jeden albo dramatycznie wymazać ostatnie zmiany, jakby się nigdy nie wydarzyły.

Składnia i najważniejsze opcje

Podstawowa forma to git reset [--soft|--mixed|--hard] [] albo wariant na plikach: git reset [] -- <ścieżki>.

  • --soft — przesuwa tylko HEAD; indeks i pliki zostają nietknięte. Zmiany z cofniętych commitów lądują w poczekalni, gotowe do nowego commita.
  • --mixed — tryb domyślny. Przesuwa HEAD i czyści indeks, ale drzewo robocze zostaje. Zmiany trafiają jako niezastagowane.
  • --hard — przesuwa HEAD, czyści indeks i nadpisuje drzewo robocze. Niezacommitowana praca przepada. Tu trzeba być przytomnym.
  • --keep — jak --hard, ale chroni Twoje lokalne, niezacommitowane zmiany — przerwie operację, zamiast je skasować.
  • --merge — resetuje, zachowując zmiany z drzewa roboczego, których nie ma w indeksie; przydatne przy odkręcaniu pomieszanego merge’a.
  • -q — tryb cichy, bez gadania o tym, co zostało zmodyfikowane.

Przykłady użycia

  • git reset — bez argumentów cofa wszystko z poczekalni do stanu niezastagowanego (czyli odwrotność git add); pliki zostają na dysku.
  • git reset plik.txt — odstaplowuje pojedynczy plik, resztę poczekalni zostawia w spokoju.
  • git reset --soft HEAD~1 — cofa ostatni commit, ale jego zmiany trzyma w poczekalni. Klasyk, gdy chcesz poprawić wiadomość commita lub coś dołożyć.
  • git reset --mixed HEAD~3 — rozplata trzy ostatnie commity; zmiany wracają jako niezastagowane, idealne do złożenia ich od nowa.
  • git reset --hard origin/main — twardo zrównuje lokalną gałąź ze zdalną, wyrzucając wszystkie lokalne zmiany. Używaj świadomie.

Częste błędy i pułapki

Nie myl git reset z git revert. Reset przepisuje historię (przesuwa HEAD), a revert tworzy nowy commit cofający zmiany. Na gałęzi już wypchniętej do zdalnego repo reset zmusi Cię do git push --force, co potrafi zepsuć pracę kolegom z zespołu. Na współdzielonych gałęziach wybieraj revert.

--hard nie pyta o zdanie. Niezacommitowane i niezastagowane zmiany znikają bezpowrotnie. Zanim go odpalisz, rzuć okiem na git status, a jeśli chcesz odzyskać skasowany commit — sprawdź git reflog, bo sam commit zwykle jeszcze przez jakiś czas siedzi w bazie obiektów. Pliki nieśledzone (untracked) --hard i tak zostawia.

Pamiętaj o domyślnym trybie. Gdy podasz commit bez flagi, dostajesz --mixed — to częste zaskoczenie u osób, które spodziewały się, że pliki zostaną nietknięte (tak, zostaną, ale poczekalnia już nie). Komenda działa identycznie na Linuksie, macOS i Windowsie.

Powiązane komendy: git revert, git checkout, git restore, git reflog, git status.