In Android Nougat and above, push notifications for your app are grouped together automatically after the # 4th.
The problem in Android is that clicking on the bundle does not expand the push notification list, it opens the app.
I have a requirement to identify users that opened the app trough a push notification. For individual notifications, this is easy since I can explore intent extras. The problem with the bundle is that extras are null and intent looks exactly the same as if the user clicked on the launcher icon. I have no way to detect that navigation was done from a push notification :(
Just in case it's not clear: I'm not using push notifications groups explicitly, this is done automatically by Android. I have not set any group key to the notifications.
I'm using Firebase. I only build the push notification using NotificationCompat
when the app is on the foreground, this logic is not executed when the app is on the background or closed (OnMessageReceived
only runs with the app in foreground).
EDIT
I know that I could change the PN payload for the event OnMessageReceived
being executed even in the background or closed. I would like to avoid this since I have found a lot of people complaining about problems with PN not arriving in this case.
http://github.com/firebase/quickstart-android/issues/368
http://github.com/firebase/quickstart-android/issues/219
I want to detect a user tapping on a grouped PN even if the app didn't create it.
Scroll down and long-press the “Settings” widget, then place it on your home screen. You'll get a list of features that the Settings shortcut can access. Tap “Notification Log.” Tap the widget and scroll through your past notifications.
Solution 1: If you handle creation of the notifications, you can try following steps:
First of all, every time when you create new notification, you can group them by same key using setGroup(...)
:
val newMessageNotification1 = NotificationCompat.Builder(applicationContext, ...)
...
.setGroup("group_messages")
.build()
As you grouped notifications by same id ("group_messages"), now you can create summary notification with different intent:
val notifyIntent = Intent(this, ResultActivity::class.java).apply {
val notifyIntent = Intent(this, ResultActivity::class.java).apply {
flags = Intent.FLAG_ACTIVITY_NEW_TASK or Intent.FLAG_ACTIVITY_CLEAR_TASK
}
val notifyPendingIntent = PendingIntent.getActivity(
this, 0, notifyIntent, PendingIntent.FLAG_UPDATE_CURRENT
)
val summaryNotification = NotificationCompat.Builder(applicationContext, ...)
.setSmallIcon(android.R.drawable.ic_btn_speak_now)
.setContentIntent(notifyPendingIntent)
.setContentTitle("Grouped notification title")
.setContentText("Grouped notification text")
.setGroup("group_messages")
.setGroupSummary(true)
.build()
As last step, you can have if
check to make sure you have more than 1 notifications with same group, and then notify with group notification:
val notificationManager = applicationContext.getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager
val notificationManagerCompat = NotificationManagerCompat.from(applicationContext)
notificationManagerCompat.notify(ID, newMessageNotification1)
val amountOfNotificationsInSameGroup = notificationManager.activeNotifications
// Here we filter notifications that are under same group
.filter { it.notification.group == "group_messages" }
.size
if (amountOfNotificationsInSameGroup >= 2) {
// if we already have minimum of 2 notifications, we'll group them under summary notification
notificationManagerCompat.notify(SUMMARY_NOTIFICATION_ID, summaryNotification)
}
You can combine the code in your onMessageReceived
method. As you can see, now you can have custom intent to handle grouped notifications. You can read more about grouped notifications here.
Solution 2: If you don't want to handle creation of notifications and still want to know if the notifications are grouped, you can try following solution:
NotificationManager
has getActiveNotifications() function which will return notifications that have been posted by the calling app and hasn't been dismissed by the user yet. When you click grouped notifications in Android, notifications won't be dismissed. Therefore, you can check size of active notifications in your launcher activity to detect if the app was launched by clicking to grouped/bundle notifications:
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
val notificationManager =
applicationContext.getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager
if (notificationManager.activeNotifications.size >= 4) {
// Notifications are grouped
// Put your logic here
// Do not forget to clear notifications
NotificationManagerCompat.from(this).cancelAll()
}
}
}
Personally, I'd prefer first solution, but according to the issues you have posted, you can use second option as well but note that you won't be able to differentiate if the app was launched from launcher or by clicking grouped notification.
With second solution there might be following questions:
Q1: How can I differentiate normal notification click from group one in same activity?
- Simply you can define click_action
and forward normal notification clicks to different activity. Check the docs.
If you want to replace previous notifications, you can also define same tag
in your notification JSON on backend side. In this way, notifications won't be bundled because newer notifications will replace the old one with same tag. Check the docs.
I hope my answer helps.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With