0

I am working on a job bidding app.

Each user has a field "User job notifications preferences".

The array field stores the data to which type of job they would like to receive notifications for.

for example: Person A has the setting to receive a notification when a job of type 'plumming' is created. Person B has the setting to receive a notification when a job of type 'electrical' is created.

Person C creates a plumming job, Peron A should receive a notification to let them know a new job of type 'plumming' has been created.

here is the code snip

// when a job is updated from new to open
// send notifications to the users that signed up for that jobtype notification
exports.onJobUpdateFromNewToOpen= functions.firestore
    .document('job/{docId}')
    .onUpdate(async (change, eventContext) => {
        const beforeSnapData = change.before.data();
        const afterSnapData = change.after.data();
        const jobType = afterSnapData['Job type'];
        const afterJobState = afterSnapData["Job state"];
        const beforeJobState = beforeSnapData["Job state"];

        console.log('job updated');

        // only consider jobs switching from new to open
        if (beforeJobState=="New" && afterJobState == "Open") {
            console.log('job updated from new to open');
            console.log('jobType: '+jobType);
            console.log('job id: '+change.after.id )


            // get users that contain the matching job type
            const usersWithJobTypePreferenceList = await admin.firestore().collection("user").where("User job notifications preferences", "array-contains-any", jobType).get();

            // get their userIds
            const userIdsList = [];
            usersWithJobTypePreferenceList.forEach((doc) => {
                const userId = doc.data()["User id"];
                userIdsList.push(userId);
            })

            // get their user tokens
            const userTokenList = [];
            for (var user in userIdsList) {
                const userId = userIdsList[user];
                const userToken = await (await admin.firestore().collection("user token").doc(userId).get()).data()["token"];
                userTokenList.push(userToken);
            };

            // send message
            const messageTitle = "new " + jobType + " has been created";
            for (var token in userTokenList) {
                var userToken = userTokenList[token];

                const payload = {
                    notification: {
                        title: messageTitle,
                        body: messageTitle,
                        sound: "default",
                    },
                    data: {
                        click_action: "FLUTTER_NOTIFICATION_CLICK",
                        message: "Sample Push Message",
                    },
                };

                return await admin.messaging().sendToDevice(receiverToken, payload);


            }


        }


    });

I think the issue is at the following line because I am getting the error 'Error: 3 INVALID_ARGUMENT: 'ARRAY_CONTAINS_ANY' requires an ArrayValue' (see image)

const usersWithJobTypePreferenceList = await admin.firestore().collection("user").where("User job notifications preferences", "array-contains-any", jobType).get();

cloud function error logs

below is the full error:

Error: 3 INVALID_ARGUMENT: 'ARRAY_CONTAINS_ANY' requires an ArrayValue.
    at Object.callErrorFromStatus (/workspace/node_modules/@grpc/grpc-js/build/src/call.js:31:19)
    at Object.onReceiveStatus (/workspace/node_modules/@grpc/grpc-js/build/src/client.js:352:49)
    at Object.onReceiveStatus (/workspace/node_modules/@grpc/grpc-js/build/src/client-interceptors.js:328:181)
    at /workspace/node_modules/@grpc/grpc-js/build/src/call-stream.js:188:78
    at processTicksAndRejections (node:internal/process/task_queues:78:11)

I interpret the error as the following: there is no value being passed to 'jobType'.but that cant be right because I am printing the value ( see screenshot )

I found the following related questions but I dont think I am having the same issue:

Getting firestore data from a Google Cloud Function with array-contains-any

Firestore: Multiple 'array-contains'

So I am not sure what the issue is here, any ideas?

here is how the data looks in firebase: data structure in firebase

I looked at similar questions and I printed the values being passed to the function that was creating the error

Dharmaraj
  • 47,845
  • 8
  • 52
  • 84
Juan Casas
  • 268
  • 2
  • 13

1 Answers1

0

I updated the line that was giving me an issue now everything works :) ::

'''

const usersWithJobTypePreferenceList = await admin.firestore().collection("user").where("User job notifications preferences", "array-contains", jobType).get();

'''

Juan Casas
  • 268
  • 2
  • 13