firebase - 当应用程序在后台(最小化)时,推送通知不起作用 - iOS

标签 firebase push-notification apple-push-notifications swift4 ios11.3

我是 Swift 的新手,我正在创建聊天应用程序,我需要在应用程序处于前台或最小化时发送通知。

但是当应用程序最小化时我没有收到通知(它在连接 USB 时工作。

  • 已启用远程通知
  • Xcode 设置中的后台获取
  • 启用推送通知
  • 生产APns证书

  • 通知代码:
    class AppDelegate: UIResponder, UIApplicationDelegate {
    
        var window: UIWindow?
        let gcmMessageIDKey = "gcm.message_id"
    
        func application(_ application: UIApplication,
                         didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
    
            FirebaseApp.configure()
    
            Messaging.messaging().delegate = self
            Messaging.messaging().shouldEstablishDirectChannel = true
    
            if #available(iOS 10.0, *) {
    
                UNUserNotificationCenter.current().delegate = self
    
                let authOptions: UNAuthorizationOptions = [.alert, .sound, .badge]
                UNUserNotificationCenter.current().requestAuthorization(
                    options: authOptions,
                    completionHandler: {_, _ in })
            } else {
                let settings: UIUserNotificationSettings =
                    UIUserNotificationSettings(types: [.alert, .sound, .badge], categories: nil)
                application.registerUserNotificationSettings(settings)
            }
    
            application.registerForRemoteNotifications()
    
            NotificationCenter.default.addObserver(self, selector: #selector(tokenRefreshNotification(_:)), name: NSNotification.Name.InstanceIDTokenRefresh, object: nil)
    
            return true
        }
    
        func application(_ application: UIApplication, didReceiveRemoteNotification userInfo: [AnyHashable: Any]) {
    
            Messaging.messaging().appDidReceiveMessage(userInfo)         
        }
    
        func application(_ application: UIApplication, didReceiveRemoteNotification userInfo: [AnyHashable: Any],
                         fetchCompletionHandler completionHandler: @escaping (UIBackgroundFetchResult) -> Void) {
    
            Messaging.messaging().appDidReceiveMessage(userInfo)
    
            let action = userInfo["action"] as! String
            let notification = UILocalNotification()
            notification.fireDate = NSDate() as Date
            notification.alertTitle = "test"
            notification.alertBody = "test"
            notification.alertAction = "Ok"
            UIApplication.shared.applicationIconBadgeNumber =  1
            UIApplication.shared.scheduleLocalNotification(notification)
    
            completionHandler(UIBackgroundFetchResult.newData)
        }
    
        func application(_ application: UIApplication, didFailToRegisterForRemoteNotificationsWithError error: Error) {
            print("Unable to register for remote notifications: \(error.localizedDescription)")
        }
    
        func application(_ application: UIApplication, didRegisterForRemoteNotificationsWithDeviceToken deviceToken: Data) {
            print("APNs token retrieved: \(deviceToken)")
    
            // With swizzling disabled you must set the APNs token here.
            Messaging.messaging().apnsToken = deviceToken
        }       
    }
    
    @available(iOS 10, *)
    extension AppDelegate : UNUserNotificationCenterDelegate {
    
        func userNotificationCenter(_ center: UNUserNotificationCenter,
                                    willPresent notification: UNNotification,
                                    withCompletionHandler completionHandler: @escaping (UNNotificationPresentationOptions) -> Void) {
            let userInfo = notification.request.content.userInfo
    
            if let messageID = userInfo[gcmMessageIDKey] {
                print("Message ID: \(messageID)")
            }
    
            completionHandler([.alert, .sound, .badge])
        }
    
        func userNotificationCenter(_ center: UNUserNotificationCenter,
                                    didReceive response: UNNotificationResponse,
                                    withCompletionHandler completionHandler: @escaping () -> Void) {
            let userInfo = response.notification.request.content.userInfo
    
            if let messageID = userInfo[gcmMessageIDKey] {
                print("Message ID: \(messageID)")
            }
    
            print(userInfo)
    
            completionHandler()
        }
        @objc func tokenRefreshNotification(_ notification: Notification) {
                guard let token = InstanceID.instanceID().token() else {
                print("No firebase token, aborting registering device")
                return
            }
            print("No firebase token, aborting registering device")           
        }
    }   
    
    extension AppDelegate : MessagingDelegate {
        // [START refresh_token]
        func messaging(_ messaging: Messaging, didReceiveRegistrationToken fcmToken: String) {
            print("Firebase registration token: \(fcmToken)")
            Messaging.messaging().subscribe(toTopic: "/topics/channel_18")           
        }
    
        func messaging(_ messaging: Messaging, didReceive remoteMessage: MessagingRemoteMessage) {
            print("Received data message: \(remoteMessage.appData)")
        }        
    }
    

    FCM有效载荷:
     {
         "to" : "/topics/channel_18",
         "data" : {
          "action" : "NOTIFY",
          "message" : "{"text":"test" }"
         },
         "content_available" : true
        }
    

    我试过优先级高和声音选项,但没有任何效果。

    请注意,我没有根据客户要求使用“通知”键。我在 FCM 有效载荷中仅使用数据消息

    当应用程序在没有 USB 连接的情况下处于后台时,请任何人帮助我工作通知。

    最佳答案

    如果它适用于非静默通知,则意味着:

  • 那么有效载荷没有正确设置。基于对此提供的答案 question我只是改变了 content_available 的位置场成notification (并且由于您不想要标题正文,因此不要添加标题/正文)或仅添加到有效负载本身中,直到看到它工作为止。
  • 我还要确保设置了 Xcode 中的所有正确功能(启用远程通知、Xcode 设置中的后台提取、启用推送通知)。如前所述,取消选中并重新选中所有这些。
  • 并确保 后台应用刷新 已为您的应用启用。这与您的通知不同。显然,请确保您的通知也已启用。例如:

  • enter image description here
  • 但是,如果您尝试了所有方法,但它对 11.3 不起作用,那么它可能是一个错误。还有这个open question提到了你的同样问题。通过点击应用程序直接运行应用程序,即 不是 从 Xcode 启动,然后使用控制台查看与静默通知相关的日志记录。如果你得到这样的信息:

  • default 13:11:47.178186 +0200   dasd    DuetActivitySchedulerDaemon Removing a launch request for application <private> by activity <private>   default com.apple.duetactivityscheduler
    

    那么很可能它是一个与此类似的错误 iOS11 question .但是你必须打开一个新的雷达,因为那个雷达是关闭的,我相信是因为它是固定的!

    关于firebase - 当应用程序在后台(最小化)时,推送通知不起作用 - iOS,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/51550990/

    相关文章:

    iphone - 有没有办法在 APNS 推送消息中包含本地时间和时区

    apple-push-notifications - 当应用程序处于前台时接收推送通知时,是否可以显示 ios 的横幅?

    android - 如何从 Android 获取 Firebase 的项目名称?

    firebase - 使用填充了虚拟数据的默认数据库启动 firebase 模拟器

    ios - 在Xcode 8.2上构建0字节文件会导致警告 "Mach-O: Reached end of file while looking for: uint32_t."吗?

    ios - 为什么通知服务扩展没有在 iOS 14 上触发?

    javascript - notificationclick 事件服务 worker

    ios - iOS 中的本地通知是否需要开发者帐户?

    swift - 如果 ref 不存在但稍后存在,则 Firebase .value 观察者不会监听

    ios - 在真实 ios 设备上测试时, ionic 推送通知错误 500