Cloud Functions ile istemci kodunu güncellemenize gerek kalmadan Firebase Realtime Database'teki etkinlikleri yönetebilirsiniz.
Cloud Functions, Realtime Database işlemlerini tam yönetici ayrıcalıklarıyla yürütmenize olanak tanır ve Realtime Database'da yapılan her değişikliğin ayrı ayrı işlenmesini sağlar. Firebase Realtime Database değişikliklerini DataSnapshot
veya Admin SDK üzerinden yapabilirsiniz.
Tipik bir yaşam döngüsünde Firebase Realtime Database işlevi aşağıdakileri yapar:
- Belirli bir Realtime Database konumunda değişiklik yapılmasını bekler.
- Bir etkinlik gerçekleştiğinde tetiklenir ve görevlerini gerçekleştirir (Cloud Functions ile neler yapabilirim? başlıklı makaleyi inceleyin. kullanım alanı örnekleri için).
- Belirtilen dokümanda depolanan verilerin anlık görüntüsünü içeren bir veri nesnesi alır.
Realtime Database işlevini tetikleme
functions.database
ile Realtime Database etkinlikleri için yeni işlevler oluşturun. Fonksiyonun ne zaman tetikleneceğini kontrol etmek için etkinlik işleyicilerden birini ve etkinlikleri dinleyeceği Realtime Database yolunu belirtin.
Etkinlik işleyiciyi ayarlama
İşlevler, Realtime Database etkinliklerini iki düzeyde işlemenize olanak tanır: Yalnızca oluşturma, güncelleme veya silme etkinliklerini dinleyebilir ya da bir yoldaki her türlü değişikliği dinleyebilirsiniz. Cloud Functions, Realtime Database için aşağıdaki etkinlik işleyicileri destekler:
- Realtime Database alanında veri oluşturulduğunda, güncellendiğinde veya silindiğinde tetiklenen
onWrite()
. - Realtime Database içinde yeni veri oluşturulduğunda tetiklenen
onCreate()
. - Realtime Database kaynağında veriler güncellendiğinde tetiklenen
onUpdate()
. - Realtime Database kaynağından veri silindiğinde tetiklenen
onDelete()
.
Örneği ve yolu belirtin
İşlevinizin ne zaman ve nerede tetiklenmesi gerektiğini kontrol etmek için bir yol belirtmek üzere ref(path)
'u çağırın ve isteğe bağlı olarak instance('INSTANCE_NAME')
ile bir Realtime Database örneği belirtin. Bir örnek belirtmezseniz işlev, Firebase projesinin varsayılan Realtime Database örneğine dağıtılır. Örneğin:
- Varsayılan Realtime Database örneği:
functions.database.ref('/foo/bar')
- "uygulama-veritabanı-2" adlı örnek:
functions.database.instance('my-app-db-2').ref('/foo/bar')
Bu yöntemler, işlevinizi Realtime Database örneğindeki belirli bir yoldaki yazma işlemlerini gerçekleştirecek şekilde yönlendirir. Yol spesifikasyonları, bir yola dokunan tüm yazma işlemlerini (altındaki herhangi bir yerde gerçekleşen yazma işlemleri dahil) eşleştirir. İşlevinizin yolunu /foo/bar
olarak ayarlarsanız bu yol aşağıdaki iki konumdaki etkinliklerle eşleşir:
/foo/bar
/foo/bar/baz/really/deep/path
Her iki durumda da Firebase, etkinliğin /foo/bar
tarihinde gerçekleştiğini yorumlar ve etkinlik verileri /foo/bar
tarihindeki eski ve yeni verileri içerir. Etkinlik verileri büyük olabilir. Bu durumda, veritabanınızın köküne yakın tek bir işlev yerine daha derin yollarda birden fazla işlev kullanmayı düşünebilirsiniz. En iyi performans için yalnızca mümkün olan en derin düzeyde veri isteyin.
Bir yol bileşenini, köşeli parantezle çevreleyerek joker karakter olarak belirtebilirsiniz; ref('foo/{bar}')
, /foo
'un herhangi bir alt öğesiyle eşleşir. Bu joker karakterli yol bileşenlerinin değerleri, işlevinizin EventContext.params
nesnesinde kullanılabilir. Bu örnekte değer context.params.bar
olarak kullanılabilir.
Joker karakter içeren yollar, tek bir yazma işleminden birden fazla etkinliği eşleştirebilir.
{
"foo": {
"hello": "world",
"firebase": "functions"
}
}
"/foo/{bar}"
yolunu iki kez eşleştirir: bir kez "hello": "world"
ile ve bir kez de "firebase": "functions"
ile.
Etkinlik verilerini işleme
Realtime Database etkinliği işlenirken döndürülen veri nesnesi bir DataSnapshot
olur.
onWrite
veya onUpdate
etkinlikleri için ilk parametre, tetikleyici etkinlikten önceki ve sonraki veri durumunu temsil eden iki anlık görüntü içeren bir Change
nesnesi olur. onCreate
ve onDelete
etkinlikleri için döndürülen veri nesnesi, oluşturulan veya silinen verilerin anlık görüntüsüdür.
Bu örnekte işlev, belirtilen yolun anlık görüntüsünü alır, bu konumdaki dizeyi büyük harfe dönüştürür ve değiştirilmiş dizeyi veritabanına yazar:
// Listens for new messages added to /messages/:pushId/original and creates an // uppercase version of the message to /messages/:pushId/uppercase exports.makeUppercase = functions.database.ref('/messages/{pushId}/original') .onCreate((snapshot, context) => { // Grab the current value of what was written to the Realtime Database. const original = snapshot.val(); functions.logger.log('Uppercasing', context.params.pushId, original); const uppercase = original.toUpperCase(); // You must return a Promise when performing asynchronous tasks inside a Functions such as // writing to the Firebase Realtime Database. // Setting an "uppercase" sibling in the Realtime Database returns a Promise. return snapshot.ref.parent.child('uppercase').set(uppercase); });
Kullanıcı kimlik doğrulama bilgilerine erişme
EventContext.auth
ve EventContext.authType
üzerinden, bir işlevi tetikleyen kullanıcının izinleri dahil kullanıcı bilgilerine erişebilirsiniz. Bu, güvenlik kurallarını zorunlu kılmak için yararlı olabilir. Böylece işlevinizin, kullanıcının izin düzeyine göre farklı işlemleri tamamlamasına izin verebilirsiniz:
const functions = require('firebase-functions/v1');
const admin = require('firebase-admin');
exports.simpleDbFunction = functions.database.ref('/path')
.onCreate((snap, context) => {
if (context.authType === 'ADMIN') {
// do something
} else if (context.authType === 'USER') {
console.log(snap.val(), 'written by', context.auth.uid);
}
});
Ayrıca, bir kullanıcının "kimliğine bürünmek" ve kullanıcı adına yazma işlemleri gerçekleştirmek için kullanıcı kimlik doğrulama bilgilerinden yararlanabilirsiniz. Eşzamanlılık sorunlarını önlemek için uygulama örneğini aşağıda gösterildiği gibi sildiğinizden emin olun:
exports.impersonateMakeUpperCase = functions.database.ref('/messages/{pushId}/original')
.onCreate((snap, context) => {
const appOptions = JSON.parse(process.env.FIREBASE_CONFIG);
appOptions.databaseAuthVariableOverride = context.auth;
const app = admin.initializeApp(appOptions, 'app');
const uppercase = snap.val().toUpperCase();
const ref = snap.ref.parent.child('uppercase');
const deleteApp = () => app.delete().catch(() => null);
return app.database().ref(ref).set(uppercase).then(res => {
// Deleting the app is necessary for preventing concurrency leaks
return deleteApp().then(() => res);
}).catch(err => {
return deleteApp().then(() => Promise.reject(err));
});
});
Önceki değeri okuma
Change
nesnesinde, etkinlikten önce Realtime Database nesnesine kaydedilenleri incelemenizi sağlayan bir before
özelliği vardır. before
mülkü, tüm yöntemlerin (örneğin, val()
ve exists()
) önceki değere atıfta bulunduğu bir DataSnapshot
döndürür. Orijinal DataSnapshot
özelliğini kullanarak veya after
özelliğini okuyarak yeni değeri tekrar okuyabilirsiniz. Herhangi bir Change
öğesindeki bu mülk, etkinliğin gerçekleşmesinden sonra verilerin durumunu temsil eden başka bir DataSnapshot
öğesidir.
Örneğin, before
mülkü, işlevin metni yalnızca ilk oluşturulduğunda büyük harf kullanmasını sağlamak için kullanılabilir:
exports.makeUppercase = functions.database.ref('/messages/{pushId}/original')
.onWrite((change, context) => {
// Only edit data when it is first created.
if (change.before.exists()) {
return null;
}
// Exit when the data is deleted.
if (!change.after.exists()) {
return null;
}
// Grab the current value of what was written to the Realtime Database.
const original = change.after.val();
console.log('Uppercasing', context.params.pushId, original);
const uppercase = original.toUpperCase();
// You must return a Promise when performing asynchronous tasks inside a Functions such as
// writing to the Firebase Realtime Database.
// Setting an "uppercase" sibling in the Realtime Database returns a Promise.
return change.after.ref.parent.child('uppercase').set(uppercase);
});