Çok Kiracılı Veri Tabanı Mimarisinde artan sayıda Kiracıyı işleme


26

Her kiracı başvurusu için ayrı veritabanları olan ortak bir sunucuda mütevazı sayıda müşterinin (kiracı) kullanımı nispeten kolaydır ve normal olarak bunu yapmanın doğru yoludur. Şu anda her kiracının kendi veritabanı örneğinin bulunduğu bir uygulama için mimariyi arıyorum.

Ancak, sorun bu uygulamanın çok sayıda kiracıya (5.000-10.000) sahip çok sayıda kiracıya (5.000-10.000) sahip olması, belki de tek bir kiracı için 2.000'in olması. Sistemin her hafta birkaç kiracı tarafından geliştirilmesini desteklememiz gerekecek.

Ayrıca, tüm kiracılara ve kullanıcılarına ortak bir giriş işlemi sunulacaktır (yani, her kiracının kendi URL’si olamaz). Bunu yapmak için, merkezi bir oturum açma işlemine ve sisteme dinamik olarak veritabanları eklemek ve kullanıcıları kaydetmek için bir araca ihtiyacım var.

  • Kayıt ve veritabanı oluşturma süreci sağlam bir şekilde nasıl otomatikleştirilebilir?

  • Sistemdeki kiracı veritabanlarını oluşturma ve kaydetme işlemi performansa veya kilitleme sorunlarına neden olabilir mi? Bunun bir sorun olacağını düşünüyorsanız, herhangi biri bunu azaltmanın yollarını önerebilir mi?

  • Merkezi kimlik doğrulamasını, kullanıcı kimlik bilgilerinin belirli bir kiracının veritabanıyla ilişkilendirileceği şekilde nasıl yönetebilirim, ancak kullanıcı ortak bir sayfadan (örneğin aynı giriş URL'sinin tümü üzerinden giriş yapabilir), ancak onların ev uygulaması belirli bir kiracının veritabanında olacak ). Kiracıların kendi girişlerini ve izinlerini sürdürebilmeleri gerekecek, ancak merkezi bir giriş sistemi bunun farkında olmalıdır. Birisi bunu yapmanın bir yolunu önerebilir mi?

  • Birden fazla veritabanı sunucusu ekleyerek 'ölçeklendirmek' gerekirse, herhangi biri, sunucudaki kullanıcı kimliklerini yönetmede hangi sorunları çözmem gerektiğini (kimliğe bürünme vb.) Ve bu sorunları azaltmanın bir yolunu önerebilir mi?


1
Böyle bir durumla uğraşmak zorunda değildim, ancak benim sezgim kiracıların kullanıma sunacağını düşündüğünüz kiracı veritabanlarını önceden yapılandırarak kiracı sunumunu ele almak ve daha önce sadece kiracı veritabanlarını yeni kiracılar olarak atamak olacaktır. kaydol. Bu şekilde, en azından kiracı DB'lerini dağıtırken kaynak çekişmesi konusunda endişelenmenize gerek kalmaz.
Joel Brown

1
5.000-10.000 kiracıya yakın bir yere gideceğinizden emin misiniz? Ve tüm kiracılarınızın 2.000 kullanıcı aralığında olacağı? Sistemimde, tek bir kiracı için başvurumuzun en fazla kullanıcısı olan sayısının yaklaşık 100 olduğunu düşünüyorum. Sektörün / uygulamanın ne olduğunu sorabilir miyim?
Aaron Bertrand

@AaronBertrand Servislerin kısmen ücretsiz ve kısmen ödeneceği bir Öğrenme Yönetim Sistemidir.
coddey

Yanıtlar:


25

Alt uçta (500 kiracı / 10000 kullanıcı) bu şekilde yaptım. Öncelikle, merkezi, merkezi olan ve kiracılar ve kullanıcılar hakkındaki tüm bilgileri içeren bir "kontrol" veritabanına sahipsiniz (Bunları SQL auth login olarak yönetmek istediğinizi sanmıyorum). Bu nedenle, aşağıdaki tablolarla "Kontrol" adlı bir veritabanını hayal edin:

CREATE TABLE dbo.Instances
(
  InstanceID INT PRIMARY KEY,
  Connection VARCHAR(255)
  --, ...
);

INSERT dbo.Instances SELECT 1, 'PROD1\Instance1';
INSERT dbo.Instances SELECT 1, 'PROD2\Instance1';
-- ...

CREATE TABLE dbo.Tenants
(
  TenantID INT PRIMARY KEY,
  Name NVARCHAR(255) NOT NULL UNIQUE,
  InstanceID INT -- Foreign key tells which instance this tenant's DB is on
  --, ...
);

INSERT dbo.Tenants SELECT 1, 'MyTenant', 1;
-- ...

CREATE TABLE dbo.Users
(
  UserID INT PRIMARY KEY,
  Username VARCHAR(320) NOT NULL UNIQUE,
  PasswordHash VARBINARY(64), -- because you never store plain text, right?
  TenantID INT -- foreign key
  --, ...
);

INSERT dbo.Users SELECT 1, 'foo@bar.com', 0x43..., 1;

Bizim durumumuzda yeni bir kiracı eklediğimizde veritabanını dinamik olarak oluşturacağız, ancak yönetici kullanıcı UI'de Tamam'ı tıklattığında değil ... her 5 dakikada bir sıradan yeni veritabanlarını çekip arka plan modelini single_user olarak ayarlayan bir arka plan işimiz vardı. ve ardından seri olarak her yeni veritabanını oluşturdu. Bunu (a) yönetici kullanıcısının veri tabanı oluşturulmasını beklemesini engellemek ve (b) iki yönetici kullanıcısının aynı anda bir veritabanı oluşturmaya çalışmasını önlemek veya başka bir şekilde modeli kilitleme yeteneğini reddetmek (yeni bir veritabanı oluştururken gereklidir) yaptık. ).

