Google kısa süre önce Firebase bünyesinde yeni veritabanı olan Cloud Firestore’i duyurdu. Şuan Beta sürümü mevcut olan Firestore birçok özelliğiyle birlikte kullanıma sunuldu. Bu makalede birlikte artı ve eksi yönlerini inceleyelim.
Cloud Firestore Nedir?
Google’nin büyük ve karmaşık yapıdaki verileri saklamak ve hızlıca sorgulamak amacıyla geliştirdiği dokuman tabanlı Nosql veritabanıdır.
Firestore esnek bir yapıya sahiptir. Veriler istenilen şemada tutulabilir. Veriler dokuman (document) adı verilen yapılarda saklanır. Dokuman topluluğuna ise Koleksiyon (collections) adı veriliyor. Bu yapısı itibariyle diğer Nosql veritabanlarına benzemekte.
Cloud Firestore vs Realtime Database
Bildiğiniz üzere Firebase’in önceden zaten Realtime Database adında bir veritabanı vardı. Peki Cloud Firestore’in mevcuttaki bu veritabanından farkı nedir ?
Cloud Firestore daha karmaşık verileri saklamak ve sorgulamak için daha gelişmiş çözümler sunuyor. Yani iç içe (Nested) verileri saklarken ve sorgularken Cloud Firestore daha performanslı, ölçeklenebilir ve esnek bir yapı sağlıyor. Sade veriler saklayacaksanız Realtime Database kullanabilirsiniz. Fakat Cloud Firestore’ nin sade verilerde de başarılı olduğunu ve gelişmiş özellikler sunduğunu da göz önünde bulundurun.
Cloud Firestore’nin Başlıca Özellikleri
- Gerçek zamanlı güncelleme özelliği (realtime listeners) sayesinde veritabanın da değişiklik olduğunda, otomatik senkronizasyon yapılarak mobil uygulamada veya web sitesinde verilerin kendiliğinden güncellenmesini sağlar.
- Offline modu desteği ile internet olmadığında cihazın localinden veriler okunabilir, yazılabilir. İnternet geldiğinde otomatik olarak cloud veritabanına senkronizasyon yapılabilir.
- Firebase Authentication ile tam uyumlu çalışmaktadır. Böylece kullanıcının yetkisine göre verilere erişim veya kısıtlama sağlanabilmektedir.
- Karmaşık, hiyerarşik, iç içe verileri kolaylıkla saklayabilir, hızlı sorgular yapabilirsiniz. Verileri belli bir şemaya göre saklamak zorunda olmadığınız için her bir dokuman farklı sayıda ve isimde alanlar içerebilir.
- Zengin platform desteği (Web, IOS, Android, Java, Node.js, Php, Go, Python..)
- Veriler Key-Value şeklinde saklanır. Her dokumanın ID’si olmalıdır. ID ister siz verin isterseniz Firestore otomatik oluştursun.
Index Yapısı
Firestore her alan için kendisi otomatik index oluşturur. Eğer tek bir alanı filtre yapıyorsanız bu indexler sayesinde hızlıca sorgu yapabilirsiniz. Eğer birden fazla alana sorgu yapıyorsanız, sorgu yapacağınız alanları sırasıyla index tanımı yapmanız gerekmektedir. Aksi halde Firestore hata verecektir. Index tanımlarını Firebase Console girerek Firestore -Indexses sekmesinden yapabilirsiniz.
İç İçe (Nested) Verileri Saklama ve Sorgulama
Firestore iç içe karmaşık yapıdaki dokumanları saklayabilmek için farklı yaklaşımlar sunmaktadır. Bunlar:
1- Nested data in documents: Dokuman içinde iç içe Json data saklamak. Eğer sade ve basit listeler saklayacaksanız bu yöntemi kolaylıkla kullanabilirsiniz. Fakat zamanla büyüyecek belgeleriniz varsa bu yöntem zamanla performans kaybı yaşamanıza sebebiyet verecektir. Bununla beraber iç içe verileri istediğiniz gibi sorgulayamayabilirsiniz.
- name :
first : “Ada”
last : “Lovelace”
born : 1815
rooms :
0 : “Software Chat”
1 : “Famous Figures”
2 : “Famous SWEs”
2- Subcollections (Alt koleksiyonlar): Dokuman içinde alt koleksiyonlara referans vererek verilerinizi saklayabilirsiniz. Bu yöntemde dokuman içindeki liste büyüdükçe dokuman boyutu büyümez. Zaman içinde genişleyecek veri olduğundan tercih edebilirsiniz. Alt koleksiyonlara rahatlıkla sorgu yapabilirsiniz. Fakat dokumanı sildiğinizde alt koleksiyonlar silinmeyecektir. Manuel olarak silmeniz gerekecek.
3-Root-level Collections: İç içe yapılarda diğer dokumanların ID’lerini saklayarak erişim sağlayabilirsiniz. İlişkisel yapıda verilerinizi saklayabilirsiniz. Fakat zamanla hiyerarşi arttıkça sorgularınız karmaşıklaşabilir.
Firestore Eksiklikleri & Dezavantajları
Makaleyi yazdığım tarih itibariyle Firestorede benim gördüğüm bazı eksiklikler şunlar:
- Gelişmiş bir sorgu yapısı mevcut değil. Örneğin OR kullanamıyoruz. Bunun için verileri ayrı ayrı çekmeniz gerekiyor.
- Eşit Değildir (!=) operatorü mevcut değil. Bunun yerine “>=” ve “<=” ile between sorgusu yaparak bunu sağlamayı önermişler.
- Eğer çoklu filtreler yapacaksanız her sorgudaki filtre dizilimi için index oluşturmanız gerekiyor.
- Full text search özelliği mevcut değil. Bunun için Algolia veya elasticsearch gibi 3. party yapılar kullanmanız gerekiyor.
- Aggregation yok! Böyle bir sorununuz varsa çözüm olarak firestore şunu öneriyor: Her ekleme işleminden sonra git veritabanında ki kayıtlara göre hesaplama yap ve static alanlara hesaplanmış değerleri yaz. Bunu ya client’te yada Firebase Cloud Function yapısında yapabilirsiniz.
- Bazı değişik kuralları da bulunuyor. Örneğin bir sorgu çekiyorsunuz. Filtre olarak range (iki değer arası) gibi bir filtre yaptınız. Ardından Order By ile sıralamak istiyorsunuz. Kural olarak ilk sıraladığınız alan range filtresine tabi tuttuğunuz alan olmalı. Yoksa hata verecektir.
Kodlama Yapısı
Firestore birçok programlama dilinde desteklenmektedir. Kolay ve güvenilir bir altyapı sunmaktadır. Aşağıda bazı Javascript örnek kodlar bulunmaktadır:
Javascript projesine firebase eklemek
//Script dosyalarını ekleyelim //Veya npm ile kurulum yapabilirsiniz. npm install firebase@4.12.0 --save const firebase = require("firebase"); require("firebase/firestore"); //Firebase konsoldan api key'lerinizi edinebilirsiniz. firebase.initializeApp({ apiKey: '### FIREBASE API KEY ###', authDomain: '### FIREBASE AUTH DOMAIN ###', projectId: '### CLOUD FIRESTORE PROJECT ID ###' }); //Firebase başlatıp db değişkenimizi kullanıma hazır hale getiriyoruz var db = firebase.firestore();
Verilere erişim:
//Users koleksiyonunu getir var usersCollectionRef = db.collection('users'); //users koleksiyonunun altındaki ID'si 'yunus' olan dokumanı getir var alovelaceDocumentRef = db.doc('users/yunus'); //Alt koleksiyonlara erişim var messageRef = db.collection('rooms').doc('roomA').collection('messages').doc('message1'); //Capital = true olan city'leri getir. var cityList = db.collection("cities").where("capital", "==", true); //Çoklu filtre kullanımı var cityList = db.collection("cities").where("state","==","EL").where("population",">",100000); //Name alanına göre sırala ve ilk 3 tanesini al citiesRef.orderBy("name","asc").limit(3);
Dokuman eklemek
db.collection("cities").doc("EL").set({ name: "Elazığ", country: "Turkey" }) .then(function() { console.log("Document successfully written!"); }) .catch(function(error) { console.error("Error writing document: ", error); });
Dokuman silmek
db.collection("cities").doc("DC").delete().then(function() { console.log("Document successfully deleted!"); }).catch(function(error) { console.error("Error removing document: ", error); });
Daha fazla bilgiye ulaşmak için Firestore dökümantasyonuna göz atabilirsiniz.
Yunus Bey teşekkürler yazı için
Projemde Firestore kullanıyorum şu an yapım aşamasında ancak aklıma takılan bazı yerler var:
Aslen offline bir proje. Kullanıcı benim firebaseimdeki PNG formatındaki verilerimi cihazına download edecek, onları istediği zaman offline görüntüleyebilecek, ancak onları modifiye edemeyecek, değiştiremeyecek vs kullanıcı kısaca hiçbir şey yapamaz yalnızca offline istediği zaman isterse 1 yıl sonra bile indirdiği şekilde kullanır. Ancak ben PNG’lere yenilerini eklediğimde, veya var olanları değiştirdiğimde, veya mevcut PNG’ler içerisinden bazılarını sildiğimde kullanıcı online olup benim databaseim ile sync olduğunda sadece benim yaptığım değişiklikleri indirerek kendi cihazı ile benim databaseimi eşlemeli.
dolayısıyla 2 fonksiyon var
1- rahatça offline kullanım
2- mantıklı senkronizasyon: mesela toplam 100 mb ilk PNG olduğunda ben 1 tane eklediğimde bunlara bütün hepsini tekrar tekrar indirmemeli faturayı ödeyemem 🙂
Sizce Firestore bunlar için mantıklı bir seçim mi yoksa alternatiflerim mevcut mudur?
Teşekkürler
Merhaba Akif Bey.
Offline çalışmayı firebase ile yapabilirsiniz. Değiştiremesin istiyorsanız kendiniz bir yapı kurmanız gerekebilir. Çok fazla medya alış verişi olacaksa dediğiniz gibi fatura kabarık olabilir. Medya kısmını duruma göre kendi ftp hesabınız üzerinden de sağlayabilirsiniz.
Size tavsiyem firebase ödeme tablosundaki limitleri göz önüne alarak buna karar vermeniz.
Hocam yazı için teşekkürler bir sorum olacaktı. Bir mobil uygulama yazmaya karar verdik iki platform içinde uygulama büyük birşey olacak yemeksepeti gibi birşey olacak o kadar ayrıntı olmayacak ama veri alışverişi 7/24 olacak bunun için Cloud Firestore mi öneririsiniz yada önerebileceğiniz başka bir veritabanı varmıdır acaba ? Cevabınızı bekliyorum. İyi Günler…
İşin içine ödeme, bakiye, işlem bütünlüğü (transaction) gibi işler gireceği için nosql yerine Relational bir database kullanmanızı tavsiye ederim. Örneğin Mssql, Mysql vb. kullanabilirsiniz.
Merhaba.
Fribase elastic Search kullanımı ile ilgili bilginiz var mı? Yada kaynak bildiğiniz. Angular projemde fribasecloud DB kullanıyorum ve Search için elastic veya ne kullanabilirim. Nasıl entegre edebilirim. Bilginiz var ise paylasabilirmisiniz? Şimdiden çok teşekkürler
Malesef bilgim yok
merhabalar,
firebase cloud messaging ile uygulamaya bildirim atabiliyorum. bu bildirimi uygulama içinde de kullanmak istiyorum. label veya alert gibi bi yerde yazsın istiyorum. Kaynaklarda cloud firestore gibi şeyler gördüm. daha önce buna benzer bir çalışmanız olmuş muydu?
teşekkürler, iyi çalışmalar
Merhaba,
onMessageReceived event’i ile gelen bildirimleri yakalayıp uygulama içinde gösterebilirsiniz.
https://firebase.google.com/docs/cloud-messaging/android/receive