“Arşivlenmiş ancak kullanılabilir” veriler için SQL Server veritabanı tasarımı


12

"Küçültmek" istediğimiz bu büyük veri tabanımız (> 1 TB) var. Veritabanı bir ana varlık etrafında döner, buna "Ziyaret" diyelim. Tartışma için, bunun tıbbi bir uygulama için bir veritabanı olduğunu varsayalım.

Her biri "Ziyaret" için bir alt tablo olan, örneğin "ziyaret_immuno" olmak üzere, prosedür, yıllık, takip, bağışıklama vb. Gibi toplam 30 ziyaret "tipi" vardır.

Veritabanı 2000 yılından bu yana yaklaşık 12 yıllık veri biriktirmiştir. Birisi "canlı" versiyonda yaklaşık 3 yıllık veri tutmamızı ve gerisini "old_data" veritabanında yayınlamayı önermiştir. Tarih SADECE normalleştirildiği için "Ziyaret" tablosunda saklanır. Ziyaret tablosu ayrıca bir ROWVERSIONsütun ve BIGINTsahte kimlik (kümelenmiş) sütun içerir. Tüm niyetler ve amaçlar için, kümeleme anahtarının bir SEQUENCE (SQL Server 2012 Enterprise) tarafından doldurulduğunu varsayalım - buna ad vereceğiz cid.

Her visit.datezaman kümeleme anahtarıyla aynı sırada değildir, örneğin bir doktor genişletilmiş ziyaretlere gittiğinde ve onun "evrak çantası" ile döndüğünde, ana tabloya birleştirilir. "Ziyaret" tablosunda, ROWVERSIONsütunun hem cidve hem de datesütunlarla senkronize olmamasına neden olacak bazı güncellemeler de vardır - basitçe söylemek gerekirse, bu nedenle ROWVERSIONne ciduygun bölme anahtarları ne de yapar.

"Canlı" veri kaldırmanın iş kuralı, visit.date36 aydan uzun olması ve bir alt visit_paymentkayıt bulunması gerektiğidir. Ayrıca, "old_data" veritabanı dışında temel tabloları içermez visit%.

Sonuç olarak:

Canlı DB (günlük kullanım) - Tüm tablolar Eski Veri DB - visit%tablolar için eski veriler

Teklif , iki veritabanındaki tablolar arasında BİRLİKTE TÜM temel tablolarda (hariç ) artı Görünümler içinde TÜM taban tablolara Anlamlılar içeren bir kabuk olan bir Kombine DB'yi çağırır .Live DBvisit%visit%

DB'de aynı dizinlerin oluşturulduğu varsayıldığında, Old-Datasorgular UNION-ALL Görünümlerinde iyi performans gösterecek mi? UNION-ALL Views için yürütme planını ne tür sorgu modelleri tetikleyebilir ?


3
A) eski verilerin arşivlenmesi ve b) verilerin erişilebilir olması için motivasyon nedir? Bakım yükü mü? Performans sorunları mı var? Arşivlenen verilerin uygulama tarafından sorunsuz bir şekilde erişilebilir olması gerekiyor mu? Uygulamada değişiklik yapılarak veya değişiklik yapılmadan?
Mark Storey-Smith

(a) Ana db'yi küçük tutmak. Diğer 3 kısma kopyalanır - dev, ön test, test. Ayrıca, hepsi pahalı depolama alanlarıyla desteklenen çoğaltılmış aynalar ve yedeklemeler de var. (b) Aşağı akım sistemleri şu anda tüm verilere erişebildiğinden, bu durumun durumunu korur. (c) Uygulamanın bir örneği tüm görünümlerle "birleşik" DB'ye karşı çalışabilir, ancak hiç performans göstermeyebileceğinden şüpheleniyorum.
孔夫子

Sadece açıklığa kavuşturmak için, arşivlenen veriler hala okuma-yazma, doğru mu? Yoksa salt okunur mu?
Jon Seigel

Eski veriler salt okunur ve% 100 doldurulmuş sayfalara dönüşür. Birleştirilmiş görünümlere bağlanan uygulamanın örneği, birisi eski verilere saçma bir şey denerse hatalar verebilir - umursamıyoruz.
孔夫子

Ben düşünüyorum salt okunur dosya grubu tarihsel veriler ve kısmi yedekleme için / bu kapsayacak geri, kabuk veritabanı ve eş anlamlı pislik eklendi olmadan. Diyorum düşünüyorum ben hafızamı tazelemek için biraz zaman ve ihtiyaca bunun mekaniği ile burnunuzu soktunuz değil gibi. Çoğaltma ile nasıl uyacağına dair bir fikrim yok ama neden aşağı akış ortamlarına canlı bir veritabanını çoğalttığınızı soruyorum.
Mark Storey-Smith

Yanıtlar:


4