Veri tabanları, temsil Tenant000000xxedildiği yerdeki isim şeması ile oluşturulmuştur . Bu yerine adlandırılmış her türlü veri tabanlarını sahip, oldukça kolay bakım işlerini yapılan , , o bir örnek olarak sadece kullanılarak, hızlı yiyecek vardı değil o vb.xxTenants.TenantIDBurgerKingMcDonaldsKFC

Yorumun önerdiği şekilde binlerce veritabanını önceden tahsis etmememizin nedeni, yönetici kullanıcılarımızın genellikle kiracının ne kadar büyük olacağı, yüksek önceliğe sahip olup olmadıkları vb. Hakkında bazı fikirlere sahip olmalarıydı. başlangıç ​​boyutlarını ve otomatik büyüme ayarlarını, veri / günlük dosyalarının hangi disk alt sistemine gideceğini, kurtarma ayarlarını, menteşeleri kaldırmak için yedekleme zamanlamasını ve hatta en iyi dengeyi kullanmak için hangi veritabanının konuşlandırılacağını akıllıca belirleyecektir ( ancak yöneticilerimiz bunu geçersiz kılabilirdi). Veritabanı oluşturulduktan sonra, kiracı tablosu seçilen örnekle güncellendi, kiracı için bir yönetici kullanıcı oluşturuldu ve yöneticilerimiz yeni kiracıya geçmeleri için e-posta adreslerine e-postayla gönderildi.

Tek bir giriş noktası kullanıyorsanız, birden fazla kiracının aynı kullanıcı adına sahip kullanıcılara izin vermesi mümkün değildir. E-posta adresini kullanmayı seçtik - eğer tüm kullanıcılar şirket için çalışıyorsa ve şirket e-posta adresini kullanıyorsa - iyi olmalı. Çözümümüz sonunda iki nedenden dolayı daha karmaşık hale geldi:

  1. Müşterilerimizden daha fazlası için çalışan danışmanlarımız vardı ve birden fazla kişiye erişmeleri gerekiyordu.
  2. Kendileri aslında birden çok kiracıdan oluşan kiracılar vardı

Böylece, TenantUsersbir kullanıcının birden fazla kiracı ile ilişkilendirilmesine izin veren bir tablo belirledik.

Başlangıçta bir kullanıcı oturum açtığında, uygulama yalnızca kontrol veritabanı için bağlantı dizesini bilecektir. Bir giriş başarılı olduğunda, bulduğu bilgilere göre bir bağlantı dizesi oluşturabilir. Örneğin

SELECT i.Connection
  FROM dbo.Instances AS i
  INNER JOIN dbo.Tenants AS t
  ON i.InstanceID = t.InstanceID
  INNER JOIN dbo.TenantUsers AS u
  ON i.TenantID = u.TenantID
  WHERE u.UserID = @UserID;

Artık uygulama kullanıcının veritabanına bağlanabilir (her kullanıcının varsayılan bir kiracısı vardı ) veya kullanıcı erişebilecekleri kiracılardan herhangi birini seçebilir. Uygulamanın ardından basitçe yeni bağlantı dizesini alır ve söz konusu kiracının giriş sayfasına yönlendirilir.

Teklif ettiğiniz bu 10MM kullanıcı alanına girerseniz, daha iyi dengelenmesi için kesinlikle buna ihtiyacınız olacaktır. Uygulamayı, farklı kontrol veritabanlarına bağlanan farklı giriş noktalarına sahip olacak şekilde düzenlemek isteyebilirsiniz. Her kiracıya bir alt etki alanı (örneğin, TenantName.YourApplicationDomain.com) verirseniz, daha fazla ölçeklendirmeniz gerektiğinde bunları kesintiye uğratmadan DNS / yönlendirmeli sahnelerin arkasında bunu yapabilirsiniz.

