Yavaş Database Sorguları Nasıl Bulunur? Net Optimizasyon Rehberi
Yavaş sorguları bulmak için MySQL/PostgreSQL’de doğru log ve metrikleri toplayın, problemli SQL’i tespit edip ölçülebilir şekilde optimize edin.
Veritabanı tarafında yavaş sorgular çoğu zaman “sitenin kasılması” olarak kullanıcıya yansır; ancak sorun çoğu zaman CPU’dan değil, sorgu tasarımından ve yanlış indekslerden çıkar. Bu rehberde, veritabanında yavaş sorguları tutan değil, doğru şekilde tespit edip kanıtlayan bir yöntem izleyeceksiniz. Hedefimiz; log + metriklerle problemli SQL’i görünür yapmak, ardından ölçülebilir bir optimizasyon yol haritası çıkarmak.
Aşağıdaki adımlar, MySQL/MariaDB ve PostgreSQL için uygulanabilir. Her bölümde, hangi veriyle karar vereceğinizi netleştiriyoruz.
1) Yavaş sorgu nedir? Ölçüm eşiğini netleştirin
“Yavaş sorgu” ifadesi tek bir sayıya indirgenmez; uygulama trafiğine göre değişir. Bu yüzden ilk adım, gecikmeyi bir zaman eşiğine bağlamaktır.
Hangi metriği izleyeceksiniz?
- Query latency (sorgu gecikmesi): Tek bir SQL’in kaç ms sürdüğünü ölçer.
- Execution count (çalıştırılma sayısı): Çok kez çalışan ama tekil olarak hızlı sorgular da toplam gecikmeyi büyütür.
- Rows examined vs rows returned: Yanlış indeks genelde “çok satır tarayıp az satır getirme” davranışı gösterir.
- Lock time: Bazı “yavaş” sorgular aslında kaynak beklediği (transaction lock) için yavaştır.
Pratik eşik önerisi
Aşağıdaki eşiği kurumsal projelerde sık kullanırız: - Web isteklerine bağlı backend endpoint’lerinde, tek sorgu için 100-300 ms aralığını başlangıç eşiği kabul edin. - Yoğun sistemlerde “eşik”i p95/p99 üzerinden belirleyin. Örneğin p95 sorgu süresi 80 ms ise, p99 üstü sorguları odaklayın.
Not: Eşik belirlemeden “logda her şey var” durumuna düşersiniz. Optimizasyon için bir hedef seçmek şart.
2) MySQL/MariaDB’de yavaş sorguları bulma (Slow Query Log)
MySQL/MariaDB tarafında yavaş sorguları yakalamak için en temel araç slow query log’tur. Bu log, belirli bir süreyi aşan sorguları SQL ve metaveriyle kaydeder.
Slow Query Log’u açın (örnek senaryo)
Kontrol paneli üzerinden değil, mümkünse DB ayarlarından yönetmek en doğrusu olur. Yönetilebilir ortamda şu parametre mantığını arayın:
- slow_query_log = ON
- long_query_time = 0.5 (örnek: 500 ms)
- log_queries_not_using_indexes = ON (indeks kullanmayanları da yakalar)
Logdan hangi alanlara bakılır?
Slow query log şu soruların yanıtını verir: - Hangi tam SQL çalışıyor? - Ne kadar sürdü (Query_time)? - Kaç satır tarandı / geri döndü? - İndeks kullanıldı mı?
Hızlı analiz yöntemi
- Logu belirli bir zaman penceresiyle filtreleyin (ör. son 1 saat).
- Aynı SQL’i tekrar edenleri gruplandırın (normalize etme gerekebilir).
- Sırayla: - Çok sayıda çalışan sorguları, - En uzun süreleri alan sorguları, - İndeks kullanmayanları çıkarın.
EXPLAIN ile kanıt üretin
Problemli SQL’i bulduktan sonra EXPLAIN (ve gerekirse EXPLAIN ANALYZE) ile planı görün. Şu kırmızı bayraklar sık görülür:
- type = ALL (full table scan)
- rows değerinin çok yüksek olması
- possible_keys boş olması
- Extra içinde Using temporary / Using filesort
3) PostgreSQL’de yavaş sorguları bulma (pg_stat_statements + log)
PostgreSQL tarafında yalnızca log’a bakmak bazen yeterli olmaz; çünkü log, “tekil örnekleri” gösterir. Bunun yerine pg_stat_statements ile istatistik biriktirmeniz gerekir.
pg_stat_statements ile doğru sorgu sıralama
Amaç: Hangi SQL gerçekten yavaş ve sık çalışıyor?
Genellikle şu kolonlar karar verdirir:
- calls (çalışma sayısı)
- total_exec_time (toplam yürütme süresi)
- mean_exec_time (ortalama)
- rows (döndürülen satır)
Örnek çıktı mantığı:
- calls çok yüksek + mean_exec_time makul ama toplam büyük ise: ölçek problemi olabilir.
- mean_exec_time yüksek ise: plan/indeks sorunu olma ihtimali artar.
Log ayarları (pg_stat yerine tamamlayıcı)
pg_stat_statements istatistik toplar; log ise daha detaylı olayları yakalar. Bu ikisini birlikte kullanın.
EXPLAIN (ANALYZE, BUFFERS) ile indeks/plan kanıtı
PostgreSQL’de EXPLAIN (ANALYZE, BUFFERS) şunu sağlar:
- Gerçek çalışma zamanı (estimated vs actual)
- Disk okuma (buffers hit/miss)
- Join stratejisi ve maliyet
Kırmızı bayraklar:
- Seq Scan ile büyük tabloda tarama
- Çok yüksek Rows Removed by Filter
- Uygunsuz join sırası
4) Logları okurken yapılan 6 yaygın hata
Yavaş sorgu tespitinde ekiplerin en çok zaman kaybettiği alanlar burada.
1) Eşiği çok düşük ayarlamak
long_query_time = 0.01 gibi değerler logu şişirir. Sonuç: gerçek problemi ayıklamak imkansızlaşır.
2) Sadece en uzun sorgulara odaklanmak
Bazen en uzun sorgular nadirdir. En yüksek toplam maliyeti yaratan sorgular çoğu zaman “daha sık çalışan, orta hızlı” sorgulardır.
3) İndeks kullanmayanları tamamen gözden kaçırmak
İndeks kullanmayan sorgular çoğunlukla tek tek “yavaş” değil, trend olarak yavaşlatır (tablo büyüdükçe).
4) Lock beklemeyi sorgu süresiyle karıştırmak
Bazı sistemlerde sorgu süresi Lock beklemesi nedeniyle uzar. Query_time arttıysa ama EXPLAIN planı iyi görünüyorsa lock analizi gerekir.
5) Uygulama seviyesindeki timeout ile yanlış karar vermek
Backend timeout’u tetiklenmiş olabilir; sorgu 2-3 saniye sürdüğü için değil, sonuç üretimi daha uzun sürdüğü için timeout oluşur. Timeout’ta değil, DB’nin ölçümünde karar verin.
6) Birden fazla örnek arasında SQL’i normalize etmeden kıyas yapmak
Aynı sorgu, farklı parametrelerle farklı görünebilir. Query normalize edilmezse “tekil farklı SQL var” yanılsaması oluşur.
5) Sorunlu SQL’i bulduktan sonra: doğru aksiyon sırası
Artık yavaş sorguları buldunuz. Sıradaki adım rastgele indeks eklemek değil; ölçümle doğrulanan bir aksiyon planı çıkarmak.
Aşağıdaki tablo, sorgu türüne göre ilk hamleyi gösterir.
| Bulgular | Olası neden | İlk kontrol/aksiyon |
|---|---|---|
Seq Scan / type=ALL |
İndeks yok veya yanlış koşul | Filtre kolonlarına uygun indeks, sorguyu yeniden yazma |
Using filesort / Using temporary |
ORDER BY/GROUP BY maliyeti | Uygun composite indeks, sıralamayı azaltma |
rows examined çok yüksek |
Seçicilik düşük | WHERE koşulunu iyileştirme, indeks seçimi |
Çok sayıda calls |
N+1 sorgu / tekrar | Uygulama tarafında birleştirme (batch), caching |
| Lock time artıyor | Transaction kapsamı geniş | Transaction’ı kısaltma, izolasyon seviyesini gözden geçirme |
H3: İndeks eklemeden önce hedefi belirleyin
İndeks eklemek her zaman kazanç getirmez. Şu veriyi toplayın: - Sorgu hangi kolonlarda filtre/ORDER kullanıyor? - Tablo yaklaşık boyutu ve büyüme hızı ne? - Yazma (INSERT/UPDATE) trafiği yüksek mi?
Composite (çok kolonlu) indeks ihtiyacında kolon sırası kritiktir. Genellikle filtre kolonlarından başlarsınız; ardından sıralama/ek koşullar gelmelidir.
H3: Uygulama kaynaklı yavaşlığın izini sürün
Yavaş sorgular bazen “DB kötü” değil, uygulamanın veri çekme stratejisi yüzündendir.
Kontrol listesi: - Aynı sayfada N+1 sorgu var mı? - Aynı rapor sayfasında tekrar eden sorgu tekrar çalışıyor mu? - Sonuçlar cache edilmiyor mu?
Bu durumda DB tarafındaki küçük indeks değişiklikleri sınırlı etki yapar; uygulama tarafında sorguyu birleştirmek (JOIN/IN, batch yaklaşımı) daha hızlı sonuç verir.
6) Sunucu ve DB performansını birlikte düşünün
Yavaş sorguyu bulmak sadece “SQL” değil. Veritabanı performansı; CPU, disk, bellek ve bağlantı davranışından etkilenir.
İzleme hedefleri
- DB işlemcileri: yüksek CPU zamanında sorgular daha yavaş bitiyorsa plan + indeks + kaynak birlikte değerlendirilir.
- Disk I/O: yüksek ise indeks işe yaramıyor olabilir veya RAM yetersiz kalıyor olabilir.
- Bağlantı sayısı: bağlantı havuzu kullanılmıyorsa DB gereksiz yük alır.
VDS/VPS üzerinde pratik doğrulama yaklaşımı
- DB üzerinde yavaş sorgu logunu açın (eşik ayarlı).
- Aynı zaman diliminde sistem metriklerini alın (CPU, RAM, disk I/O).
- Problemli SQL için
EXPLAINçıktısını karşılaştırın. - İndeks/SQL değişikliğini uygulayın.
- Değişiklik sonrası aynı pencereyle tekrar ölçün.
Bu döngü, “tahminle optimizasyon”u bitirir.
Sonuç: Aksiyon almanızı sağlayan net akış
Yavaş database sorgularını bulmak için tek bir rapor yetmez; log + istatistik + plan kanıtı kombinasyonu gerekir. İlk adım olarak MySQL/MariaDB’de slow query log ile, PostgreSQL’de pg_stat_statements ile hedef sorguları listeleyin. Ardından EXPLAIN (ANALYZE, BUFFERS) veya EXPLAIN ile bulgu üretip, indeks veya sorgu/yük stratejisi değişimini ölçülebilir şekilde doğrulayın.
Aksiyon önerisi: Bugün mevcut sisteminizde 1 saatlik bir pencere seçin, eşiği makul tutarak yavaş sorguları çıkarın, ilk 10 sorguyu sıraya koyun ve her biri için EXPLAIN planını kaydedin. Bu kayıtlar olmadan yapılacak indeks denemeleri rastgele olur; kayıtlarla ise hangi değişikliğin gerçekten hız kazandırdığını net biçimde görürsünüz.
Hosting karşılaştırması yapmaya hazır mısın?
100+ firmanın fiyatlarını tek tıkla karşılaştır, en uygun paketi bul.
Hosting Karşılaştır →İlgili Yazılar
Snapshot yedekleme gerçek backup yerine geçer mi?
Snapshot (anlık görüntü) hızlı geri dönüş sağlar. Ancak gerçek backup değildir. Doğru strateji, süre/erişim ve test kriterlerini birlikte ele alır.
Paylaşımlı Hosting Yeterli mi? Ne Zaman Değiştirmeli?
Paylaşımlı hosting ne zaman yeterli olur, ne zaman VDS/VPS gerekir? Trafik, kaynak, hız, güvenlik ve maliyet eşiklerini net şekilde öğren.
Sunucu Loglarından Anormallik Tespiti: Net İzleme Rehberi
Sunucu loglarını izleyerek CPU, servis hatası ve güvenlik sinyallerini kaçırmadan anormallik tespit edin. Adım adım filtreler ve kontrol listesi.
WAF nedir? Web siteni korumak için net işlev ve kullanım rehberi
WAF (Web Application Firewall) ne yapar, hangi saldırıları engeller ve doğru kurulum/konfigürasyon için net kontrol listesi.