Search code examples
swiftswift3ios10unnotificationrequest

Unique Identifier for scheduling notifications, Swift 3 iOS 10


I am scheduling notifications with Unique Identifiers so I don't have to make a new String for each notification. This all works well for scheduling but the problem lies in trying to cancel them.

This is my code for scheduling notifications...

let notifIdentifier = TaskManager.notification2.userInfo.description as String!
let trigger = UNCalendarNotificationTrigger(dateMatching: components , repeats: true)
let request = UNNotificationRequest(identifier: notifIdentifier! , content: TaskManager.notification2, trigger: trigger)
UNUserNotificationCenter.current().add(request, withCompletionHandler: nil)

This is the code for cancelling notifications ...

// Deletion of Cells ...

func tableView(_ tableView: UITableView, commit editingStyle: UITableViewCellEditingStyle, forRowAt indexPath: IndexPath) {
    
    let managedObject: NSManagedObject = frc.object(at: indexPath) as! NSManagedObject
    context.delete(managedObject)
    if tableView == TaskTableViews {
    let itemController = TaskManager()
    let nItem: List = frc.object(at: indexPath) as! List
    itemController.nItem = nItem
    UNUserNotificationCenter.current().removePendingNotificationRequests(withIdentifiers: [itemController.notifIdentifier!] )

When I try to cancel them, they are very hit and miss. I have tested the code by changing the identifier to a regular String and everything works as it should so its definitely the unique identifier.

Any thoughts/ suggestions on creating a unique ID for every new task/notification?


Solution

  • Scheduling notifications

    @IBAction func scheduleNotification(_ sender: AnyObject) {
    
        let uuid = UUID().uuidString
    
    
        let content = UNMutableNotificationContent()
        content.title = NSString.localizedUserNotificationString(forKey: "Example", arguments: nil)
        content.sound = UNNotificationSound.default()
        //...
    
        var dateComponents = Calendar.current.dateComponents([.year, .month, .day, .hour, .minute], from: self.datePicker.date)
        dateComponents.second = 0
    
        let trigger = UNCalendarNotificationTrigger(dateMatching: dateComponents, repeats: false)
    
        let request = UNNotificationRequest(identifier: uuid, content: content, trigger: trigger)
    
        UNUserNotificationCenter.current().add(request) { (error) in
    
            if let errorPerforms = error {
             print(errorPerforms.localizedDescription)
            } else {
             print("Success")
            }
        }
    
    
        let managedObject = ManagedObject(context: self.managedObjectContext!)
        managedObject.setValue(uuid, forKey: "uuid")
        //...
    
        do {
         try self.managedObjectContext.save()
            self.dimiss()
        } catch {}
    }
    

    Delete notifications from the indexPath.

     // Override to support editing the table view.
    override func tableView(_ tableView: UITableView, commit editingStyle: UITableViewCellEditingStyle, forRowAt indexPath: IndexPath) {
    
        switch editingStyle {
        case .delete:
    
            let managedObject = self.fetchedResultsController.object(at: indexPath)
            self.managedObjectContext.delete(managedObject)
    
            let center = UNUserNotificationCenter.current()
            center.removeDeliveredNotifications(withIdentifiers: [managedObject.uuid!])
            center.removePendingNotificationRequests(withIdentifiers: [managedObject.uuid!])
    
            do {
             try self.managedObjectContext.save()
                self.tableView.reloadData()
            } catch {}
    
        default:
            break
        }
    
    }
    

    This works well! When you're using the NSFetchedResultsControllerDelegate protocol methods. Hope it helps