Laravel Türkiye Discord Kanalı Forumda kod paylaşılırken dikkat edilmesi gerekenler!Birlikte proje geliştirmek ister misiniz?

Merhaba,
laravel de multi tenant, sass veya kiralama yoluyla uygulama geliştirenlerin tecrübelerini merak ediyorum.

Elbette uygulamaya göre değişiklik gösterir ama tek DB ile kiracı başına DB arasında hangisini tercih etmeliyiz/ediyorsunuz ?

Bu iş için söylenenler ; veri izolasyonu için çoklu db, yedekleme için tek db. Buna ek olarak, endekslerin boyutu büyüyecek ve büyük veri kümesine sahip bir kiracı, daha küçük veri kümelerine sahip diğer kiracıları etkileyecektir.

Gene multi tenant/sass uygulaması oluşturmak için paket kullanımı mı yoksa kendi yolumuzu oluşturmak mı ?

İncelediğim ve inceleyeceğim bazı paketler ;
https://tenancy.dev/docs/hyn/5.4
https://tenancyforlaravel.com/
https://github.com/romegasoftware/Multitenancy
https://docs.spatie.be/laravel-multitenancy/v1/introduction/

Bu konuyu en az 6-7 senedir çeşitli forumlarda ortamlarda tartışıyorum. Burda da konum vardır kesin, ne kadar Slack, Discord, Telegram kanalı varsa, ne kadar forum varsa, ne kadar meetup varsa hepsinde cevap aradım.

Ama bunun kesin bir cevabı olmadığını görüp bıraktım. 😃

Cevap: size hangisi daha uygunsa doğru olan odur. Bu kadarla kestirip atmak hoş değil biliyorum ama maalesef bu konuda sizi tatmin edecek cevabı bulamayacaksınız.

Ben ikisini de denedim. İkisiyle de çalıştım, ikisiyle de yoruldum. Günün sonunda hangisini tercih ederim derseniz %51 ile tek DB kazanır.

Tek DB seçme sebepleri:

-Güncelleştirmek daha kolay. İstediğin kadar otomatize et, güncelleştirme çoklu DB'de eziyet.

-Veri izolasyonu zor gibi görünüyor ama sizi challenge a zorluyor. Laravel özelinde konuşursak ben Gate'leri Policy'leri kullanmayı asla öğrenmezdim bu yola girmesem. Kolaya kaçmadan çaba harcarsanız sonucunda çok verimli bir yapı kurabilirsiniz.

Tek DB seçmeme sebepleri:

-Kiracıya özel dikey geliştirmeler eziyet.

Boş laflar:

-Efendim tek DB'de çalışırsan bir kiracının verisi büyürse diğer kiracıları etkiler.. derler. Eğer sen altyapını yatayda genişletemiyorsan tek bir kiracının verisi kendi DB'sinde çok büyürse sizin için değişen bişey olmaz. Yine isyanlardasınız. Öyle altyapı kuracaksınız ki hem yatay hem dikey genişlemeye imkan verecek. Ama dikey olmasa bile yatay kesin genişletebilmelisiniz. Biraz devops a kaçıyor konu ama multitenant bir girişim yapacaksanız bunlara hakim olmak zorla değil mecburi.

Uzun lafın kısası: tek DB'yi sonra bölmesi daha kolay, çok DB'yi sonra birleştirmesi daha zor. Tek DB ile başlayın, baktınız olmuyor, çoğaltırsınız.

