简体   繁体   English

Firebase 云函数中的聊天消息通知。 触发云时无法从 promise 获取数据 Function

[英]Chat message notification in Firebase Cloud Functions. Can't get data from a promise when triggering a Cloud Function

I develop in iOS and this is the first time I'm coding in Typescript. I made my first Cloud Function that triggers when a new chat message is sent in RTDB and notifies the members that receive the message.我在 iOS 开发,这是我第一次在 Typescript 编码。我制作了我的第一个 Cloud Function,它在 RTDB 中发送新聊天消息时触发并通知接收消息的成员。

When I make the call to Firestore to get tokens of the user devices (userTokens) I get no errors and have the correct path, but the data returned from those promises don't show anything.当我调用 Firestore 以获取用户设备的令牌 (userTokens) 时,我没有收到任何错误并且路径正确,但是从这些承诺返回的数据没有显示任何内容。 When I log the "tokenList" it just says ["0"].当我记录“tokenList”时,它只是说 [“0”]。 I think the error is when I push the promise to a list or resolve them, but I haven't managed to fix it.我认为错误是当我将 promise 推送到列表或解决它们时,但我还没有设法修复它。

The code:代码:

import * as functions from "firebase-functions"
import * as admin from "firebase-admin"
admin.initializeApp()

export const newLastMessageDetected = functions.database
.ref('/ChatMessages/{chatID}/{messageID}/')
.onCreate(async (snap, context) => {
    const values = snap.val()
    const chatID = context.params.chatID
    const messageID = context.params.messageID
    const message = values.message
    const fromID = values.fromID
    const fromName = values.fromName

    console.log( `LastMessage changed with chatID: ${chatID} and messageID ${messageID} `)
    console.log( `Last message: ${message} by fromID: ${fromID} and by name ${fromName}`)

    const payload = { 
        notification: {
            title: fromName,
            body: message
            
        }
    }

    let membersSnapshotRef =  admin.database().ref('/Members/' + chatID + '/')

    return membersSnapshotRef.once('value')
        .then(dataSnapshot => {
            const promises = []
            console.log('*** GOT SNAPSHOT ***')
            dataSnapshot.forEach((element) => {
                if (element.key != fromID && element.val() === true) {
                    const p = admin.firestore().collection('userTokens').doc(`${element.key}`).collection('devices').get()
                    console.log('*** GOT PROMISE ***')
                    console.log(`*** The recipientID: ${element.key} ***`)
                    console.log(`${p}`)                    
                    promises.push(p)
                }
                
            })
            return Promise.all(promises).then(snapshot => {
                console.log('*** GOT RETURNED PROMISES ***')
                const tokenList = []
                const data = snapshot.keys()
                for (const token in data) {
                    console.log(`${token}`)
                    tokenList.push(token)
                }
                console.log(`${tokenList}`)
                return admin.messaging().sendToDevice(tokenList, payload).then(result => {
                    console.log("Notification sent!");
                    return null;
            })

           
        })
        .catch(error => {
            console.log(`${error}`)
        })
       
    })
    
})

When you use Promise.all() , the result of the promise it returns is always going to be an array.当您使用Promise.all()时,它返回的 promise 的结果始终是一个数组。

Promise.all(promises).then(snapshot => {
    // snapshot is an array of results with one element for each of the promises
})

You need to iterate that array to find the results of all the promises you stored in the promises array.您需要迭代该数组以找到存储在promises数组中的所有 promise 的结果。 snapshot.keys() does not iterate that array - it is just giving you a list of numbers that are the indexes of those array. snapshot.keys()不会迭代该数组 - 它只是为您提供一个数字列表,这些数字是这些数组的索引。 Try using snapshot.forEach() instead.尝试改用snapshot.forEach()

You might want to review some documentation for promise.all .您可能想要查看promise.all 的一些文档

