iOS Push Notifications Custom Sound - ios

I have been breaking my head for almost a week, to create my own sound when I generate push notifications in iOS. Version is 13.4. Problem is all push notifications are silent, even though all settings in iPhone is correct. Below is my AppDelegate.swift file. I don't know where and how to make a change so that I can generate my own sound when I receive push notifications. Please can you let me know where is the mistake? Also, I am new to iOS. So any help regarding this would be highly appreciated.
import UIKit
import Firebase
import UserNotifications
import FirebaseMessaging
import FirebaseInstanceID
#UIApplicationMain
class AppDelegate: UIResponder, UIApplicationDelegate, MessagingDelegate, UNUserNotificationCenterDelegate {
var window: UIWindow?
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
// Override point for customization after application launch.
if #available(iOS 10.0, *) {
// For iOS 10 display notification (sent via APNS)
UNUserNotificationCenter.current().delegate = (self as UNUserNotificationCenterDelegate)
UNUserNotificationCenter.current().requestAuthorization(
options: [.alert, .badge, .sound],
completionHandler: {_, _ in })
Messaging.messaging().delegate = (self as MessagingDelegate)
} else {
let settings: UIUserNotificationSettings =
UIUserNotificationSettings(types: [UIUserNotificationType.alert, UIUserNotificationType.badge, UIUserNotificationType.sound], categories: nil)
UIApplication.shared.registerUserNotificationSettings(settings)
}
UIApplication.shared.registerForRemoteNotifications()
UIApplication.shared.applicationIconBadgeNumber = 0
FirebaseApp.configure()
NSSetUncaughtExceptionHandler { exception in
print(exception)
print(exception.callStackSymbols)
}
return true
}
// The callback to handle data message received via FCM for devices running iOS 10 or above.
func applicationReceivedRemoteMessage(_ remoteMessage: MessagingRemoteMessage) {
print("Remote message is ", remoteMessage.appData)
}
func applicationWillResignActive(_ application: UIApplication) {
// Sent when the application is about to move from active to inactive state. This can occur for certain types of temporary interruptions (such as an incoming phone call or SMS message) or when the user quits the application and it begins the transition to the background state.
// Use this method to pause ongoing tasks, disable timers, and invalidate graphics rendering callbacks. Games should use this method to pause the game.
}
func applicationDidEnterBackground(_ application: UIApplication) {
// Use this method to release shared resources, save user data, invalidate timers, and store enough application state information to restore your application to its current state in case it is terminated later.
// If your application supports background execution, this method is called instead of applicationWillTerminate: when the user quits.
}
func applicationWillEnterForeground(_ application: UIApplication) {
// Called as part of the transition from the background to the active state; here you can undo many of the changes made on entering the background.
}
func applicationDidBecomeActive(_ application: UIApplication) {
// Restart any tasks that were paused (or not yet started) while the application was inactive. If the application was previously in the background, optionally refresh the user interface.
}
func applicationWillTerminate(_ application: UIApplication) {
// Called when the application is about to terminate. Save data if appropriate. See also applicationDidEnterBackground:.
}
func application(_ application: UIApplication, didFailToRegisterForRemoteNotificationsWithError error: Error) {
print("i am not available in simulator \(error)")
}
func messaging(_ messaging: Messaging, didReceiveRegistrationToken fcmToken: String) {
let token = Messaging.messaging().fcmToken
regToken=token!
}
func application(_ application: UIApplication, didReceiveRemoteNotification userInfo: [AnyHashable : Any]) {
print("didReceiveRemoteNotification", userInfo)
let content = UNMutableNotificationContent()
if let title = userInfo["title"]
{
content.title = title as! String
}
if let title = userInfo["text"]
{
content.body = title as! String
}
content.userInfo = userInfo
//content.sound = UNNotificationSound.default
content.sound = UNNotificationSound(named: UNNotificationSoundName(rawValue: "tornado_alarm.caf"))
let trigger = UNTimeIntervalNotificationTrigger.init(timeInterval: 0.5, repeats: false)
let request = UNNotificationRequest(identifier:"rig", content: content, trigger: trigger)
UNUserNotificationCenter.current().delegate = (self as UNUserNotificationCenterDelegate)
UNUserNotificationCenter.current().add(request) { (error) in
if let getError = error {
print("didReceiveRemoteNotification error is ", getError.localizedDescription)
}
}
}
func userNotificationCenter(_ center: UNUserNotificationCenter, willPresent notification: UNNotification, withCompletionHandler completionHandler: #escaping (UNNotificationPresentationOptions) -> Void)
{
print("willPresent", notification.request.content.userInfo)
if notification.request.identifier == "rig"{
completionHandler( [.alert,.sound,.badge])
}else{
completionHandler([.alert, .badge, .sound])
}
}
func userNotificationCenter(center: UNUserNotificationCenter, willPresentNotification notification: UNNotification, withCompletionHandler completionHandler: #escaping (UNNotificationPresentationOptions) -> Void)
{
//Handle the notification
completionHandler(
[UNNotificationPresentationOptions.alert,
UNNotificationPresentationOptions.sound,
UNNotificationPresentationOptions.badge])
}
func application(_ application: UIApplication, didRegisterForRemoteNotificationsWithDeviceToken deviceToken: Data) {
Messaging.messaging().apnsToken = deviceToken
let deviceTokenString = deviceToken.reduce("", {$0 + String(format: "%02X", $1)})
print("Device Token Is ", deviceTokenString)
}
func userNotificationCenter(_ center: UNUserNotificationCenter, didReceive response: UNNotificationResponse, withCompletionHandler completionHandler: #escaping () -> Void) {
}
}

Related

Firebase cloud messaging not working on IOS at all for some reason

I want to implement Firebase Messaging in an iOS app, and I'm running into a vexing issue.
I followed these two videos to the letter, and I'm not receiving any notifications (either popups or console indications of a received notification).
Here is my AppDelegate.swift:
//
// AppDelegate.swift
//
import UIKit
import Firebase
import UserNotifications
import FirebaseMessaging
#UIApplicationMain
class AppDelegate: UIResponder, UIApplicationDelegate {
var window: UIWindow?
var orientationLock = UIInterfaceOrientationMask.all
let gcmMessageIDKey = "gcm.message_id"
func application(_ application: UIApplication, supportedInterfaceOrientationsFor window: UIWindow?) -> UIInterfaceOrientationMask {
return self.orientationLock
}
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
// Override point for customization after application launch.
FirebaseApp.configure()
if #available(iOS 10.0, *) {
// For iOS 10 display notification (sent via APNS)
UNUserNotificationCenter.current().delegate = self
let authOptions: UNAuthorizationOptions = [.alert, .badge, .sound]
UNUserNotificationCenter.current().requestAuthorization(
options: authOptions,
completionHandler: {_, _ in })
} else {
let settings: UIUserNotificationSettings =
UIUserNotificationSettings(types: [.alert, .badge, .sound], categories: nil)
application.registerUserNotificationSettings(settings)
}
application.registerForRemoteNotifications()
Messaging.messaging().delegate = self
return true
}
func applicationWillResignActive(_ application: UIApplication) {
// Sent when the application is about to move from active to inactive state. This can occur for certain types of temporary interruptions (such as an incoming phone call or SMS message) or when the user quits the application and it begins the transition to the background state.
// Use this method to pause ongoing tasks, disable timers, and invalidate graphics rendering callbacks. Games should use this method to pause the game.
}
func applicationDidEnterBackground(_ application: UIApplication) {
// Use this method to release shared resources, save user data, invalidate timers, and store enough application state information to restore your application to its current state in case it is terminated later.
// If your application supports background execution, this method is called instead of applicationWillTerminate: when the user quits.
}
func applicationWillEnterForeground(_ application: UIApplication) {
// Called as part of the transition from the background to the active state; here you can undo many of the changes made on entering the background.
}
func applicationDidBecomeActive(_ application: UIApplication) {
// Restart any tasks that were paused (or not yet started) while the application was inactive. If the application was previously in the background, optionally refresh the user interface.
}
func applicationWillTerminate(_ application: UIApplication) {
// Called when the application is about to terminate. Save data if appropriate. See also applicationDidEnterBackground:.
}
}
extension AppDelegate : MessagingDelegate{
func messaging(_ messaging: Messaging, didReceiveRegistrationToken fcmToken: String) {
print("Firebase registration token: \(fcmToken)")
let dataDict:[String: String] = ["token": fcmToken]
NotificationCenter.default.post(name: Notification.Name("FCMToken"), object: nil, userInfo: dataDict)
// TODO: If necessary send token to application server.
// Note: This callback is fired at each app startup and whenever a new token is generated.
}
func messaging(_ messaging: Messaging, didReceive remoteMessage: MessagingRemoteMessage) {
print("Message data: \(remoteMessage.appData)")
}
}
#available(iOS 10, *)
extension AppDelegate : UNUserNotificationCenterDelegate {
// Receive displayed notifications for iOS 10 devices.
func userNotificationCenter(_ center: UNUserNotificationCenter,
willPresent notification: UNNotification,
withCompletionHandler completionHandler: #escaping (UNNotificationPresentationOptions) -> Void) {
let userInfo = notification.request.content.userInfo
// With swizzling disabled you must let Messaging know about the message, for Analytics
// Messaging.messaging().appDidReceiveMessage(userInfo)
// Print message ID.
if let messageID = userInfo[gcmMessageIDKey] {
print("Message ID: \(messageID)")
}
// Print full message.
print(userInfo)
// Change this to your preferred presentation option
completionHandler([])
}
func userNotificationCenter(_ center: UNUserNotificationCenter,
didReceive response: UNNotificationResponse,
withCompletionHandler completionHandler: #escaping () -> Void) {
let userInfo = response.notification.request.content.userInfo
// Print message ID.
if let messageID = userInfo[gcmMessageIDKey] {
print("Message ID: \(messageID)")
}
// Print full message.
print(userInfo)
completionHandler()
}
}
I've added the APNS key to Firebase, verified the entitlements, etc.
The funny thing is this used to work, but doesn't.
Any pointers would be highly appreciated!