Kolaylık sağlamak için, canlı veritabanının çağrıldığını LiveDbve başarılı veritabanının çağrıldığını varsayınArchiveDb

  • Bir eşanlamlı aracılığıyla veritabanındaki LiveDbtablolara işaret eden bir BİRLİK TÜM görünümü ekleyin ArchiveDb(Eşanlamlı kombine bir db yapmanıza gerek yoktur)
  • "Bölüm" özelliğini açın visit.dateve visit_paymentszaten yoksa bu sütunu da denormalize edin (bu, birlikte konumlandırılmış birleştirme performansını artırır)
  • Mümkünse iki büyük tabloyu arşivleyin (optimize ediciyi açma olasılığını azaltır). BİRLİKTE TÜM görünümünü ve diğer tabloları LiveDbdaha küçük tablolara yapılan tüm birleşimlerin yerel tutulması
  • Hem masalarda bir CHECK kısıtlaması ekleyin LiveDbve ArchiveDb bu aralığını tanımlayan visit.datetabloda içeriyordu. Bu, iyileştiricinin arşiv tablosunu, sütunu içeren arama ve taramalardan kaldırmasına yardımcı olur visit.data. Bu kısıtlamayı periyodik olarak güncellemeniz gerekecektir.
  • BİRLİĞİ TÜM görünümünde, filtrelenen bir WHERE ölçütü ekleyin visit.data. Bu, kontrol kısıtlamasında önceden belirttiğiniz ipucuna ek olarak yapılır. Bu, filtrelerin aşağı itilme olasılığını en üst düzeye çıkarır
  • EE'niz varsa, tabloyu arşiv veritabanında bölümleyin (Ancak canlı veritabanında DEĞİL). Gerçekten süslü olmak istiyorsanız, yedekleme zamanlarından tasarruf etmek için arşiv veritabanlarının dosya grubu düzeyinde yedeklemesini / geri yüklemesini kullanın.
  • AchiveDbHenüz yapmadıysa BASİT kurtarma moduna geçmeyi düşünün . İşlem günlüğü yedeklemelerine ihtiyacınız yoktur.ArchiveDb
  • Kullanım INSERT ... İLE (tablock) SEÇ ... İLE (rowlock) arasında veri taşırken hedef üzerinde minimum günlüğü zorlamak LiveDbveArchiveDb

Yukarıdakilerin tümü, iyileştiricinin arşiv tablolarını arama ve taramalardan kaldıracağını garanti etmez, ancak daha olası hale getirir.

Eliminasyon gerçekleşmediğinde. Bunlar görebileceğiniz etkidir (bu liste eksik olabilir). Aramalar için, her sorguda ek bir arama alırsınız (bu, IOPS'u çalıştırır). Taramalar için sonuçlar performans için felaket olabilir, çünkü hem arşiv hem de canlı tabloları tarayabilirsiniz. Optimize ediciyi açmanın tipik yolları şunlardır:

  • Eğer katılırsanız visit%birlikte tablo ve yapmak içermez visit.dataiçinde kriterlerini (eğer denormalise istediğiniz bu yüzden) katıldı. Bu nedenle, bazı sorgularınızı değiştirmek isteyebilirsiniz
  • Bir karma visit.datatablo ile başka bir tablo (örneğin bir tarih boyutu) alırsanız, tabloların doğru şekilde kaldırılmasını sağlayamayabilirsiniz.
  • Arşivlenen tablolar üzerinden veri toplamaya çalışırsanız
  • Herhangi bir şeye filtre uygularsanız AMA, visit.dataörneğin doğrudan görünümün anahtarını arayın.

Son senaryo için, cid- mümkünse başka bir kontrol kısıtlaması ekleyerek kendinizi en kötü etkilere karşı koruyabilirsiniz . cidTablodaki satırların tarihleri ​​ve ilerlemesi ile ilgili olarak "temiz" olmayan bir diziden bahsettiniz . Ancak, şu bilgileri içeren bir tablo tutabilir misiniz: "Bundan cidbu yana bu sayının üstünde yok visit.data" veya benzeri? Bu daha sonra ek bir kısıtlama getirebilir.

Dikkat edilmesi gereken başka bir şey, bölümlenmiş görünümü sorguladıktan sonra paralel sorguların çok daha fazla iş parçacığı oluşturabileceğidir (her iki "alt tablo" da aynı paralel optimizasyonlara maruz kalacağı için). Bu nedenle, sunucudaki MAXDOP'u veya paralel olan sorguları sınırlamak isteyebilirsiniz.

Bu arada, sorguları iyi biliyorsanız - iki veritabanında aynı dizinlere bile ihtiyacınız olmayabilir (bu, tabloların doğru şekilde kaldırılacağından% 100 emin olduğunuzu varsayar). Hatta sütun mağazalarını kullanmayı düşünebilirsiniz ArchiveDb.


-1

Yaptığımız yol, eski verileri toplu olarak yeni oluşturulan bir veritabanına yazmak ve eski verileri canlı db'den silmektir. Bu şekilde her iki db'ye de erişilebilir. Ayrıca, yeni oluşturulan veritabanını yedekleyebilir ve başka yerlere geri yükleyerek üretim alanlarındaki büyük ayak izini kaldırabilirsiniz. Umarım bu ihtiyaçlarınız için kabul edilebilir bir çözümdür.


Uygulama uyumluluğunu korumak için OP'nin bundan daha ileri gitmesi gerekir. Soruyu okudun mu?
Jon Seigel
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.