Bundan daha fazlası var - like @Darin Sadece buradaki yüzeyi çiziyorum. Özgür olmayan bir danışmaya ihtiyacınız olursa bana bildirin. :-)


Deneyiminizi paylaştığınız için teşekkür ederiz. Gerçekten de, aydınlanmış beni. Ama sen zaten Non-Free yazdın. :(
coddey

1
Demek istediğim, ücretsiz tavsiyelere ayrılacak çok fazla zamanım olmasıydı. :-)
Aaron Bertrand

+1 - hemen hemen daha önce kullandığımla aynı yaklaşım. ~ aynı sayıda kiracı da gerçekten işe yaradı.
AdaTheDev

Ana veritabanı ve kiracı veritabanı arasındaki ilişki nasıl ele alınır? (Tetikleyicileri vb. kullanmadan)
Jitendra Pancholi

@jitendra gerçekten çok fazla seçenek yok - kiracı veritabanında, asıl veritabanındaki verilerle ilgili olması gereken veriler ne kadardır? Ayrıca popüler tetikleyicilerden korktuğumu anladığımdan da emin değilim - uygun bir şekilde yazılan tetikleyici korkacak bir şey değil ...
Aaron Bertrand

10

Kendine çok ilginç bir projen var. Hiç kimsenin en azından SQL Server'da bu kadar büyük bir şeyi uygulamaya çalıştığını hiç görmedim. Mesajınızı ne kadar çok okursam, o kadar çok soru soruyorum ...

En kötü senaryo altyapısı (aslında en iyi senaryo, işletme bazında), 10 K veritabanına 2k kullanıcı gerekir. Bu 20.000.000 kullanıcı. 20 M SQL Server girişlerini yönetme konusunda başarılı olamayacaksınız. IMO. Sadece bunlardan sadece birkaçı, onları sunucudan sunucuya taşıma, kimlik çarpışmalarını ve yanlış tanımlanmış ID'leri izleme ile ilgileniyor. Ayrıca SQL Server'ın sys.server_principals içinde 20 M satır ile nasıl davranacağından emin değilim. Ek olarak, web uygulamanız muhtemelen tek veya çok düşük sayıda kullanıcı olarak bağlanmak isteyecektir. IIS, DSN dizeleri aynı olmadıkça bağlantıları birleştiremez. Bir DSN dizesinin niteliklerinden biri kullanıcı adıdır. Farklı kullanıcılar havuz yok demektir.

Kendi kullanıcı kimlik bilgilerinizi almanız gerekecek. Bir kullanıcının hangi kiracıya ait olduğunu bulmak ve web kodunuzun uygun veritabanını seçmesi gerekir. Bu kullanıcı meta verileri kritiktir, bir yerde depolanması, kümelenmesi veya yansıtılması gerekir, hızlı olması gerekir ve iyi korunması gerekir (güvenlik açısından bakıldığında). şifreleyin.). SQL'in burada iyi bir fikir olduğunu varsayarsak, bu veritabanını sunucunun kiracılarından uzak tutardım. Bu, bir güvenlik açısından ve bir yükleme açısından yardımcı olur, ancak kullanıcılar bir kez doğrulanırsa ve web uygulaması başka bir durumda doğru veritabanına yönlendirildiğinde, bu kullanıcı meta verilerinin bu konuda daha fazla sorgulanmayacağını tahmin ediyorum. kullanıcı.

Hızlı soru: iki farklı kiracıya ait iki farklı kullanıcının aynı kullanıcı adına sahip olmasına izin verilmeli midir?

Başka bir hızlı soru: Size FuBar, Inc. için çalıştığımı söylersem, bunu nereden biliyorsunuz? FuBar size bir kullanıcı listesi verecek mi ve onları kullanıcı adlarının bir listesini geri mi vereceksiniz, yoksa kendi kendine sağlanacak mı?

Çok örneğe gitmeniz gerekecek. Bu kullanıcıların bir kısmı bile uygulamaya bir kerede vurmaya karar verirse, tek bir örnek eritilecektir. Tüm bu istekleri bir kerede çalıştırmak için yeterli işçi iş parçacığı olmayacak. Aynı anda yalnızca 1000 kullanıcı sizin örneğinize isabet ederse, muhtemelen çalışan iş parçacığı tükenir ve istek istiflenip beklemeye başlar. Bunun olduğunu gördüm; Buradaki belirti, yeni bağlantıların örneğe giriş yapamayacağıdır, çünkü onlara hizmet verecek uygun iş parçacığı yoktur. Bu çok kısa ömürlü bir davranış ise, uygulama hayatta kalabilir. Değilse veya uygulamanız titizse, kullanıcılar hata alır.