FCM push for iOS callback not called

I have a problem with FCM push notifications.
func userNotificationCenter(_ center: UNUserNotificationCenter, didReceive response: UNNotificationResponse, withCompletionHandler completionHandler: #escaping () -> Swift.Void)
and
func userNotificationCenter(_ center: UNUserNotificationCenter, willPresent notification: UNNotification, withCompletionHandler completionHandler: #escaping (UNNotificationPresentationOptions) -> Swift.Void)
are not called when I receive a push. The notification is generated in my iPhone.
func application(_ application: UIApplication, didReceiveRemoteNotification userInfo: [AnyHashable: Any], fetchCompletionHandler completionHandler: #escaping (UIBackgroundFetchResult) -> Void)
is called instead but I don't understand why because it's deprecated.
The content of my notification:
{
"to": "FCM Token",
"priority": "high",
"content_available": true,
"notification": {
"sound": "default",
"title": "Test",
"body": "Test",
"description": "Test"
},
"data": {
"id": 123456,
"status": "11",
}
}
In my AppDelegate.swift:
import UIKit
import CoreData
import Firebase
import Fabric
import Crashlytics
import GoogleMaps
import GooglePlaces
import FBSDKLoginKit
import GoogleSignIn
import NotificationBannerSwift
import UserNotifications
#UIApplicationMain
class AppDelegate: UIResponder, UIApplicationDelegate {
var window: UIWindow?
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
// Override point for customization after application launch.
FirebaseApp.configure()
if #available(iOS 10.0, *) {
// For iOS 10 display notification (sent via APNS)
UNUserNotificationCenter.current().delegate = self
let authOptions: UNAuthorizationOptions = [.alert, .badge, .sound]
UNUserNotificationCenter.current().requestAuthorization(
options: authOptions,
completionHandler: {_, _ in })
} else {
let settings: UIUserNotificationSettings =
UIUserNotificationSettings(types: [.alert, .badge, .sound], categories: nil)
application.registerUserNotificationSettings(settings)
}
application.registerForRemoteNotifications()
Messaging.messaging().delegate = self
Messaging.messaging().shouldEstablishDirectChannel = true
return ApplicationDelegate.shared.application(application, didFinishLaunchingWithOptions: launchOptions)
}
func applicationWillResignActive(_ application: UIApplication) {
pprint(" - applicationWillResignActive - ")
// Sent when the application is about to move from active to inactive state. This can occur for certain types of temporary interruptions (such as an incoming phone call or SMS message) or when the user quits the application and it begins the transition to the background state.
// Use this method to pause ongoing tasks, disable timers, and invalidate graphics rendering callbacks. Games should use this method to pause the game.
AppEvents.activateApp()
}
func applicationDidEnterBackground(_ application: UIApplication) {
pprint(" - applicationDidEnterBackground - ")
// Use this method to release shared resources, save user data, invalidate timers, and store enough application state information to restore your application to its current state in case it is terminated later.
// If your application supports background execution, this method is called instead of applicationWillTerminate: when the user quits.
}
func applicationWillEnterForeground(_ application: UIApplication) {
pprint(" - applicationWillEnterForeground - ")
// Called as part of the transition from the background to the active state; here you can undo many of the changes made on entering the background.
}
func applicationDidBecomeActive(_ application: UIApplication) {
pprint(" - applicationDidBecomeActive - ")
// Restart any tasks that were paused (or not yet started) while the application was inactive. If the application was previously in the background, optionally refresh the user interface.
}
func applicationWillTerminate(_ application: UIApplication) {
pprint(" - applicationWillTerminate - ")
// Called when the application is about to terminate. Save data if appropriate. See also applicationDidEnterBackground:.
}
func application(_ application: UIApplication, didFailToRegisterForRemoteNotificationsWithError error: Error) {
print("Unable to register for remote notifications: \(error.localizedDescription)")
}
private func application(application: UIApplication, didRegisterForRemoteNotificationsWithDeviceToken deviceToken: NSData) {
pprint("apns token: ", deviceToken)
Messaging.messaging().apnsToken = deviceToken as Data
}
func application(_ application: UIApplication, didReceiveRemoteNotification userInfo: [AnyHashable: Any], fetchCompletionHandler completionHandler: #escaping (UIBackgroundFetchResult) -> Void) {
// If you are receiving a notification message while your app is in the background,
// this callback will not be fired till the user taps on the notification launching the application.
// TODO: Handle data of notification
// With swizzling disabled you must let Messaging know about the message, for Analytics
Messaging.messaging().appDidReceiveMessage(userInfo)
// Print message ID.
print(" ")
print("-- New message classique --")
print("Notification received : \(userInfo)")
print(" ")
// Print full message.
print(userInfo)
completionHandler(.noData)
}
// MARK: - UNUserNotificationCenterDelegate methods
extension AppDelegate: UNUserNotificationCenterDelegate {
// FOREGROUND: The method will be called on the delegate only if the application is in the foreground. If the method is not implemented or the handler is not called in a timely manner then the notification will not be presented. The application can choose to have the notification presented as a sound, badge, alert and/or in the notification list. This decision should be based on whether the information in the notification is otherwise visible to the user.
func userNotificationCenter(_ center: UNUserNotificationCenter, willPresent notification: UNNotification, withCompletionHandler completionHandler: #escaping (UNNotificationPresentationOptions) -> Swift.Void) {
DispatchQueue.main.async {
// print("will present: ", notification)
// Messaging.messaging().appDidReceiveMessage(notification.request.content.userInfo)
// completionHandler(.alert)
let userInfo = notification.request.content.userInfo
// With swizzling disabled you must let Messaging know about the message, for Analytics
Messaging.messaging().appDidReceiveMessage(userInfo)
// Print message ID.
print(" ")
print("Notification received : \(notification)")
print("-- New message from Notification ios10 only --")
print(" ")
guard
let aps = userInfo[AnyHashable("aps")] as? NSDictionary,
let alert = aps["alert"] as? NSDictionary,
let body = alert["body"] as? String,
let title = alert["title"] as? String
else {
// handle any error here
return
}
print("Title: \(title) \nBody:\(body)")
let banner = NotificationBanner(title: title, subtitle: body, style: .success)
banner.show()
// Change this to your preferred presentation option
//completionHandler([])
}
}
// BACKGROUND: The method will be called on the delegate when the user responded to the notification by opening the application, dismissing the notification or choosing a UNNotificationAction. The delegate must be set before the application returns from applicationDidFinishLaunching:.
func userNotificationCenter(_ center: UNUserNotificationCenter, didReceive response: UNNotificationResponse, withCompletionHandler completionHandler: #escaping () -> Swift.Void) {
DispatchQueue.main.async {
print("didReceive")
let userInfo = response.notification.request.content.userInfo
// Print message ID.
if let messageID = userInfo["gcmMessageIDKey"] {
print("Message ID: \(messageID)")
}
print(userInfo)
if let body = userInfo["body"] as? String {
print("inbody")
NotificationCenter.default.post(name: Notification.Name("userInfo"), object: body)
}
//Push().handlePush(info: userInfo)
// Print full message.
print(userInfo)
Messaging.messaging().appDidReceiveMessage(response.notification.request.content.userInfo)
completionHandler()
}
}
}
// MARK: - MessagingDelegate methods
extension AppDelegate: MessagingDelegate {
func messaging(_ messaging: Messaging, didReceiveRegistrationToken fcmToken: String) {
//log.info("FCM registration token received = \(fcmToken)")
print("FCM registration token received = \(fcmToken)")
let dataDict:[String: String] = ["token": fcmToken]
NotificationCenter.default.post(name: Notification.Name("FCMToken"), object: nil, userInfo: dataDict)
// TODO: If necessary send token to application server.
// Note: This callback is fired at each app startup and whenever a new token is generated.
}
func messaging(_ messaging: Messaging, didReceive remoteMessage: MessagingRemoteMessage) {
//log.info("didReceive message = \(remoteMessage)")
print("didReceive message = \(remoteMessage)")
}
func applicationReceivedRemoteMessage(_ remoteMessage: MessagingRemoteMessage) {
print(" - - - FIR Remote message - - - ")
print("%#", remoteMessage.appData)
//Push().handlePush(info: remoteMessage.appData)
}
}
In my Info.plist I have FirebaseAppdelegateProxyEnable set to NO
In capabilities, I have Push Notifications enabled and Remote Notifications are enabled too in Background Mode.
I'm using Xcode 11.1. I have converted my project to Swift 5 (it was created with Swift 3), I have changed the build system to the new one.
I have two targets with this project I don't know if it can be related to my issue.
I try with an empty new project with the same AppDelegate.swift, same bundle identifier and it works.
try this
func userNotificationCenter(_ center: UNUserNotificationCenter, didReceive response: UNNotificationResponse, withCompletionHandler completionHandler: #escaping () -> Void) {
// put your code here
}
func userNotificationCenter(_ center: UNUserNotificationCenter, willPresent notification: UNNotification, withCompletionHandler completionHandler: #escaping (UNNotificationPresentationOptions) -> Void) {
// put your code here
}

How to call did receive response method in ios<10 in swift?

I'm using this code when user clicks on notification.
it works perfectly in ios 10 and above but don't know how to make it workable for ios < 10.
i have searched for lot of tutorials and articles but didn't get anything out of it please help me in resolving this issue.
import UIKit
import UserNotifications
#UIApplicationMain
class AppDelegate: UIResponder, UIApplicationDelegate {
var window: UIWindow?
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
// Override point for customization after application launch.
if #available(iOS 10.0, *) {
print("we are here 10")
// For iOS 10 display notification (sent via APNS)
UNUserNotificationCenter.current().delegate = self
let authOptions: UNAuthorizationOptions = [.alert, .badge, .sound]
UNUserNotificationCenter.current().requestAuthorization(
options: authOptions,
completionHandler: {_, _ in })
} else {
print("we are here 9")
let settings: UIUserNotificationSettings =
UIUserNotificationSettings(types: [.alert, .badge, .sound], categories: nil)
application.registerUserNotificationSettings(settings)
}
application.registerForRemoteNotifications()
return true
}
func applicationWillResignActive(_ application: UIApplication) {
// Sent when the application is about to move from active to inactive state. This can occur for certain types of temporary interruptions (such as an incoming phone call or SMS message) or when the user quits the application and it begins the transition to the background state.
// Use this method to pause ongoing tasks, disable timers, and invalidate graphics rendering callbacks. Games should use this method to pause the game.
}
func applicationDidEnterBackground(_ application: UIApplication) {
// Use this method to release shared resources, save user data, invalidate timers, and store enough application state information to restore your application to its current state in case it is terminated later.
// If your application supports background execution, this method is called instead of applicationWillTerminate: when the user quits.
}
func applicationWillEnterForeground(_ application: UIApplication) {
// Called as part of the transition from the background to the active state; here you can undo many of the changes made on entering the background.
}
func applicationDidBecomeActive(_ application: UIApplication) {
// Restart any tasks that were paused (or not yet started) while the application was inactive. If the application was previously in the background, optionally refresh the user interface.
}
func applicationWillTerminate(_ application: UIApplication) {
// Called when the application is about to terminate. Save data if appropriate. See also applicationDidEnterBackground:.
}
}
// [START ios_10_message_handling]
#available(iOS 10, *)
extension AppDelegate : UNUserNotificationCenterDelegate {
// Receive displayed notifications for iOS 10 devices.
func userNotificationCenter(_ center: UNUserNotificationCenter,
willPresent notification: UNNotification,
withCompletionHandler completionHandler: #escaping (UNNotificationPresentationOptions) -> Void) {
let userInfo = notification.request.content.userInfo
// With swizzling disabled you must let Messaging know about the message, for Analytics
// Messaging.messaging().appDidReceiveMessage(userInfo)
// Print message ID.
// Print full message.
print(userInfo)
// Change this to your preferred presentation option
completionHandler([])
}
func userNotificationCenter(_ center: UNUserNotificationCenter,
didReceive response: UNNotificationResponse,
withCompletionHandler completionHandler: #escaping () -> Void) {
let userInfo = response.notification.request.content.userInfo
// Print message ID.
print("we are here")
// Print full message.
print(userInfo["customParameterKey_from"] as! String)
//show user notification
completionHandler()
}
}
Try this
- (void)application:(UIApplication *)application didReceiveLocalNotification:(UILocalNotification *)notification
{
}
for ios 8,9 response find on
func application(_ application: UIApplication, didReceiveRemoteNotification userInfo: [AnyHashable: Any], fetchCompletionHandler completionHandler: #escaping (UIBackgroundFetchResult) -> Void) {
//do something with userinfo
}

iOS Firebase messaging not receiving

I've been breaking my head on this today and yesterday, for some reason my iOS application is not receiving any firebase notifications. For as far as I know I have done everything as it should be.
I have checked the certifications in my Apple developer account and everything is set up correctly (see screenshots).
I am testing on a physical device
Firebase is set up properly and the logs show it connected to firebase correctly
I have enabled push notifications, background fetch and remote notifications in the capabilities tab of the project
I have added my APN key from my Apple console to Firebase
When sending a notification through the Firebase console to a topic or to all iOS apps nothing happens. I have the same app running on android smoothly which is receiving all notifications when targeted.
AppDelegate.swift
//
// AppDelegate.swift
// CoyoteBreda
//
// Created by Milan van Dijck on 28/02/2017.
// Copyright © 2017 Miscoria web development. All rights reserved.
//
import UIKit
import GoogleMaps
import Firebase
import FirebaseMessaging
import UserNotifications
#UIApplicationMain
class AppDelegate: UIResponder, UIApplicationDelegate {
var window: UIWindow?
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
// Override point for customization after application launch.
GMSServices.provideAPIKey("AIzaSyB2JNmY2D6q7lYKmJmyeeDXdk-ILEM4q1Q")
UIApplication.shared.setMinimumBackgroundFetchInterval(UIApplicationBackgroundFetchIntervalMinimum)
//Initialize firebase
//FIRApp.configure()
do {
Network.reachability = try Reachability(hostname: "www.google.com")
do {
try Network.reachability?.start()
} catch let error as Network.Error {
print(error)
} catch {
print(error)
}
} catch {
print(error)
}
// Add observer for InstanceID token refresh callback.
NotificationCenter.default.addObserver(self, selector: #selector(self.tokenRefreshNotification),
name: NSNotification.Name.firInstanceIDTokenRefresh, object: nil)
return true
}
func application(_ application: UIApplication, willFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey : Any]? = nil) -> Bool {
// -----------------------
// FIREBASE MESSAGING
// -----------------------
FIRApp.configure()
application.registerForRemoteNotifications()
requestNotificationAuthorization(application: application)
if let userInfo = launchOptions?[UIApplicationLaunchOptionsKey.remoteNotification] {
NSLog("[RemoteNotification] applicationState: \(applicationStateString) didFinishLaunchingWithOptions for iOS9: \(userInfo)")
//TODO: Handle background notification
}
application.registerForRemoteNotifications()
return true;
}
func tokenRefreshNotification(notification: NSNotification)
{
if let refreshedToken = FIRInstanceID.instanceID().token()
{
print("InstanceID token: \(refreshedToken)")
}
// Connect to FCM since connection may have failed when attempted before having a token.
connectToFcm()
}
func application(application: UIApplication, didRegisterForRemoteNotificationsWithDeviceToken deviceToken: NSData)
{
FIRInstanceID.instanceID().setAPNSToken(deviceToken as Data, type: FIRInstanceIDAPNSTokenType.sandbox)
FIRInstanceID.instanceID().setAPNSToken(deviceToken as Data, type: FIRInstanceIDAPNSTokenType.prod)
}
func connectToFcm()
{
FIRMessaging.messaging().connect { (error) in
if (error != nil)
{
print("[Unable to connect with FCM. \(String(describing: error))]")
}
else
{
print("[Connected to FCM.]")
}
}
}
var applicationStateString: String {
if UIApplication.shared.applicationState == .active {
return "active"
} else if UIApplication.shared.applicationState == .background {
return "background"
}else {
return "inactive"
}
}
func requestNotificationAuthorization(application: UIApplication) {
if #available(iOS 10.0, *) {
UNUserNotificationCenter.current().delegate = self
let authOptions: UNAuthorizationOptions = [.alert, .badge, .sound]
UNUserNotificationCenter.current().requestAuthorization(options: authOptions, completionHandler: {_, _ in })
} else {
let settings: UIUserNotificationSettings = UIUserNotificationSettings(types: [.alert, .badge, .sound], categories: nil)
application.registerUserNotificationSettings(settings)
}
}
func application(_ application: UIApplication, didRegisterForRemoteNotificationsWithDeviceToken deviceToken: Data) {
print("[REGISTERING FOR TOPICS]")
FIRMessaging.messaging().subscribe(toTopic: "/topics/activiteit")
FIRMessaging.messaging().subscribe(toTopic: "/topics/message")
}
func application(_ application: UIApplication, performFetchWithCompletionHandler completionHandler: #escaping (UIBackgroundFetchResult) -> Void) {
// Update the database
DatabaseUpdater.performUpdate(performFetchWithCompletionHandler: completionHandler)
// TODO: update views
//completionHandler(.newData)
}
func applicationWillResignActive(_ application: UIApplication) {
// Sent when the application is about to move from active to inactive state. This can occur for certain types of temporary interruptions (such as an incoming phone call or SMS message) or when the user quits the application and it begins the transition to the background state.
// Use this method to pause ongoing tasks, disable timers, and invalidate graphics rendering callbacks. Games should use this method to pause the game.
}
func applicationDidEnterBackground(_ application: UIApplication) {
// Use this method to release shared resources, save user data, invalidate timers, and store enough application state information to restore your application to its current state in case it is terminated later.
// If your application supports background execution, this method is called instead of applicationWillTerminate: when the user quits.
}
func applicationWillEnterForeground(_ application: UIApplication) {
// Called as part of the transition from the background to the active state; here you can undo many of the changes made on entering the background.
}
func applicationDidBecomeActive(_ application: UIApplication) {
// Restart any tasks that were paused (or not yet started) while the application was inactive. If the application was previously in the background, optionally refresh the user interface.
connectToFcm()
DatabaseUpdater.performUpdate(performFetchWithCompletionHandler: {(result: UIBackgroundFetchResult) -> Void in
NSLog("Done updating!")
})
}
func applicationWillTerminate(_ application: UIApplication) {
// Called when the application is about to terminate. Save data if appropriate. See also applicationDidEnterBackground:.
}
}
#available(iOS 10, *)
extension AppDelegate : FIRMessagingDelegate {
// Receive data message on iOS 10 devices.
func applicationReceivedRemoteMessage(_ remoteMessage: FIRMessagingRemoteMessage) {
print("%#", remoteMessage.appData)
}
}
extension AppDelegate : UNUserNotificationCenterDelegate {
// iOS10+, called when presenting notification in foreground
func userNotificationCenter(_ center: UNUserNotificationCenter, willPresent notification: UNNotification, withCompletionHandler completionHandler: #escaping (UNNotificationPresentationOptions) -> Void) {
let userInfo = notification.request.content.userInfo
NSLog("[UserNotificationCenter] applicationState: \(applicationStateString) willPresentNotification: \(userInfo)")
//TODO: Handle foreground notification
completionHandler([.alert])
}
// iOS10+, called when received response (default open, dismiss or custom action) for a notification
func userNotificationCenter(_ center: UNUserNotificationCenter, didReceive response: UNNotificationResponse, withCompletionHandler completionHandler: #escaping () -> Void) {
let userInfo = response.notification.request.content.userInfo
NSLog("[UserNotificationCenter] applicationState: \(applicationStateString) didReceiveResponse: \(userInfo)")
//TODO: Handle background notification
completionHandler()
}
}
Application output:
Apple certificates:
Any help would be much appreciated.
try this
import UIKit
import Firebase
import FirebaseMessaging
import UserNotifications
#UIApplicationMain
class AppDelegate: UIResponder,UIApplicationDelegate,UNUserNotificationCenterDelegate{
var window: UIWindow?
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
// Override point for customization after application launch.
//create the notificationCenter
if #available(iOS 10.0, *) {
// For iOS 10 display notification (sent via APNS)
UNUserNotificationCenter.current().delegate = self
let authOptions: UNAuthorizationOptions = [.alert, .badge, .sound]
UNUserNotificationCenter.current().requestAuthorization(
options: authOptions,
completionHandler: {_, _ in })
// For iOS 10 data message (sent via FCM)
//FIRMessaging.messaging().remoteMessageDelegate = self
} else {
let settings: UIUserNotificationSettings =
UIUserNotificationSettings(types: [.alert, .badge, .sound], categories: nil)
application.registerUserNotificationSettings(settings)
}
application.registerForRemoteNotifications()
FirebaseApp.configure()
return true
}
func application(_ application: UIApplication, didRegisterForRemoteNotificationsWithDeviceToken deviceToken: Data) {
var token = ""
for i in 0..<deviceToken.count {
token = token + String(format: "%02.2hhx", arguments: [deviceToken[i]])
}
print("Registration succeeded! Token: ", token)
}
func application(_ application: UIApplication, didFailToRegisterForRemoteNotificationsWithError error: Error) {
print("Registration failed!")
}
func applicationWillResignActive(_ application: UIApplication) {
// Sent when the application is about to move from active to inactive state. This can occur for certain types of temporary interruptions (such as an incoming phone call or SMS message) or when the user quits the application and it begins the transition to the background state.
// Use this method to pause ongoing tasks, disable timers, and invalidate graphics rendering callbacks. Games should use this method to pause the game.
}
func applicationDidEnterBackground(_ application: UIApplication) {
// Use this method to release shared resources, save user data, invalidate timers, and store enough application state information to restore your application to its current state in case it is terminated later.
// If your application supports background execution, this method is called instead of applicationWillTerminate: when the user quits.
}
func applicationWillEnterForeground(_ application: UIApplication) {
// Called as part of the transition from the background to the active state; here you can undo many of the changes made on entering the background.
}
func applicationDidBecomeActive(_ application: UIApplication) {
// Restart any tasks that were paused (or not yet started) while the application was inactive. If the application was previously in the background, optionally refresh the user interface.
}
func applicationWillTerminate(_ application: UIApplication) {
// Called when the application is about to terminate. Save data if appropriate. See also applicationDidEnterBackground:.
}
// Firebase notification received
#available(iOS 10.0, *)
func userNotificationCenter(_ center: UNUserNotificationCenter, willPresent notification: UNNotification, withCompletionHandler completionHandler: #escaping (_ options: UNNotificationPresentationOptions) -> Void) {
// custom code to handle push while app is in the foreground
print("Handle push from foreground\(notification.request.content.userInfo)")
// let dict = notification.request.content.userInfo["aps"] as! NSDictionary
// print(dict)
// let d : [String : Any] = dict["alert"] as! [String : Any]
// let body : String = d["body"] as! String
// let title : String = d["title"] as! String
//
// print("Title:\(title) + body:\(body)")
//
//
//
// self.showAlertAppDelegate(title: title,message:body,buttonTitle:"ok",window:self.window!)
completionHandler(.alert)
}
#available(iOS 10.0, *)
func userNotificationCenter(_ center: UNUserNotificationCenter, didReceive response: UNNotificationResponse, withCompletionHandler completionHandler: #escaping () -> Void) {
// if you set a member variable in didReceiveRemoteNotification, you will know if this is from closed or background
if response.actionIdentifier == "goToApp"{
let storyBoard : UIStoryboard = UIStoryboard(name: "Main", bundle:nil)
let nextViewController = storyBoard.instantiateViewController(withIdentifier: "SecondViewController") as! SecondViewController
let appDelegate = UIApplication.shared.delegate as! AppDelegate
appDelegate.window?.rootViewController = nextViewController
}else if response.actionIdentifier == "cancel" {
print("close")
}else {
}
print("Handle push from background or closed\(response.notification.request.content.userInfo)")
}
func showAlertAppDelegate(title: String,message : String,buttonTitle: String,window: UIWindow){
let alert = UIAlertController(title: title, message: message, preferredStyle: UIAlertControllerStyle.alert)
alert.addAction(UIAlertAction(title: buttonTitle, style: UIAlertActionStyle.default, handler: nil))
window.rootViewController?.present(alert, animated: false, completion: nil)
}
// Firebase ended here
}
As you say that you are receiving notification in Android and having issue with iOS, then there is possibility that this issue comes because of Payload format. I also met with this issue earlier.
Please make sure that your Payload format must be like below.
{
"aps" : {
"alert" : {
"body" : "great match!",
"title" : "Portugal vs. Denmark",
},
"badge" : 1,
},
"customKey" : "customValue"
}
And if your app running on ios 10 or later, then make sure you set delegate.
For more information, see here

unable to receive the push notification in foreground using FCM

I have been trying to get firebase push-notification in my app. I have tried everything on the internet but couldn't find solution. I have been receiving notification in background, but when App is in foreground I am unable to get the notification. But when I print the userInfo in "didReceiveRemoteNotification" I get the message in console
Any help would be appreciated.
import Firebase
import UserNotifications
#UIApplicationMain
class AppDelegate: UIResponder, UIApplicationDelegate{
var window: UIWindow?
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
//FirebaseApp.configure()
self.initializeFCM(application)
let token = InstanceID.instanceID().token()
debugPrint("GCM TOKEN = \(String(describing: token))")
return true
}
func application(_ application: UIApplication, didFailToRegisterForRemoteNotificationsWithError error: Error)
{
debugPrint("didFailToRegisterForRemoteNotificationsWithError: \(error)")
}
func application(received remoteMessage: MessagingRemoteMessage)
{
debugPrint("remoteMessage:\(remoteMessage.appData)")
}
func initializeFCM(_ application: UIApplication)
{
print("initializeFCM")
if #available(iOS 10.0, *) // enable new way for notifications on iOS 10
{
let center = UNUserNotificationCenter.current()
center.delegate = self
center.requestAuthorization(options: [.badge, .alert , .sound]) { (accepted, error) in
if !accepted
{
print("Notification access denied.")
}
else
{
print("Notification access accepted.")
UIApplication.shared.registerForRemoteNotifications();
}
}
}
else
{
let type: UIUserNotificationType = [UIUserNotificationType.badge, UIUserNotificationType.alert, UIUserNotificationType.sound];
let setting = UIUserNotificationSettings(types: type, categories: nil);
UIApplication.shared.registerUserNotificationSettings(setting);
UIApplication.shared.registerForRemoteNotifications();
}
FirebaseApp.configure()
Messaging.messaging().delegate = self
Messaging.messaging().shouldEstablishDirectChannel = true
}
// enable new way for notifications on iOS 10
func application(_ application: UIApplication, didRegister notificationSettings: UIUserNotificationSettings)
{
debugPrint("didRegister notificationSettings")
if (notificationSettings.types == .alert || notificationSettings.types == .badge || notificationSettings.types == .sound)
{
application.registerForRemoteNotifications()
}
}
func application(application: UIApplication, didRegisterForRemoteNotificationsWithDeviceToken deviceToken: NSData)
{
debugPrint("didRegisterForRemoteNotificationsWithDeviceToken: NSDATA")
let token = String(format: "%#", deviceToken as CVarArg)
debugPrint("*** deviceToken: \(token)")
Messaging.messaging().apnsToken = deviceToken as Data
debugPrint("Firebase Token:",InstanceID.instanceID().token() as Any)
}
func application(_ application: UIApplication, didRegisterForRemoteNotificationsWithDeviceToken deviceToken: Data)
{
debugPrint("didRegisterForRemoteNotificationsWithDeviceToken: DATA")
let token = String(format: "%#", deviceToken as CVarArg)
debugPrint("*** deviceToken: \(token)")
Messaging.messaging().apnsToken = deviceToken
debugPrint("Firebase Token:",InstanceID.instanceID().token() as Any)
}
//-------------------------------------------------------------------------//
// [START receive_message]
func application(_ application: UIApplication, didReceiveRemoteNotification userInfo: [AnyHashable: Any]) {
Messaging.messaging().appDidReceiveMessage(userInfo)
print(userInfo)
}
func application(_ application: UIApplication, didReceiveRemoteNotification userInfo: [AnyHashable: Any],
fetchCompletionHandler completionHandler: #escaping (UIBackgroundFetchResult) -> Void) {
Messaging.messaging().appDidReceiveMessage(userInfo)
print(userInfo)
completionHandler(UIBackgroundFetchResult.newData)
}
// [END receive_message]
}
// [START ios_10_message_handling]
#available(iOS 10, *)
extension AppDelegate : UNUserNotificationCenterDelegate {
// Receive displayed notifications for iOS 10 devices.
func userNotificationCenter(_ center: UNUserNotificationCenter,
willPresent notification: UNNotification,
withCompletionHandler completionHandler: #escaping (UNNotificationPresentationOptions) -> Void) {
let userInfo = notification.request.content.userInfo
// With swizzling disabled you must let Messaging know about the message, for Analytics
Messaging.messaging().appDidReceiveMessage(userInfo)
print(userInfo)
// Change this to your preferred presentation option
completionHandler([])
}
func userNotificationCenter(_ center: UNUserNotificationCenter,
didReceive response: UNNotificationResponse,
withCompletionHandler completionHandler: #escaping () -> Void) {
let userInfo = response.notification.request.content.userInfo
Messaging.messaging().appDidReceiveMessage(userInfo)
print(userInfo)
completionHandler()
}
}
// [END ios_10_message_handling]
extension AppDelegate : MessagingDelegate {
// [START refresh_token]
func messaging(_ messaging: Messaging, didRefreshRegistrationToken fcmToken: String) {
print("Firebase registration token: \(fcmToken)")
}
func messaging(_ messaging: Messaging, didReceive remoteMessage: MessagingRemoteMessage) {
print("Received data message: \(remoteMessage.appData)")
}
// [END ios_10_data_message]
}
Since iOS 14, .alert is deprecated, you might use .banner instead:
func userNotificationCenter(_ center: UNUserNotificationCenter, willPresent notification: UNNotification, withCompletionHandler completionHandler: #escaping (UNNotificationPresentationOptions) -> Void) {
let content = notification.request.content
// Process notification content
print("\(content.userInfo)")
completionHandler([.banner, .list, .sound]) // Display notification Banner
}
From iOS 10, You can display Apple's default notification banner using below function.
Notification behaviour will depend on properties which you return within completionHandler.
func userNotificationCenter(_ center: UNUserNotificationCenter, willPresent notification: UNNotification, withCompletionHandler completionHandler: #escaping (UNNotificationPresentationOptions) -> Void) {
let content = notification.request.content
// Process notification content
print("\(content.userInfo)")
completionHandler([.alert, .sound]) // Display notification Banner
}
As per details in your question, you have already implemented above function, but with blank completionHandler(). Because of that notification banner doesn't display while app is in foreground state.
Earlier iOS 10:
You need to handle this by yourself. Like if you want to display banner when you received a notification, while app is in foreground state. You need to do this by yourself. You have to design your custom notification banner to display within app.
Hope it helps you.
Add this func in your AppDelegate:
func userNotificationCenter(_ center: UNUserNotificationCenter, willPresent notification: UNNotification, withCompletionHandler completionHandler: #escaping (UNNotificationPresentationOptions) -> Void) {
completionHandler([.alert, .sound, .badge])
}
Add UNUserNotificationCenterDelegate protocol to your AppDelegate class like this:
class AppDelegate: UIResponder, UIApplicationDelegate, UNUserNotificationCenterDelegate {
Add below line in didFinishLaunchingWithOptions func:
UNUserNotificationCenter.current().delegate = self

Resources