Yasin Ateş

Git’te Yanlış Commit’i Kurtarma: git reset, git revert ve git reflog ️

Git’te Yanlış Commit’i Kurtarma: git reset, git revert ve git reflog ️

git push yaptıktan sonra "Dur, ben bunu yapmayacaktım" diye içinizden geçirdiğimiz olmuştur mutlaka 🥲 Bu yazıda git reset, git revert ve git reflog komutlarını gerçek senaryolar üzerinden ele alacağız.

Git Neyi Kaydeder, Neyi Siler?

Git’te “silinen” bir şey aslında çoğu zaman gerçekten silinmiş değildir. Git her commit’i bir snapshot olarak saklar ve bu snapshot’lar birbirini referans eden bir zincir oluşturur. Branch’ler bu zincirdeki belirli bir halkayı işaret eden pointer’lardır. git reset komutunu çalıştırdığımızda branch pointer'ı geriye taşıyoruz; commit nesnesi hemen silinmiyor. git reflog da tam bu noktada devreye giriyor: HEAD'in tüm hareketlerini kayıt altında tutuyor.

Yani git reset --hard ile mahvettiğimizi düşündüğümüz commit'i 90 gün içinde (garbage collection süresi default 90 gün) kurtarmamıza olanak tanıyor.

📝 Git’in iç yapısı hakkında çok daha kapsamlı bir içerik okumak istiyorsanız daha önce yazdığım Sıfırdan İleri Seviyeye: Git Versiyon Kontrol Sistemi makalesine göz atabilirsiniz.

↩️ git reset: Henüz Push Edilmemiş Hataları Geri Alma

git reset modları

git reset ‘in 3 farklı modu var ve hangisini kullandığımız, değişikliklerin nereye gideceğini belirliyor.

★— soft: Commit’i Geri Al, Değişiklikleri Koru

Commit mesajını kötü yazdınız ya da birkaç commit’i tek bir temiz commit’te birleştirmek istiyorsunuz. --soft tam bu iş için.

Son commit’i geri alıp değişiklikleri staging area’da bırakalım:

git reset --soft HEAD~1
  • HEAD~1: Bir önceki commit'e git demek. HEAD~3 yazarsak üç commit geriye gideriz.
  • Değişiklikler staging area’da kalır; yani git add yapmamıza gerek yok, direkt git commit yazabiliriz.
  • Beklenen sonuç: git status çalıştırdığımızda değişiklikler "Changes to be committed" bölümünde görünür.
# Son 3 commit'i tek bir commit'te birleştirmek için
git reset --soft HEAD~3
git commit -m "feat(auth): kullanıcı giriş sistemi tamamlandı"

★ — mixed: Commit’i Geri Al, Staging’i de Temizle

Bu, git reset'in varsayılan davranışı. Commit geri alınır, değişiklikler çalışma dizininde kalır ama staging area temizlenir.

git reset HEAD~1
# veya açıkça yazarsak:
git reset --mixed HEAD~1
  • Değişiklikler dosyalarda duruyor ama git add yapılmamış halde.
  • Hangi dosyaları commit’e dahil etmek istediğimizi yeniden seçme şansı verdiği için en sık kullandığımız mod bu.
  • Beklenen sonuç: git status çalıştırdığımızda değişiklikler "Changes not staged for commit" bölümünde görünür.

★ — hard: Her Şeyi Sil, Temiz Stage

Commit’i ve o commit’te yapılan tüm değişiklikleri tamamen silmek istiyoruz. Dikkatli olmamız gereken tek mod bu.

git reset --hard HEAD~1
  • Değişiklikler hem staging area’dan hem çalışma dizininden uçuyor.
  • Dosyalar commit öncesi haline dönüyor.
  • Beklenen sonuç: git status "nothing to commit, working tree clean" diyor.

Belirli bir commit hash’ine de resetleyebiliriz:

# Önce hangi commit'e dönmek istediğimizi bulalım
git log --oneline

