10

Basically, I'm simply trying to print the notifications that my app has delivered, but doing something like:

UNUserNotificationCenter.current().getDeliveredNotifications { (notifications) in
    print(notifications)
}

just displays an empty array in the Xcode console, even when the notification center contains several delivered notifications. (print(notifications.count) returns 0)

I can use getPendingNotificationRequests to successfully grab the notifications that are scheduled yet undelivered, update them, and even remove them with removePendingNotificationRequests(withIdentifiers:). But any attempt to access/modify/remove anything that's been delivered does not work.

Am I missing something simple here? Did something change recently with the way iOS 10+ accesses the delivered notifications?

shim
  • 9,289
  • 12
  • 69
  • 108
Bryan Chapel
  • 346
  • 2
  • 12

2 Answers2

9

I did face the same problem with getDeliveredNotification, the array of notifications were always empty.

So, I realized that I was setting [UIApplication sharedApplication].applicationBadgeNumber to 0, what clear all remote notifications from notification center.

Now I set applicationBadgeNumber to 0 only after I get all pending notifications.

Thomás Pereira
  • 9,589
  • 2
  • 31
  • 34
  • In my case, I'm not setting `applicationBadgeNumber`; still getting empty array of delivered notifications. – shim Mar 16 '18 at 16:11
  • I'm sorry, maybe your push notification needs to update badge counting for you able to use `getDeliveredNotification`. Can you test it? – Thomás Pereira Mar 16 '18 at 16:14
  • What, you mean you're supposed to manually increment it? I schedule local notifications to fire in the future, and I'm checking this function after the notification has fired (I am trying to get `removeDeliveredNotifications(withIdentifiers:)` to work but the notification always stays in the notification center) – shim Mar 16 '18 at 16:16
  • Sorry, I didn't know You're talking about local notifications. In case of push notifications, you can send a badge count in the Push Notification's payload! Although you see if this thread https://stackoverflow.com/a/20780778/3052059 helps you. :) – Thomás Pereira Mar 16 '18 at 16:30
  • Well, that particular thread is pre-iOS 10, using deprecated APIs. Using the new `UNUserNotificationCenter` etc here. – shim Mar 16 '18 at 16:31
3

It was empty when I used it on a UNNotificationServiceExtension, it turned out that I needed to use a Semaphore in order to prevent the extension to return 0 results:

        let semaphore = DispatchSemaphore(value: 0)
        let center = UNUserNotificationCenter.current()
        center.getDeliveredNotifications { notifications in
            defer {
                semaphore.signal()
            }

            let relatedNotificationIdentifiers = notifications.filter { notification in
                notification.request.content.userInfo["callId"] as? String == callId
                    && notification.request.identifier != request.identifier
            }.map(\.request.identifier)

            // This call is async
            center.removeDeliveredNotifications(withIdentifiers: relatedNotificationIdentifiers)

            // ...so this call needs to be done with a slight delay because otherwise
            // it will be killed before it is done removing the notifications
            DispatchQueue.main.asyncAfter(deadline: .now() + 0.1) {
                contentHandler(bestAttemptContent)
            }
        }

        semaphore.wait()

Also, in the end it needed some wait to execute removeDeliveredNotifications which is async under the hood as well.

apns-collapse-id can help reducing incoming APNS messages.

Lucas van Dongen
  • 9,328
  • 7
  • 39
  • 60