I am trying to send push notifications to a user at a scheduled time. Say they set the date for an event and they want to be notified 30 minutes before, that is when I would like to send them a notification. I am using firebase as my backend and the project is built with expo.
I am curious how I would use expo's notification system if I am using firebase cloud messaging because it says I need separate permission from firebase (I already have the expo token for each user). I have looked into node cron/schedule and also react-native push notification but I am unsure which would be the best solution and where I would deploy the solution (such as running a cloud function).
I assume I need some type of function that takes the token, message body, title, and date and then sets it up to schedule it either to the server or locally. And then that function would be called when they press the button to receive the notification. They can also change the date of the event so it would need to switch the date if the user did that.
Any advice would be greatly appreciated as I have been researching this for days and still am unsure of the best approach.
One possible approach:
In your backend, schedule a cron job that runs every minute (or every 15 seconds) and checks against database which events have start time within next 30 mins.
Once you have the events, find out the users registered for those events and collect their user ids.
As you mention that you already have stored the tokens, so I assume that those tokens exist in some table against the user id. (e.g. mapping of user-id and tokens). Look up this table to fetch the tokens of those users.
Prepare the notification payload and call firebase messaging to send notification against the token. For example, at this point you can call the sendToDevice() function from Firebase SDK: firebase.messaging().sendToDevice(tokens, payload);
Now you can implement these steps in your backend (e.g. Nodejs) or you can deploy a cloud function for this and setup scheduling for this cloud function.
Let me know if you need any further help!
Related
Disclaimer: I'm finding my way and not sure how to ask the question. This is what I want to do:
I am getting data from twitter API in my app (this is working).
I then want to store that data (as an array), and serve it to whichever user is accessing the app (so that I don't need to query the API everytime, just poll every 10 mins).
What do I need to be able to do this? (external database? or can I just save to a file on the server in someway? or something else)
For ref I'm building with sveltekit, and deploying with vercel.
If you are using Twitter's API directly within your own app, every user of your app needs to query the API at least once to get some data. You cannot serve the results that are returned to one user to other users without having your own back-end server and handling this accordingly. However, you can save a copy of the data returned to each user to that user's localStorage so that specific user does not have to query the API every time.
You can save the data on the client's localStorage and save an expiry timestamp that allows you to query the API again after the timestamp has passed.
Here is a tutorial on how to use localStorage with SvelteKit
I am using the Google Cloud Firebase Realtime database to store messages. The messages are saved in
users/$userID/messages/$topic[0..n]/message[0..n]
I am using the official JS library AngularFire. I am listening on new messages via the following code:
this.observable = this.db.list(`users/${user.uid}/topics/${topic}/`).valueChanges();
I can now subscribe to the observable. Imagine the user has 1 million messages in a given topic. Whenever I add a new message, I receive the 1 million messages in the callback.
My question is, how much data is actually transferred behind the scenes if I modify or add a new message? I know the library keeps a local copy of the database.
On top, how do I find out which message got modified? Or do I need to figure this out myself?
If you have an existing listener, and a new message is added, only that new message is sent to that client. You can easily verify this for yourself by looking at the web socket traffic in the network tab of your browser's developer tools.
But I would recommend to use a query and limit to reduce the number of messages retrieved, as it seems unlikely any user will read 1 million messages, and it's wasteful to retrieve (much) more data than the user will see.
Based on the AngularFire documentation on querying lists, that should be something like:
this.db.list(`users/${user.uid}/topics/${topic}/`,
ref => ref.orderByKey().limitToLast(20)
).valueChanges()
Im working on a group chat function in my react native app and therefore every person using my app or better said the chat function will have a listener attached to a firestore collection which holds all my chat messages.
The feature I want to implement is a counter of people who are currently in the chat, so basicly I want to count the numbers of listeners that are currently listening to the firebase collection.
One idea I had was to increment a counter in firestore and retrieve it as soon as you start to listen to the document and if you go back one screen, decrement it. If you join the chat, counter goes up, if you leave counter goes down.
The problem with this method is that I dont handle any people loosing connection or closing the app while listening to the document. The increment would be done but the decrement not and therefore I would have a wrong number as my counter.
I wanted to ask therefore if anybody has any idea how to accomplish this task? Is there for example a possibility to execute a function on lost connection? I could imagine this beeing hard on the frontend so inside my app because as soon as I loose connection to the firestore... Im not able to retrieve or send and data anymore.
The feature I want to implement is a counter of people who are
currently in the chat
I think you are looking for the presence mechanism that can be set with the Realtime Database and to which you can connect Cloud Firestore by using Cloud Functions.
Have a look at:
Build presence in Cloud Firestore
How To Build a Presence System (Firebase blog)
Documentation about the onDisconnect() operation
I am currently using SocketIO and NodeJS to handle messages. However the problem is that when the user becomes offline there's no way that the other user will receive the message.
The solution I came up with was to store the message in the database.
But a new problem arise, when fetching the message and push notification.
If I do fetch for "n" minutes in the server when the app is in background/inactive. There will be a lot of request in the server, and I personally think that it is inefficient. and also it drains the battery.
What is the proper way how to handle fetching the messages from database or pushing notification in app without making too much request in "n" minutes and draining too much power?
You need to save the last sync time in the App. And whenever app comes from background/Inactive state. You need to call an API with this time. This API will give you all the messages and the Push notification which has comes after the last sync time. In this way, With one API call, you will be able to get all the messages and push notifications. I had used this approach to syncing my data in one of my app.
My suggestion is to implement a system of background jobs in the API, checking when there is a new notification to be launched, or with the notification already ready waiting to be launched in the queue. You can search for queue manager like Bull, Bee-Queue.
To launch push notification in the closed/inactive app, you can use a service like OneSignal or Firebase.
I implemented this a few weeks ago and did it this way.
API = Node.js, Bull Queue
App = React Native, OneSignal
Going back to this question if somebody stumbled upon this question.
The best way to handle offline messages regardless if you are using NodeJS/MongoDB, etc. is to store it on server's database. Then call an API that fetches the the messages which is equal to user's ID whenever the mobile app comes to foreground.
If your problem is that you needed notification and you are using
react-native-push-notifications / react-native-push-notification-ios
Then you should use the data notification to include the message on notification parameter on the server's side(Assuming that you are using Firebase Cloud Messaging). With this way you can directly save the message on the mobile's database.
I am building a messaging app that updates in realtime. So far I can log in with google and post a message and then that message displays on screen. however, if I log in via another google account (the app is hosted on heroku) and post a message as userB then userA won't see this message on their screen until they refresh the page. what is the best way to update all screens in real time so people can actually have a conversation in real time.
every message is posted and stored in the firebase. my only solution so far requires using the javascript setInterval method and pulling from the database every 3-5 seconds. this worked however it caused the app to become very slow and laggy and a poor experience. any pointers/tips are welcomed
You are using the Firebase and its one of the main feature is the real-time database. Firebase will automatically let you know if there is any change in your JSON database. You no need to send the request in interval basic.
You can refer Zero to App: Develop with Firebase - Google I/O 2016 It is also a messaging app demo by the Google Guys.
You can find the sample source code in Github to send and receive the message in real-time.
There are a lot of ways to do this. Generally, you will want to be notified by the server once a new message has come in and not have to ping the server every X seconds.
You could look at these:
socket.io and learn about websockets in general
A nice list of existing chat apps that utilize react
Google's cloud messaging, as you already use firebase, this might be the way to go for you here.
This should lead you in the right direction.