Replikasyon ve Okuma Replikaları — Yazdım Ama Göremiyorum
Önce şunu oku: MVCC ve Kilitler — Eski Satır Sürümleri Nerede Yaşar?
30 saniyede özet
Veritabanının kopyaları (replikalar) okuma yükünü paylaşır, ama asıl veritabanının biraz gerisinden gelir. Kullanıcı kendi yaptığı değişikliği göremeyebilir; asıl makine çökerse son yazılanlar kaybolabilir.
Kullanıcı profil adını değiştirdi, “kaydedildi” mesajını gördü ve sayfayı yeniledi: eski ad duruyordu. Tekrar kaydetti, yine eski ad. Destek kaydı açtığında ad çoktan düzelmişti.
Adım adım oku
- Kullanıcının yeni adı yazma sunucusuna, yani primary'ye, merkeze gider.
- Replika değişikliği primary'nin günlüğünden biraz sonra alır; kurye yoldadır.
- Bu arada replikadan okuyan kullanıcı eski adı görür, üstelik kaydetme başarılı dönmüştür.
- Kullanıcı kendi yazdığını bir süre primary'den okursa her zaman güncel hâli görür.
-
Bayt: Profil adımı değiştirdim, kaydedildi dedi. Sayfayı yeniledim: eski ad!
-
Sen: Tekrar kaydetsen?
-
Bayt: Kaydettim, yine eski ad. Destek kaydı açtığımda ise ad çoktan düzelmişti.
-
Bayt: Merkez ile şubeler aynı anda mı güncellenir?
Biri yazar, diğerleri kopyalar
Yazmalar tek bir sunucuya, primary’ye gider. Replikalar primary’nin değişiklik günlüğünü alıp aynı değişiklikleri kendilerine uygular. Okumaları replikalara dağıtmak, primary’nin yükünü azaltır.
PostgreSQL’de streaming replication, SQL Server’da Always On availability groups, Oracle’da Data Guard bu işi yapar. Üçünde de varsayılan ya da en yaygın kurulum asenkrondur.
Kafam karıştı, daha basit anlat
Tek bir kişi deftere yazar, diğerleri onun yazdıklarını kendi defterlerine kopyalar. Okumak isteyenler kopyalara gider, böylece yazan kişi rahat çalışır.
Okuma replikası eklemenin temel amacı nedir ve neyi çözmez?
Geriden gelmenin iki bedeli
Asenkron replikasyon. Kullanıcı 'kaydedildi' cevabını aldı ve primary hemen ardından çöktü. Replika yeni primary oldu. Kullanıcının değişikliği nerede? Cevabı göster
Kaybolmuş olabilir. Asenkron commit replikayı beklemez. Değişiklik replikaya gönderilmeden primary çöktüyse, yeni primary onu hiç görmemiştir.
Replikanın primary’nin gerisinde kaldığı süreye replication lagBir replikanın primary'deki değişiklikleri ne kadar geriden uyguladığı. Bu süre boyunca replikadan yapılan okumalar eski veriyi gösterir.Sözlükte gör → denir. Bu süre boyunca replika eski veriyi gösterir; lag büyürken primary çökerse aradaki yazmalar failoverPrimary çöktüğünde bir replikanın yeni primary olarak devralması. Asenkron replikasyonda replikaya ulaşmamış yazmalar bu sırada kaybolabilir.Sözlükte gör →’da kaybolur.
Senkron replikasyonun da iki derecesi var. “Replika diske yazsın” kaybı önler ama okumayı tazelemez. “Replika uygulasın” (PostgreSQL’de remote_apply) ikisini de sağlar, ama her commit en çok burada bekler.
Kafam karıştı, daha basit anlat
Kopyalar biraz geriden gelir. O arada kopyaya bakan kişi eski bilgiyi görür. Asıl defter tam o sırada kaybolursa, kopyalanmamış satırlar da kaybolur.
Asenkron replikasyonda primary çöktü ve replika devraldı. Kullanıcılara 'kaydedildi' denmiş son birkaç sipariş yok. Neden?
PostgreSQL'de `synchronous_commit = on` ve senkron bir replika var. Yine de replikadan okuyan kullanıcı az önce commit edilen değişikliği göremiyor. Neden?
Kendin gör
Yazdım ama göremiyorum
Tohum 488310Oynat ya da adımla.
Şu an ne oldu?
Kullanıcı adını değiştirip sayfayı yeniliyor
Yazma primary'ye gidiyor. Okuma nereden yapılacak ve replika o ana kadar yetişmiş olacak mı?
Görevler0/3
Kullanıcının az önce kaydettiğini görmemesini sağlaaçık
İpucu
Okumayı gecikmeli replikaya gönder.
Kullanıcıya "kaydedildi" denmiş bir değişikliği failover'da kaybetaçık
İpucu
Commit replikayı beklemesin; replika geride olsun.
Replika gecikmeliyken bile replikadan taze oku ve çökmede kayıp yaşamaaçık
İpucu
Replikanın değişikliği görünür yapmasını bekle.
Olay günlüğü (0)
Henüz olay yok. Oynat veya adımla.
- Varsayılanla oynat. Okuma replikadan: kullanıcı eski adı görüyor.
- “Primary çöksün”ü aç. Onaylanmış yazma kayboldu.
- Replikasyonu “diske yazsın” yap. Kayıp yok, ama okuma hâlâ eski.
- “Uygulasın” yap. Taze ve güvenli; commit bekledi.
- Asenkrona dön, okumayı “yazan primary’den okusun” yap. Okuma taze, ama çökme kaybı duruyor.
Simülatörde asenkron replikasyon ve 'yazan kullanıcı primary'den okusun' seçiliyken okuma taze çıktı, ama çökme açılınca yazma yine kayboldu. Buradan çıkan ders ne?
Kendi yazdığını okumak
Her okuma taze olmak zorunda değil; ama kullanıcının kendi değişikliğini görmesi gereken okumalar vardır. Buna read-your-writesBir kullanıcının kendi yaptığı değişikliği sonraki okumalarında mutlaka görmesi garantisi. Replikalardan okurken kendiliğinden sağlanmaz.Sözlükte gör → garantisi denir.
- Yazan kullanıcıyı bir süre primary’ye yönlendir: en basit yol; oturumda “son yazma zamanı” tut.
- Yazma konumunu bekle: primary’nin döndürdüğü log konumunu sakla, replika o konumu uygulamadan ondan okuma.
- Kritik okumaları hep primary’den yap: bakiye, stok, ödeme durumu.
Bir mobil bankacılık uygulamasında bu üç yol yan yana nasıl duruyor, birlikte bakalım. Müşteri FAST ile para gönderiyor ve hemen hesap sayfasına dönüyor.
Derinleş · Hesap sayfası: hangi okuma hangi kopyadan? 4 dosya · ~70 satır · ilk okumada atlayabilirsin
Kafam karıştı, daha basit anlat
Kullanıcı az önce yazdığını hemen görmek ister. En kolay yol, yazdıktan sonra kısa bir süre onun okumalarını asıl deftere yönlendirmektir.
Kullanıcılar profillerini güncelledikten sonra eski bilgiyi görüyor. Okumalar replikalardan yapılıyor. En az bedelli çözüm hangisi?
Her okumayı replikadan yapılabilir ya da primary'den yapılmalı olarak ayır.
Tuzaklar
Replikalar arasında zıplamak. Farklı gecikmeli iki replikadan sırayla okuyan kullanıcı, zamanda geriye gidebilir: yorum görünür, sonra kaybolur.
Senkron replika düşerse. PostgreSQL’de senkron replika yoksa commit’ler bekler; yazmalar durur. Birden çok aday replika ya da bilinçli bir geri düşme planı gerekir.
readOnly ile yönlendirme. Spring’de @Transactional(readOnly = true) okumaları replikaya gönderiyorsa, yazmadan hemen sonra aynı istekte yapılan okuma da oraya gidebilir.
Gecikmeyi izlememek. PostgreSQL’de pg_stat_replication, SQL Server’da redo kuyruğu, Oracle’da apply lag izlenmeli.
Okumalar `readOnly` transaction'lar üzerinden replikaya yönlendiriliyor. Kullanıcı yorum ekleyince yorum listede görünmüyor. Hatalı satır hangisi?
Kendini sına
Yazmalar primary'ye gider, replikalar değişiklikleri sonradan uygular.
Bir yük dengeleyici okumaları iki replikaya rastgele dağıtıyor; biri az, diğeri çok geride. Kullanıcı yeni bir yorumu görüyor, sayfayı yenileyince yorum kayboluyor. Hangi garanti eksik?
Aklında kalacak üç şey
- 1 Asenkron replikasyonda kayıt, kopyayı beklemeden tamamlanır. Kopyadan okumak eski veri gösterebilir; asıl makine çökerse kopyaya ulaşmamış yazmalar kaybolur.
- 2 Senkron replikasyonun da dereceleri var: 'kopya diske yazsın' kaybı önler ama okumayı tazelemez; 'kopya uygulasın' ikisini de sağlar, bedeli en çok beklemektir.
- 3 Kullanıcının kendi yazdığını görmesi gereken okumaları asıl veritabanına ya da o yazmayı almış bir kopyaya yönlendir.
5 kart sonraki derste seni bekliyor
Bu dersin üstüne kurulanlar
Bunlar bu dersi temel alıyor; hazır olduğunda devam edebilirsin.
- VeritabanlarıSharding ve Shard Anahtarı — Veriyi Bölmenin Tek Önemli KararıÖdemeleri aya göre dört veritabanına böldün. Bugünün bütün ödemeleri hangisine gidiyor?Derse git
- VeritabanlarıYedek ve Geri Dönüş — WHERE'siz Bir DELETE Kaç Saatlik Veriyi Götürür?Öğlen biri WHERE yazmadan bir DELETE çalıştırdı. Yedek sunucu da var, gece yedeği de. Hangisi kaç saatlik havaleyi kurtarır?Derse git
- System Design & Dağıtık SistemlerÇok Bölgeli Kurulum — Bir Bölge Kararınca Banka Çalışmaya Devam Eder mi?İstanbul bölgesi karardı. Frankfurt'taki kopya hemen devraldı. Ama son üç havale ortada yok. Nereye gittiler?Derse git