Başlayacak çok fazla kiracınız olmasa bile, geleceği ve otomasyonu düşünmeye başlamalısınız, çünkü sunucunuzun tıkandığını ve çevrimiçi duruma getirmek için 10 yeni kiracı olduğunu görünce, oldukça geç ve hizmetinizdeyken (ve Müşterileriniz ve yakında çıkacak olan müşterileriniz), sorununuzu çözene kadar acı çekeceklerdir.

Veritabanlarını aşırı yüklenmiş sunuculardan hafif yüklü (veya yeni) sunuculara taşımak için bir yola ihtiyacınız olacak. Bir kesinti süresine sahip bir pencere alıp alamayacağınız SLA'nıza bağlı olacaktır.

SalesForce gibi belirli bir uygulama sağlıyor musunuz, yoksa bu veritabanları kiracılarınıza koymak istediğiniz her şey için yalnızca kapsayıcılar mı?

Veritabanları ne kadar büyük? Çok büyük değillerse, yalnızca şablon sağlayan bir yedekleme dosyasından geri yükleyebilirsiniz. (Bu model veritabanının yaptığından çok farklı değil, ancak SQL 6.5 ile günlerimden beri hiç kimsenin modeli gerçekten iyi kullandığını görmedim.) Şablon bir kez daha yeni veritabanı adına geri yüklendiğinde, daha sonra yeni veritabanını belirli bir kiracı için gerektiği şekilde özelleştirin. Belli kiracı olmadan önce kişiselleştirmeyi yapamazsınız. Eğer veritabanı büyükse, herhangi bir yeni kiracı alana ihtiyaç duymadan önce geri yüklemeyi önceden yapmanız dışında aynı temel prosedürü uygulayabilirsiniz. Bu veritabanlarından birkaçını, belki de bir tanesini bir arada tutabilirsiniz. Etrafta çok fazla tutarsanız, bu sizi belki de ihtiyaç duyduğunuzdan daha fazla donanım ve / veya depolama alanı almaya zorlar.

Eğer bu sizin uygulamanızsa, şemalardaki güncellemeleri nasıl yapacaksınız? Web uygulamanıza tek bir URL kullanıyorsanız, veritabanının sürümlerini kod sürümleriyle nasıl düz tutabilirsiniz?

Artık kullanılmayan veritabanlarını nasıl tespit ediyor ve yok ediyorsunuz? Klima grubunuz birisinin faturasını üç aydır ödemediğini söyleyene kadar bekler misiniz?

Kiracılar izinleri yönetiyorsa, bu, uygulamanın iç işleyişini biraz anladıklarını veya uygulamanızın çok basit bir rol yapısına sahip olduğunu gösterir. Blogger gibi bir şeyi kaba bir örnek olarak kullanarak, kullanıcılar (yayınları okuyabilir), (yayınları okuyabilir ve yorum yazabilir), (... ve yayınları oluşturabilir), (... ve diğer yayınlarını düzenleyebilir), (... ve sıfırlayabilir diğer kullanıcıların şifreleri) veya (... ve her neyse). Bu farklı hak kümelerinin her biri için bir role sahip olmak ve bir kullanıcıyı bir role veya başka birine atamak çok zor olmamalıdır, ancak uygulamanızın 'GRANT' ifadeleri çalıştırmasını istemezsiniz. Hiyerarşiye sahip ve mirasa bağlı olan rollere dikkat edin, kafa karıştırıcı olabilir. Bir kullanıcıyı tanıtıyor veya alçaltıyorsanız, onları ilişkili tüm rollerden çekip çıkardıklarını ve sonra da ihtiyaç duydukları rollere eklemelerini söylerim. Oh

Burada sadece yüzeyi çizdiğimi düşünüyorum ve bu yazı zaten çok uzun. Gereksinim duyduğunuz şey bir kitap ya da en azından bunu yapan birinden bir beyaz kağıt. Bu adamların çoğu, rekabet avantajı olarak görürlerse konuşmayacak.


Yorumlarınız için teşekkür ederiz. Gerçekten de proje ilginç. Kelime sınırlaması nedeniyle, yorumunuzu çok hassas tutarım. Her kiracının yaklaşık 120-150 masa alacağı bir Öğrenme Yönetim Sistemi'dir. Kiracıdan bağımsız olarak hiçbir kullanıcı aynı kullanıcı adına sahip değildir. Karmaşıklığı daha da azaltmak için DNS CNAME eşlemesi, örneğin kiracı1.abc.com. Şimdi Kaynama noktası - onu doğru bir şekilde tasarlamak böylece paylaştığınız tüm öneriyi karşılayacak ve bunun için endişeleniyorum. Teknik incelemeyi almak övgüye değer ancak kolay değil, belki de olabilir. !!!!
coddey
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.