Scenerio
So I recently was working on an internal app for the company where we could silent certain push notifications depending on the the information they had. In the backend I wrote few Firebase cloud functions to send the notifications.
Problem
The problem that I was facing was, I would still recieve the Push Notification if the app was in background but it would worked fine when the app was in Foreground.
I was handling the generation of Notification in a subclass of FirebaseMessagingService
. So in the onMessageReceived
method we would check for the payload and create the notification if it was not silenced buy the user in the app. And on the backend we were using standard Notification messages
message type to send the Push Notification.
The payload in the cloud function looked something like this:
1
2
3
4
5
6
const payload = {
notification: {
title: 'Title',
body: `Body of Notification.`,
},
};
And this is how I was handling the push notification on the Android side.
1
2
3
4
5
6
7
8
9
10
override fun onMessageReceived(remoteMessage: RemoteMessage) {
if (remoteMessage.data.isNotEmpty()) {
Log.d(TAG, "Message data payload: ${remoteMessage.data}")
handleNow()
}
remoteMessage.notification?.let {
sendNotification(it.title ?: "Something went down.", it.body ?: "Check your app to see the status.")
}
}
Old solution was to override handleIntent
method, but from verion 11 or 12 it seems like they have made than method final so we cannot override it.
Solution
Seems like there are 2 message types Notification messages
and Data messages
. As you saw above we were using Notification messages
for the payload. But instead we needed to use Data messages
for the payload. More about how to handle them can be found here. So now my payload for android looks like this:
1
2
3
4
5
6
const payload = {
data: {
title: 'Title',
body: `Body of Notification.`,
},
};
And my onMessageReceived
looks like this:
1
2
3
4
5
6
7
override fun onMessageReceived(remoteMessage: RemoteMessage) {
if(remoteMessage.toIntent().hasExtra("title") && remoteMessage.toIntent().hasExtra("body")) {
val title = remoteMessage.toIntent().getStringExtra("title")
val body = remoteMessage.toIntent().getStringExtra("body")
sendNotification(title ?: "Something went down.", body ?: "Check your app to see the status.")
}
}
This way now I can handle background and foreground notification the same way at a single place.