TL;DR: .gitignore çalışmıyorsa dosya neredeyse her zaman zaten takiptedir. Git, hiç görmediği dosyaları yok sayar — index’teki bir dosya, yazdığınız hiçbir kuraldan etkilenmez. Gerçeği git check-ignore -v <path> ile öğrenin: sessiz çıktı, yolun takipte olduğunu ve hiçbir kuralın geçerli olmadığını gösterir. git rm --cached <path> ile düzeltin, commit’leyin; yok sayma kuralı o commit’ten itibaren çalışmaya başlar. Kural sırası, olumsuzlama tuzakları ve VS Code kırmızı ringaları kalan vakaları açıklar.
.gitignore neden çalışmıyor?
Tek mekanizma, vakaların çoğunluğunu karşılar: dosya, kuraldan önce commit’lenmiş. .gitignore, dosyaları git’ten saklayan bir filtre değildir — git add‘in takipsiz hâldeki hangi dosyaları alacağına dair bir kuraldır. Bir dosya index’e girdikten sonra git, onu açıkça takipten çıkarana dek içerik değişikliklerini izlemeye devam eder. Olay olduktan sonra .gitignore‘u düzeltmek, takipli dosyalar açısından hiçbir şeyi değiştirmez; ”.env‘i commit’le, panikle, .env‘i .gitignore‘a ekle, tekrar commit’le” klasik dizisinin her push’ta sırrı göndermeye devam etmesinin sebebi budur.
Bu herkesi ısırır, çünkü git neredeyse evrenseldir — Stack Overflow 2022 anketi, Git kullanımını profesyonel geliştiricilerin %93’ünün üzerinde ölçtü (survey.stackoverflow.co) — ve bu geliştiricilerin her biri, er ya da geç geçen hafta commit’lediği bir dosya için kural yazar.
Bu yazının geri kalanı azınlıktaki vakaları kapsıyor: kural sırası hataları, olumsuzlama tuzakları, klasör uç durumları ve IDE sorusu. Ama önce bir sonraki bölümdeki sağlık kontrolünü çalıştırın — on seferin dokuzundan fazlasında araştırmayı orada bitirirsiniz.
Bir dosyayla hangi gitignore kuralının eşleştiğini nasıl görürüm?
git check-ignore teşhis aracıdır ve sessizliği başlı başına bir teşhistir:
# Kural geçerliyse eşleşen kural + dosya + satır numarasını yazar
git check-ignore -v debug.log
# .gitignore:3:*.log debug.log
# Hiçbir kural geçerli değilse HİÇBİR ŞEY yazmaz — dosya takipte (ya da kural yok)
git check-ignore -v src/.env
# (sessizlik = .gitignore bu yolu yok saymıyor, ne yazdıysanız)
# Çıkış kodları: 0 = yok sayılıyor, 1 = yok — betikte kullanılabilir
git check-ignore -q debug.log && echo "ignored" || echo "tracked or unruly" -v çıktısını okuma: önce yok sayma kaynağı (.gitignore, .git/info/exclude ya da genel ignore dosyanız), sonra satır-numarası:kalıp, sonra yol. Sonraki bir kural sizi şaşırttıysa önceliği hatırlayın: son eşleşen kural kazanır — *.log‘dan sonra gelen !important.log, o tek dosyayı geri dahil eder.
Zaten commit’lenmiş dosyalar için gitignore neden çalışmıyor?
Dosyayı takipten çıkarın, diskte tutun, silmeyi commit’leyin:
# Tek dosyayı takipten çıkar (diskteki kopya sağ kalır — --cached yalnızca index'e dokunur)
git rm --cached .env
git commit -m "stop tracking .env"
# Kuralın artık geçerli olduğunu doğrula
git check-ignore -v .env Bu commit’ten itibaren yolun sahibi .gitignore‘dur: üzerindeki düzenlemeler git status‘ta görünmez, git add . onu yeniden almaz. Ama dosya geçmişte durmaya devam eder — sır söz konusuysa, son commit’ten kaldırmak yetmez. Kimlik bilgisini değiştirmek (rotate) tek gerçek çözümdür; geçmiş yeniden yazımı ise kozmetiktir (ve son commit’i geri almak, yalnızca kötü commit hâlâ uçtayken işe yarar).
Baştan commit’lenmiş çöp dolusu bir repo için — build çıktısı, editör artıkları, erken sızan node_modules — toplu takipten çıkarma iki satırlıktır:
git rm -r --cached .
git add .
git commit -m "apply .gitignore to tracked files" Bu, index’i güncel kurallara göre yeniden kurar: yok sayılan yollar düşer, geri kalan her şey değişmeden yeniden eklenir. Diff dramatik görünür (binlerce silme) ama diskten hiçbir şey silinmez. Amacınız dosyaları yalnızca takipten çıkarmak değil silmekse o iş git clean -fdx‘e düşer — bkz. git remove untracked files: güvenli yöntem.
Git, hiç görmediği dosyaları yok sayar. Index’te duran bir dosya
.gitignore‘a karşı bağışıktır — yazacağınız hiçbir kural onu geri göremez.
Klasörler için gitignore neden çalışmıyor?
Üç klasöre özgü tuzak:
1. Sondaki eğik çizgi eşleşmeyi değil, niyeti belli eder. build de build/ de bir dizinle eşleşir ama build/, kastettiğinizin yalnızca dizin olduğunu belgeler — build adında bir dosya bundan kurtulur. Simetri ise geri dahil etmede bozulur (sonraki tuzak).
2. Olumsuzlama, hariç tutulmuş bir dizin içindeki dosyaları kurtaramaz. Git belgeleri tereddütsüz: “Bir dosyanın üst dizinlerinden biri hariç tutulmuşsa, o dosyayı yeniden dahil etmek mümkün değildir” (git-scm.com/docs/gitignore). Bu bir performans kararıdır — git, hariç tutulan dizinleri tek tek gezmek yerine topluca atlar. Yani bu çalışmaz:
build/
!build/keep.me # ölü kural — git build/ içine hiç bakmaz Çözüm, dizinin değil içeriğin hariç tutulması:
build/*
!build/keep.me # çalışır — build/ kendisi incelemeye hâlâ açık 3. İç içe .gitignore dosyaları kendi alanlarında kazanır. subdir/.gitignore içindeki kurallar, subdir altındaki yollar için kök dosyayı geçersiz kılar. git check-ignore -v beklemediğiniz bir yok sayma kaynağı gösterdiğinde sebep genellikle budur.
VS Code’da gitignore neden çalışmıyor?
Neredeyse hiçbir zaman VS Code yüzünden değil. Editörün Source Control görünümü, git’in okuduğu aynı index’i okur; belirti aynıdır: dosya çoktan commit’lenmiştir ve hiçbir IDE yeniden başlatması index’i değiştirmez. Yine de bilinmeye değer iki VS Code komşusu gerçek:
- Explorer’da soluk = yok sayılıyor; turuncu/sarı = değişikliği olan takipli dosya. Yok saydıktan sonra modified görünen dosya, takipte olduğunun teyididir — yukarıdaki
git rm --cachedçözümünü çalıştırın. - Explorer’ın changed listesinde bir dosyanın hiç belirmemesi, kuralın çalıştığı anlamına gelir — dosya ilk etapta takipsiz olarak ortaya çıkmamıştır. İnsanlar “VS Code gitignore’umu görmezden geliyor” derken çoğu zaman CLI
git statusile bayat bir SCM görünümü çelişiyordur; git’i suçlamadan pencereyi yenileyin (Cmd/Ctrl+Shift+P→ “Reload Window”).
.gitignore mu, .git/info/exclude mu, global mi: hangisi ne zaman?
| Dosya | Kapsam | Commit’lenir mi? | Ne için |
|---|---|---|---|
.gitignore (repo) | Klonlayan herkes | Evet | Build çıktısı, bağımlılıklar, .env — paylaşılan kurallar |
.git/info/exclude | Yalnızca sizin klonunuz | Hayır | Kişisel artıklar: .scratch/, editör çöpleri |
core.excludesFile (global) | Tüm repolarınız | Hayır | İşletim sistemi çöpü: .DS_Store, Thumbs.db, *.swp |
.gitignore + olumsuzlama | Repo | Evet | Takipli config istisnalarını geri dahil etme |
Global dosya, çoğu geliştiricinin hiç ayarlamadığı ve ayarlaması gereken dosyadır:
git config --global core.excludesFile ~/.gitignore_global
printf '.DS_Store\nThumbs.db\n*.swp\n' >> ~/.gitignore_global Kopyalamaya değer ev kuralı: kural bütün takıma fayda sağlıyorsa repoya aittir; yalnızca size fayda sağlıyorsa exclude‘a ya da global dosyaya. Kişisel yok sayma kurallarını commit’lemek, .gitignore dosyalarının 300 satıra uzamasının ve hangi yarısının hâlâ önemli olduğunu kimsenin bilmediği sebeptir.
Takipli bir dosyanın değişikliklerini nasıl yok sayarım?
Bazen takipli bir dosyayı istersiniz (bir config şablonu, bir IDE ayar dosyası) ama yerel düzenlemelerinizin git status‘ta belirmesini istemezsiniz. git update-index üzerinde iki flag var; ikisi de takım iş akışına ait değildir:
git update-index --skip-worktree config/local.dev # yerel düzenlemeler sessizleşir
git update-index --no-skip-worktree config/local.dev # ...ve geri döner --skip-worktree savunulabilir olanıdır — “yerel sürümümün sapması bilinçli” der. Kuzeni --assume-unchanged bir performans sözüdür (“bu dosya değişmeyecek”), yok sayma mekanizması değildir ve git onu sessizce bozabilir. İki flag de, upstream de dosyayı değiştirdiğinde pull anında gürültüyle patlar — kalıcı cevaplar, kuruluş anında exclude üzerinden yerel-özel bir config ya da git’in takip ettiği, sizin kopyaladığınız bir şablon dosyadır (config.example).
30 saniyelik gitignore sağlık kontrolü
git check-ignore -v <path> # hangi kural? (sessizlik = takipte, kural yok)
git ls-files --error-unmatch <path> # dosya hiç takipte mi?
git rm --cached <path> # takipten çıkar, diskte tut
git commit -m "stop tracking <path>"
git check-ignore -v <path> # kural artık görünüyor Teşhis et, takipten çıkar, doğrula. Her “gitignore çalışmıyor” raporunun arkasındaki örüntü, iki şapka giymiş aynı dosyadır — index’in bir yanında takipli, öbür yanında yok sayılan — ve ikinci şapkayı tek bir --cached flag’i çıkarır.
FAQ
.gitignore neden çalışmıyor?
Çoğu durumda dosya zaten takiptedir. Git yalnızca takip edilmeyen dosyaları yok sayar; index'teki bir dosya, git rm --cached ile takipten çıkarıp commit'leyene dek .gitignore'a karşı bağışıktır.
Bir dosyayla hangi gitignore kuralının eşleştiğini nasıl kontrol ederim?
git check-ignore -v <path> çalıştırın. Tam .gitignore satırını ve kural numarasını yazar; dosya takipteyse ve hiçbir kural geçerli değilse sessizce çıkar.
git rm --cached yerel dosyamı siler mi?
Hayır. --cached dosyayı yalnızca index'ten çıkarır; diskteki kopya kalır. Silmeyi commit'leyin, dosya takipsiz olur ve bu noktadan sonra .gitignore geçerli olur.
gitignore, yok sayılan bir klasörün içindeki dosyayı neden geri dahil edemez?
Git performans için hariç tutulan dizinleri tamamen atlar. Git belgelerine göre, bir dosyanın üst dizinlerinden biri hariç tutulmuşsa o dosyayı yeniden dahil etmek mümkün değildir.
— mrsaynothing
Get the next one by email
One email per post. No spam, no algorithms.
what is this?Ollama GPU'yu Kullanmıyor mu? Linux, Windows ve WSL'de Çözüm
Yazıları beğendiniz mi? Ben geçim için böyle inşa ederim. beni işe al