Kolay gelsin. 🙂

    alihankoc teşekkürler,
    Peki multi tenant için paket kullanıyor musunuz ? önerir misiniz ?

    Hayır kullanmadım hiç. 😀

      3 yıl sonra

      alihankoc Tek db de teanncy yapsını sadece tablolara customer_id gibi belirteçler ekleyerek mi yaptın ?

        nuri60
        bu şekilde yapmıştım
        //users_table
        $table->integer('app_id')->default(0); // Bağlı olduğu App

        // Örnek Model
        public static function boot()
        {
        parent::boot();
        static::creating(function ($activity) {
        $uye = Auth::user();
        $activity->app_id = $uye->app_id ;
        //$activity->user_id = $uye->id ;
        });
        }

        public function newQuery($excludeDeleted = true)
        {
            $uye = Auth::user();
            return parent::newQuery($excludeDeleted = true)
                ->where('app_id', '=', $uye->app_id);
        }

        nuri60 Evet bu şekilde ama bir katman daha koymuştum arada tenants ve tenant_settings isimli tablolarım vardı. Buralarda tenant a özel ayarları falan da tutuyordum. Çünkü her tenant ın farklı ihtiyaçları da olabiliyor. Her bir customer ı bir tenant a bağladım, sonra da diğer tüm customer ın yazdığı tabloları tenant tablosuna tenant_id ile bağladım.

        Farz-ı misal users tablosu var, customer'ın bir tanesi name, surname, email zorunlu olsun diyor diğeri birthday ve profil foto da zorunlu olsun diyor. Bunun validasyonunu kodda yapamıyorsun çünkü her tenant a özel kod bloğu eklemen gerekir. Bu validasyonları db'de tenant_settings'te tutup tenant'a göre validasyonları buradan çekerek gerçekleştiriyordum. Bu sayede kullanıcıya panelden de zorunlu alanları değiştirmesine imkan tanıyordum. Tenant_settings tablosunu da redis te cacheliyordum. Çok efektif olmuştu.

        Bu validasyon sadece bir örnek, bu ayarlar bir sürü farklı senaryoda işimi kolaylaştırmıştı.

          alihankoc teşekkür ederim yanıtın için bu yazıya 2020 yılında yanıtlamışsın
          Mümkün ise bu zamana kadar bu konu hakkında edindiğin şeyleri özetleme şansın olur mu ?

            4 gün sonra

            nuri60 Edindiğim şeyleri özetlemek zor bir iş açıkçası, onlarca farklı projede yüzlerce farklı senaryo ile karşılaştım. Bu yüzden bu kadar genel bir soruya cevap vermem doğru olmaz ve zamanım da yetmez. Nereden başlayacağımı bile bilemiyorum şu an.

            Ancak siz bir problemi bana iletirseniz ben o probleme daha önce bir çözüm ürettiysem nasıl ürettim şeklinde, üretmediysem de ben olsam nasıl bir çözüm üretirdim şeklinde bir cevap verebilirim.

              alihankoc Bu konuya giriş yapan birine tavsiyeler vermek ister misin peki ?

                nuri60 İsterim. 😃

                Bugün tekrar multitenant bir app yapsam en çok dikkat edeceğim 5 madde:

                1-İlk tavsiyem müşterilere karşı çok esnek olmayın. Her tenant başka bir şey ister. Hepsine yaparız abi demeyin. Rijit kalın, yeri geldiğinde ki gelecek, bunu yapmayız diyebilmelisiniz. Multitenant bir app yapıyorsanız bir app yapıyorsunuz demektir değil mi. O zaman bir app yapın. Eğer çok esnek olursanız bir app içinde 1000 app yapmak zorunda kalırsınız. Her müşteriye o kadar dikey çözümler üretirsiniz ki artık içinden çıkılamaz hale gelir projeniz.

                2-Rol izin yönetimini baştan iyi düşünün. Bu tür projelerde sadece role dayalı bir mekanizma çalışmaz. Yani sizin belirlediğiniz roller sizin belirlediğiniz sınırlarda çalışsın isterseniz olmaz. Her tenant farklı sınırlar ister. Mesela bir tanesi muhasebeci faturaları görsün derken diğeri satışçı da görsün der. Bu yüzden izin mekanizması da olması lazım. Siz app içindeki izinleri belirlersiniz. Sonra rolleri serbest bırakırsınız, her tenant kendi rollerini belirler ve istediği izinleri rollere atar. Ancak uygulamanız çok kapsamlıysa işler bi yerden sonra çorba olabilir. Ne kadar karışabileceği konusunda 7 sene önce bu forumda açtığım konu burada: https://laravel.gen.tr/d/2986-row-level-security-satir-bazinda-guvenlik

                3-KVKK, GDPR, CCPA gibi veri gizliliği konusundaki kanunları iyi takip edin. Özellikle hassas veri saklıyorsanız kanunlara aykırı bir veri politikası izlemeyin. Bu kanunlar böyle hiç beklemediğiniz bir anda projenizi sonlandırma noktasına getirebilir. Çok korkunç para cezaları ile de karşı karşıya kalabilirsiniz. Mesela AB verisini AB dışına, TR verisini TR dışına, Çin verisini Çin dışına çıkarmak isterseniz app içinde kaydı bulunan her kullanıcıdan izin almış olmalısınız. Sakladığınız veri türüne göre hiç çıkaramama durumunuz da olabilir. Oluşturacağınız gizlilik politikaları için uzmanlardan yardım alın. Bu tür belgelerdeki açıkları bularak hak iddia eden ve para kazanan insanlar var. Her ülkenin veya bölgenin kendi kanunları var. Çok dikkat edin. Siz verilerin güvenliğinden sorumlu olduğunuz kadar nerede sakladığınızdan ve kim aracılığı ile sakladığınızdan da sorumlusunuz.

                4-Bu madde biraz 3.ün devamı gibi, sizin farklı müşterileriniz verisini farklı ülkelerde barındırmak istiyor (izin alabiliyor olsa bile) olabilir. Biri der ki bizim müşteriler AB'de, diğer der ki bizimkiler HongKong da biz verileri buralarda tutmak zorundayız. Şimdi böyle bir durumda mecburen farklı yerlerde veritabanlarınız bulunacak ama belki de tek DB mantığı ile ilerlediniz. Bu durumlara karşı önden hazırlıklı olmalısınız. Tek DB kullanıyor olsanız bile çok DB ye geçebiliyor olmalısınız. Aslında şöyle bir şey gerekebilir; tek DB ama HongKong bölgesindeki müşteriler tek DB, Avrupa bölgesindeki herkes tek DB gibi. Yani bunlar örnek çok senaryo çıkar. Bunları düşünerek tasarım yapın.

                5-Eğer uygulamanız multi-language ise çevirileri mutlaka tenantlara göre özelleştirilebilir bir yapıda kurun. Yani her tenant istediği bir metine istediği bir çeviriyi ekleyebilsin. Biri der ki validasyonda "eposta alanı zorunludur" yazsın, diğeri der ki "lütfen eposta adresinizi girin", diğeri de "epostaaaaaaaaa". Yine aynı madde içinde yazayım; Validasyonları da tenantlara göre özelleştirilebilir yapın. Biri eposta zorunlu olsun der biri olmasın de, bunu kendileri belirleyebilsin. Esnek olmayın dedik ilk maddede. Aslında bu imkanları baştan sağlarsanız sonradan esnemek zorunda kalmazsınız. Yani bu tür şeyleri baştan düşünürseniz sonra her müşteri gelip size ben eposta zorunlu olsun istiyorum, mesajı da alttan girsin üstten çıksın istiyorum demez, kendin arayüzden hallet diyebilirsin çünkü.

                Bonus cümleler:

                • Mümkünse çok yük alan servislerinizi mikroservise dönüştürün.
                • Arayüzü de siz yapıyorsanız çok basit yapın. Süsten püsten mümkün mertebe kaçının. Son kullanıcı Nasa'da mühendis bile olsa sizin ürününüzü (aslında kendisine ait olmayan bir ürünü diyelim) teknoloji özürlü gibi kullanır. İlk baktığında kolayca anlam veremeyeceği hiç bir şey olmasın arayüzde.
                • Kullanıcılara iki adımlı doğrulama yöntemiyle giriş yaptırın.
                • Yönetim paneli gibi bir şey yapacaksanız projeden tamamen ayırın ayrı bir proje olarak geliştirin.
                • Localization ile internalization'u karıştırmayın. Çok dilli yaparsınız ama localize etmek farklı bir şeydir. Mesela adam Türkçe kullanıyordur arayüzü ama para birimi Euro'dur ve Avrupa'da iş yapıyordur. Sizin vergi oranlarınız, para birimleriniz vs hepsi bu tenanta göre olmalıdır.
                • Aklıma çok gelir düşünürsem ama burada bırakıyorum. Aklıma gelirse yine eklerim. 😃

                Bol şans.

                  alihankoc çok çok teşekkür ederim zaman ayırıp cevapladın için 🙏🙏

                  alihankoc Çok değerli tecrübeler. Paylaştığınız için teşekkürler.