I actually really messed up because I tried to retrieve the data on the query;我真的搞砸了,因为我试图检索查询中的数据; didn't realize that the first loop was on the retrieved queries, so I had to do another on the documents retrieved.没有意识到第一个循环是针对检索到的查询,所以我不得不对检索到的文档执行另一个循环。 The device tokens are each of the documentIDs with the timestamp stored as the data.设备令牌是每个文档 ID,其中时间戳存储为数据。

The working code:工作代码:

import * as functions from "firebase-functions"
import * as admin from "firebase-admin"
admin.initializeApp()

export const newLastMessageDetected = functions.database
.ref('/ChatMessages/{chatID}/{messageID}/')
.onCreate(async (snap, context) => {
    const values = snap.val()
    const chatID = context.params.chatID
    const messageID = context.params.messageID
    const message = values.message
    const fromID = values.fromID
    const fromName = values.fromName

    console.log( `LastMessage changed with chatID: ${chatID} and messageID ${messageID} `)
    console.log( `Last message: ${message} by fromID: ${fromID} and by name ${fromName}`)

    const payload = { 
        notification: {
            title: fromName,
            body: message
            
        }
    }

    let membersSnapshotRef =  admin.database().ref('/Members/' + chatID + '/')

    return membersSnapshotRef.once('value')
        .then(dataSnapshot => {
            const promises = []
            // const docIDS = []
            console.log('*** GOT SNAPSHOT ***')

            dataSnapshot.forEach((element) => {
                if (element.key != fromID && element.val() === true) {
                    const doc = admin.firestore().collection('userTokens').doc(`${element.key}`).collection('devices')
                    const p = doc.get()
                    // const docID = doc.id
                    console.log('*** GOT PROMISE ***')
                    console.log(`*** The recipientID: ${element.key} ***`)
                    // console.log(`*** The docID: ${docID} ***`)
                    promises.push(p)
                    // docIDS.push(docID)
                }
                
            })
            return Promise.all(promises)
        })
        .then(async querySnapshot => {
            console.log('*** GOT RETURNED PROMISES ***')
            const tokenList = []
            
            querySnapshot.forEach(snap => { // first here
                console.log(`${snap.id}  *** `) 
                console.log(`${snap}  *** `) 
                
                snap.forEach(doc => { // then here
                    console.log(`${doc.id}`)
                    tokenList.push(doc.id)
                })
            
            })

            await admin.messaging().sendToDevice(tokenList, payload)
            console.log("Notification sent!")
            return null
           
          
        })
        .catch(error => {
            console.log(`${error}`)
        })
    
})

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 Firebase 在没有云功能的情况下发送新消息时向聊天成员推送通知 - Firebase pushing notification to chat members when a new message gets delivered without cloud functions 具有 Firebase 实时数据库的云功能未触发 onCreate 且未发送 FCM 通知 - Cloud functions with Firebase Realtime Database not triggering onCreate and not sending FCM notification Firebase crashlytics 的云函数未触发 - Firebase cloud functions for crashlytics are not triggering 从 Cloud 触发数据流作业时 dill 出错 Function - Error with dill when triggering a Data Flow job from Cloud Function Firebase Cloud Functions - 从 https 中的上下文获取来源可调用 function - Firebase Cloud Functions - get origin from context in https callable function 未收到通过 iOS 应用程序中的 firebase 云功能发送的推送通知,尽管我从消息控制台获取 - Not receiving push notification sent via firebase cloud functions in iOS app though I get the from messaging console 如何从 React stream 聊天应用程序调用 Firebase 云 function - How to call Firebase cloud function from React stream chat app Firebase RemoteConfig 是否可以从云功能访问 - Can Firebase RemoteConfig be accessed from cloud functions 当从 firestore 的 firebase 云 function 中获取数据时,我们在使用转换器时得到的是不可分配的错误 - When fetching data in a firebase cloud function from firestore we get is not assignable errors when using a converter 无法部署到 firebase 云 function - Can´t deploy to firebase cloud function
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM