Search code examples
swiftapple-push-notifications

didRegisterForRemoteNotificationsWithDeviceToken does not get triggered - Push Notifications not working


I've spent hours now trying to figure out why didRegisterForRemoteNotificationsWithDeviceToken is not being called. It worked before. I didn't touch it in weeks. Now stopped working.

Here's my setup:

  1. Got didRegisterForRemoteNotificationsWithDeviceToken sitting in SceneDelegate
  2. Have declared SceneDelegate to be the UNUserNotificationCenterDelegate
  3. I'm setting UNUserNotificationCenter.current().delegate = self in func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions)
  4. I'm calling UNUserNotificationCenter.current().requestAuthorization { granted, error in... from one of the UIViewControllers in my App, specifically in viewDidLoad of that Controller - I get the Authorization Pop-up and when accepting I get a true back for granted
  5. Within UNUserNotificationCenter.current().getNotificationSettings { settings in ... a check for settings.authorizationStatus == .authorized returns true
  6. Push Notifications are added as a capability for the App in "Signing & Capabilities" and the entitlement file has been created. I've even already deleted and re-created the entitlement file - just to be sure...
  7. I've made sure to run the app on a real device (both via Xcode as well as via TestFlight) - so the delegate not being called is not related to the App running in the Simulator.
  8. Have checked if didFailToRegisterForRemoteNotificationsWithError gets called instead at least - but it doesn't.
  9. I have tried with a second physical device which I have never used for testing before.
  10. I've even checked the status of the APNS Sandbox here: https://developer.apple.com/system-status/
  11. The didReceive delegate gets called though if I'm sending a test notification to simulator via terminal command xcrun simctl push... and I'm getting the notification.
  12. Provisioning profile is managed by Xcode and the specified AppID is configured for Push Notifications. Certificates are set up in apple developer account.

Here's how I'm requesting Authorization from the user within viewDidLoad of one of my Apps UIViewControlles

UNUserNotificationCenter.current().requestAuthorization(options: [.alert, .badge, .sound]) { granted, error in
            DispatchQueue.main.async {
                if (granted) {
                    //self.processInitialAPNSRegistration()
                    UIApplication.shared.registerForRemoteNotifications()
                    UserDefaults.standard.set(true, forKey: "pushNotificationsEnabled")
                }
                print("permission granted?: \(granted)")
            }
        }

And here's the didRegisterForRemoteNotificationsWithDeviceToken delegate method sitting inside SceneDelegate. Note: I'm also setting UNUserNotificationCenter.current().delegate = self in scene willConnectTo and declaredSceneDelegateto implement theUNUserNotificationCenterDelegate` protocol.

func application(_ application: UIApplication, didRegisterForRemoteNotificationsWithDeviceToken deviceToken: Data) {
        let token = deviceToken.map { String(format:"%02.2hhx", $0) }.joined()
        print("didRegisterForRemoteNotificationsWithDeviceToken GOT CALLED - APNS TOKEN IS: \(token)")

        self.apiService.setAPNSToken(apnsToken: token, completion: {result in
            switch result {
            case .success(let resultString):
                DispatchQueue.main.async {
                    UserDefaults.standard.set(token, forKey: "apnsToken")
                    print(resultString, " TOKEN IS: \(token)")
                }
            case .failure(let error):
                print("AN ERROR OCCURED: \(error.localizedDescription)")
            }
        })

    }

Whatever I do, didRegisterForRemoteNotificationsWithDeviceToken is not getting triggered. I'm running out of ideas on what is going wrong.

Where is the error? How can I get didRegisterForRemoteNotificationsWithDeviceToken to execute again?


Solution

  • I think you have gone wrong in the second step didRegisterForRemoteNotificationsWithDeviceToken, didFailToRegisterForRemoteNotificationsWithError delegates are available in UIApplicationDelegate not in UNUserNotificationCenterDelegate

    Add UIApplicationDelegate to your SceneDelegate class and in willConnectTo function set the delegate as:

    UIApplication.shared.delegate = self
    

    I hope this works... let me know if you still see an issue.