当有人喜欢一张照片时,我正在尝试使用Firebase Cloud Functions发送通知。我已经解决了Firebase的例子,展示了当有人关注你并试图修改它时如何发送一个。
问题是,我需要在函数中执行另一个额外的查询,以获得喜欢照片的人的密钥,然后才能从他们的用户节点获得他们的令牌。问题是getDeviceTokensPromise不知何故没有得到满足,并且tokensSnapshot.hasChildren无法读取,因为它是未定义的。我怎么才能修复它?
exports.sendPhotoLikeNotification = functions.database.ref(`/photo_like_clusters/{photoID}/{likedUserID}`)
.onWrite((change, context) => {
const photoID = context.params.photoID;
const likedUserID = context.params.likedUserID;
// If un-follow we exit the function
if (!change.after.val()) {
return console.log('User ', likedUserID, 'un-liked photo', photoID);
}
var tripName;
var username = change.after.val()
// The snapshot to the user's tokens.
let tokensSnapshot;
// The array containing all the user's tokens.
let tokens;
const photoInfoPromise = admin.database().ref(`/photos/${photoID}`).once('value')
.then(dataSnapshot => {
tripName = dataSnapshot.val().tripName;
key = dataSnapshot.val().ownerKey;
console.log("the key is", key)
return getDeviceTokensPromise = admin.database()
.ref(`/users/${key}/notificationTokens`).once('value');
///// I need to make sure that this returns the promise used in Promise.all()/////
});
return Promise.all([getDeviceTokensPromise, photoInfoPromise]).then(results => {
console.log(results)
tokensSnapshot = results[0];
// Check if there are any device tokens.
//////This is where I get the error that tokensSnapshot is undefined///////
if (!tokensSnapshot.hasChildren()) {
return console.log('There are no notification tokens to send to.');
}
// Notification details.
const payload = {
notification: {
title: 'Someone liked a photo!',
body: `${username} liked one of your photos in ${tripName}.`,
}
};
// Listing all tokens as an array.
tokens = Object.keys(tokensSnapshot.val());
// Send notifications to all tokens.
return admin.messaging().sendToDevice(tokens, payload);
});
发布于 2018-06-10 02:32:59
好的,根据你的评论,这是最新的答案。
您需要链接您的承诺,并且您不需要使用Promise.all()
-该函数用于一组异步任务,所有这些任务都需要在您采取下一步操作之前(并行地)完成。
您的解决方案应该如下所示:
admin.database().ref(`/photos/${photoID}`).once('value')
.then(dataSnapshot => {
// Extract your data here
const key = dataSnapshot.val().ownerKey;
// Do your other stuff here
// Now perform your next query
return admin.database().ref(`/users/${key}/notificationTokens`).once('value');
})
.then(tokenSnapshot => {
// Here you can use token Snapshot
})
.catch(error => {
console.log(error);
});
因为您的第二个网络请求依赖于第一个请求的完成,所以通过在第一个请求之后附加第二个.then()
来链接您的承诺,并且不要使用分号;终止它。如果在第一个.then()
作用域中创建的新promise解析,它将调用第二个.then()
函数。
如果您需要访问第二个.then()
作用域中的变量,则必须在常规函数中声明它们,并在闭包作用域中分配它们。
你可以在promise chaining here上查看更多信息。
https://stackoverflow.com/questions/50776237
复制相似问题