# Çıktı:
# f4e5d6c feat: ödeme sayfası eklendi
# a1b2c3d feat: ürün listesi tamamlandı ← buraya dönmek istiyoruz
# b7a8c9d feat: anasayfa tasarımı

git reset --hard a1b2c3d
  • git log --oneline bize her commit'in kısa hash'ini ve mesajını tek satırda gösteriyor.
  • Hash’in tamamını yazmak zorunda değiliz; ilk 7 karakteri yeterli.

★Reset Yaparken Bilmemiz Gereken Kritik Kural

git reset yalnızca henüz push etmediğimiz commit'ler için güvenli. Push edilmiş commit'lere reset yapıp sonra git push --force yaparsak, takım arkadaşlarımızın yerel repolarını karıştırırız. Paylaşılan branch'lerde bir sonraki bölümde değindiğim git revert'i kullanmamız daha faydalı olur

🔄 git revert: Push Edilmiş Hataları Güvenle Geri Alın

git revert geçmişi silmiyor. Seçtiğimiz commit'in tam tersini yapan yeni bir commit oluşturuyor. Bu yüzden main veya develop gibi paylaşılan branch'lerde en güvenli seçeneklerden birisi

Diyelim ki production’a hatalı bir commit push ettik:

# Önce hangi commit'i geri almak istediğimizi bulalım
git log --oneline

# Çıktı:

# c3d4e5f fix: sepet hesaplama düzeltildi ← bu commit hatalıydı

# a1b2c3d feat: ürün detay sayfası eklendi
# b7a8c9d feat: anasayfa tamamlandı

Hatalı commit’i revert edelim:

git revert c3d4e5f
  • Git otomatik olarak bir commit mesajı önerir: Revert "fix: sepet hesaplama düzeltildi"
  • Mesajı değiştirmek istiyorsak editör açılır; değiştirmek istemiyorsak --no-edit ekleyebiliriz.
  • Beklenen sonuç: git log --oneline çalıştırdığımızda yeni bir revert commit görürüz, eski commit hala geçmişte duruyor.
# Editörü açmadan direkt revert et
git revert c3d4e5f --no-edit

# Push et — takım arkadaşlarında sorun çıkmaz
git push origin main

Birden Fazla Commit’i Revert Etmek

Son 3 commit hatalıysa hepsini tek seferde revert edebiliriz:

# En eski commit'ten başlayarak en yeniye doğru revert eder
git revert HEAD~3..HEAD --no-edit
  • HEAD~3..HEAD: Son 3 commit aralığını belirtiyor.
  • Her commit için ayrı bir revert commit oluşturuyor.

Merge Commit’i Revert Etmek

Merge commit’leri biraz daha özel. Hangi parent’ı temel alacağımızı söylememiz gerekiyor:

git log --oneline

# Çıktı:
# e6f7a8b Merge branch 'feature/odeme' into main
# ...

git revert -m 1 e6f7a8b
  • -m 1: "Parent 1'i temel al" demek. Parent 1 genellikle merge yapılan branch (main), parent 2 ise merge edilen branch (feature/odeme).

Beklenen sonuç: feature branch’inde yapılan tüm değişiklikler geri alınmış yeni bir commit oluşur.

🕵️ git reflog: “Her Şeyi Mahvettim” Dediğiniz An İçin

git reflog

git reflog, HEAD'in tüm hareketlerini tarih sırasıyla kaydeder. git reset --hard yapsanız bile, branch silinmiş olsa bile, reflog bu hareketleri tutar.

git reflog

Örnek çıktı:

c3d4e5f HEAD@{0}: reset: moving to HEAD~2
f4e5d6c HEAD@{1}: commit: feat: bildirim sistemi eklendi
a1b2c3d HEAD@{2}: commit: feat: ürün favorileme eklendi
b7a8c9d HEAD@{3}: checkout: moving from feature to main
e6f7a8b HEAD@{4}: commit: fix: giriş formu validasyonu düzeltildi
  • HEAD@{0}: En son hareket.
  • HEAD@{1}: Bir önceki konum; yani git reset --hard yapmadan önceki commit.
  • Soldaki hash: O hareketteki commit’in hash’i.

