I have function in Firebase Cloud Functions which is used to send notifications to specific users within my app and has as the notificationContent
the following cod
I had this same confusion and realized I misunderstood what collapseKey and tag are for.
collapseKey will limit the number of notifications a client receives while they're offline, tag is what will stack notifications together in the drawer.
So for a typical cloud function, it should look like this:
const notification = {
notification: {
'title': 'Interesting title',
'body': 'Hello, world'
},
'data': {
'whatever': whatever,
},
'android':{
'collapseKey': collapseKey,
'priority': 'high',
'notification': {
'tag': tag,
}
},
'token': fcmToken
};
admin.messaging().send(notification)
Note that the "tag" parameter sits inside of the android notification, not the top-level notification.
The easiest and most flexible solution is to extend the FirebaseMessagingService
and handle the notification yourself. But first instead of using notification
on your notificationContent
in your cloud function, you have to change that to data
so that you send a data message instead of a notification message. The difference is that the notification message will have an implicit collapse key (the package name of the app), while the data message won't have one. But the data message needs to be handled on the client or else it won't be displayed.
Here's a sample of what you'll need for your FirebaseMessagingService
:
public class MyFCMService extends FirebaseMessagingService {
@Override
public void onMessageReceived(RemoteMessage remoteMessage) {
if (remoteMessage.getNotification() != null) {
//this notification was sent from the Firebase console, because in our cloud function, we are using the DATA tag, not the notification tag
//so here we have to handle the notification that was sent from the console
...
} else if (remoteMessage.getData().get(KEY) != null) {
//this data message was sent from our cloud function
//KEY is one of the keys that you are using on the cloud function
//in your example, you are using the keys: title, body, icon, sound
//display the notification to the user
...
notificationManager.notify(TAG, ID, notificationBuilder.build());
//you have to use the same TAG and the same ID on each notification if you want your 2nd notification to simply update the text of the first one, instead of showing as a new notification
}
}
}
PS. When you send a notification from your cloud function (well if you use the data
tag, it's actually a data message, not a notification message), then this method will be called, regardless if the app is in the background or in the foreground. HOWEVER, when you send a notification from the firebase console, this method will be called ONLY if the app is in the foreground. If the app is in the background, the Firebase SDK will handle the notification and show it to the user. In some cases, it makes sense to show a notification only when the user is not running the app, for example if you want to advertise some new features of the app. In that case, what you can do is use a unique tag on the notification console (e.g. "display_in_foreground") and check that tag on the client. If you have set that to true, you can show the notification even to users that are currently running the app, or if it's false you can choose not to show the notification. This check will happen only if the app is in the foreground. If it's in the background, this won't be called at all and the SDK will handle to show the notification.
If you want to use more customizable and advanced notification features.
You should only send FCM with data
payload, and create notification at android client side.
Remember that if you send FCM with notification
payload or notification
+ data
payload, the notification will be created by android core system and BroadcastReceiver
's onReceive
method won't being called if your app is on background.
If you send FCM with data
payload, it will call onReceive
all the time, so you can produce custom notification manually at android client side. (most app uses latter method.)
I hope this link would be helpful.