In one of the WWDC sessions I got code snippet for updating existing notifications. I don't think it works. Trying to update notification content.
First I request pending notifications from UNUserNotificationCenter
which always works. Then I am creating new request to update notification with existing unique identifier.
There's 1 new variable content: String
.
// Got at least one pending notification.
let triggerCopy = request!.trigger as! UNTimeIntervalNotificationTrigger
let interval = triggerCopy.timeInterval
let newTrigger = UNTimeIntervalNotificationTrigger(timeInterval: interval, repeats: true)
// Update notificaion conent.
let notificationContent = UNMutableNotificationContent()
notificationContent.title = NSString.localizedUserNotificationString(forKey: "Existing Title", arguments: nil)
notificationContent.body = content
let updateRequest = UNNotificationRequest(identifier: request!.identifier, content: notificationContent, trigger: newTrigger)
UNUserNotificationCenter.current().add(updateRequest, withCompletionHandler: { (error) in
if error != nil {
print("🚫 Couldn't update notification \(error!.localizedDescription)")
}
})
I am unable to catch error. The problem is that notification content body doesn't change.
I also tried to change trigger with different repeat interval. It doesn't work, notification is repeated with the same original interval it was created with.
Read Chris' answer, trying to go with first option.
let center = UNUserNotificationCenter.current()
center.getPendingNotificationRequests(completionHandler: { (requests) in
for request in requests {
if request.identifier == notificationIdentifier {
// Got at least one pending notification,
// update its content.
let notificationContent = UNMutableNotificationContent()
notificationContent.title = NSString.localizedUserNotificationString(forKey: "new title", arguments: nil)
notificationContent.body = "new body"
request.content = notificationContent // ⛔️ request.content is read only.
}
}
})
As you can see I can't modify original request.
Had go with second "delete first" option. Noticed that calling removePendingNotificationRequests
and schedule after, still gives me old notification version. I had to add 1 second delay between calling removePendingNotificationRequests
and center.add(request)
.
Marked Chris' answer as accepted but feel free to share better option.
The problem is that you're not modifying the existing notification, and instead adding a new notification with a duplicate identifier.
Let's tackle the duplicate issue first, the reason this duplicate notification doesn't show up is because the identifier isn't unique. From the docs:
(if identifier is not unique, notifications are not delivered).
You have two options. You can 1) modify the existing Notification, or 2) remove it and add the new one.
For 1, you already have the request, instead of pulling the trigger and identifier out of it, just replace request.content with your updated notificationContent.
For 2, you would just need to add a line before your Add:
UNUserNotificationCenter.current().removePendingNotificationRequests(withIdentifiers: [request!.identifier])
After I've requested to Allow Notifications:
I trigger a notification right from my viewDidLoad
but then also trigger another one with the same identifier. At the end the the updatedBody/updatedTitle show up.
import UIKit
import UserNotifications
class ViewController: UIViewController {
override func viewDidLoad() {
super.viewDidLoad()
let content = UNMutableNotificationContent()
content.title = "Scheduled Task"
content.body = "dumbBody"
content.badge = 1
content.sound = UNNotificationSound.default()
content.categoryIdentifier = "alertCategory"
UNUserNotificationCenter.current().delegate = self
//Setting time for notification trigger
let trigger = UNTimeIntervalNotificationTrigger.init(timeInterval: 3.0, repeats: false)
let request = UNNotificationRequest(identifier:"myIdentifier", content: content, trigger: trigger)
UNUserNotificationCenter.current().add(request, withCompletionHandler: {_ in print(" was registered")})
updateNotification()
}
My update function
func updateNotification(){
let center = UNUserNotificationCenter.current()
var request : UNNotificationRequest?
center.getPendingNotificationRequests{ notifications in
for notificationRequest in notifications{
if notificationRequest.identifier == "myIdentifier"{
request = notificationRequest
center.removeAllPendingNotificationRequests() // Removing this line or keeping it makes NO difference
}
}
let newTrigger = UNTimeIntervalNotificationTrigger.init(timeInterval: 5.0, repeats: false)
// Update notificaion conent.
let notificationContent = UNMutableNotificationContent()
notificationContent.title = "UpdatedTitle"
notificationContent.body = "updatedBody"
let updateRequest = UNNotificationRequest(identifier: request!.identifier, content: notificationContent, trigger: newTrigger)
UNUserNotificationCenter.current().add(updateRequest, withCompletionHandler: { (error) in
print("successfully updated")
if error != nil {
print("🚫 Couldn't update notification \(error!.localizedDescription)")
}
})
}
}
}
In the above snippet: Removing center.removeAllPendingNotificationRequests()
would make no difference. Still I would receive the updatedNotification.
For handling incoming notifications
extension ViewController:UNUserNotificationCenterDelegate{
func userNotificationCenter(_ center: UNUserNotificationCenter, didReceive response: UNNotificationResponse, withCompletionHandler completionHandler: @escaping () -> Void) {
print("original identifier was : \(response.notification.request.identifier)")
print("original body was : \(response.notification.request.content.body)")
print("Tapped in notification")
switch response.actionIdentifier {
default:
print("some action was clicked")
}
}
func userNotificationCenter(_ center: UNUserNotificationCenter, willPresent notification: UNNotification, withCompletionHandler completionHandler: @escaping (UNNotificationPresentationOptions) -> Void) {
print("Notification being triggered")
completionHandler( [.alert,.sound,.badge])
}
}
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