Senaryo 1: git reset — hard ile Commit’i Kaybettim

# Önce reflog'a bakalım, kaybettiğimiz commit'i bulalım
git reflog

# f4e5d6c HEAD@{1}: commit: feat: bildirim sistemi eklendi ← bu kayboldu

# O commit'e geri dönelim
git reset --hard f4e5d6c
  • Beklenen sonuç: Çalışma dizinimiz o commit’teki halini alıyor, hiçbir şey kaybolmamış gibi devam edebiliriz.

Senaryo 2: Silinen Branch’i Kurtarmak

Branch’i sildik ama içindeki commit’leri kurtarmak istiyoruz:

git reflog

# a1b2c3d HEAD@{2}: commit: feat: dashboard tamamlandı ← silinen branch'teki son commit

# Yeni bir branch oluşturup o commit'i işaret ettirelim
git checkout -b kurtarilan-branch a1b2c3d
  • Beklenen sonuç: kurtarilan-branch adında yeni bir branch oluşuyor ve o commit'teki tüm dosyalara erişebiliyoruz.

Senaryo 3: Kaybolan Stash’i Kurtarmak

git stash drop ile yanlış stash'i sildiyseniz reflog yine yardımcı olabilir:

git reflog stash

# Çıktı:
# a1b2c3d refs/stash@{0}: WIP on main: b7a8c9d dashboard başlangıcı
# f4e5d6c refs/stash@{1}: WIP on feature: e6f7a8b ödeme formu
# Kaybolan stash'i yeni bir branch olarak kurtaralım
git checkout -b stash-kurtarma f4e5d6c
💡 git reflog bana kalırsa aralarında en önemlisi. Branch veya tag’e bağlı olmayan, force push, hard reset yapıp, bütün tuşlara bastıktan sonra herşeyi mahvettiğimizi anladığımızda kullanabileceğimiz harika bir komut. Hatta benim de şuan içinde bulunduğumuz makaleyi yazma sebebim diyebilirim

🎯 Hangi Komutu Ne Zaman Kullanmalıyız?

git reset, git reflog, git revert ne zaman hangisi kullanılmalı

Henüz push etmediğim commit’leri geri almak istiyorum git reset kullanırız. Değişiklikleri tamamen silmek istemiyorsak --soft veya --mixed, her şeyi silmek istiyorsak --hard.

Push edilmiş bir commit’i geri almam gerekiyor git revert kullanırız. Takım arkadaşlarımızın çalışmasını bozmadan güvenle geri alırız.

git reset — hard yaptım ve commit’i kaybettim git reflog açarız, kaybolan commit'in hash'ini buluruz, git reset --hard <hash> ile geri döneriz.

Sildiğim branch’i kurtarmam gerekiyor git reflog ile o branch'in son commit'ini buluruz, git checkout -b <yeni-ad> <hash> ile kurtarırız.

Staging area’ya yanlış dosya ekledim, henüz commit etmedim git restore --staged <dosya> kullanırız. Reset'e gerek yok.

Commit etmediğim dosya değişikliğini geri almak istiyorum git restore <dosya> kullanırız. Bu değişiklik geri alınamaz olduğundan dikkatli olmak gerekiyor.

📬 Geri Bildirim

Makaleyi yazarken, kaynakları belirleme ve araştırma için kendi notlarımı, yazım denetimi ve ek araştırma için Claude Opus 4.6 ve GPT 5.2 modellerini kullandım. Resimleri üretmek için ise Gemini 3 Pro Preview 2k (Nano Banana Pro) ve GPT Image 1.5 High Fidelity modellerini kullandım.

Yazı ile ilgili tavsiye, öneri, eleştirileri dikkate alıyorum. İletişime geçmek isterseniz bana websitemdeki sosyal medya adreslerimden veya Linkedin üzerinden ulaşabilirsiniz.

Sevgiyle kalın, Yasin 🤗

📚 Makaleyi Yazarken Kullandığım Kaynaklar