应用程序终止时处理推送通知

时间:2016-01-28 10:30:00

标签: ios objective-c iphone push-notification

当我的应用程序没有运行并收到推送通知时,如果我点击该通知,应用程序就会启动 - 但是它没有提示用户设置的警报视图,询问他们是否他们想要查看通知的内容。它只是发射,并坐在那里。

推送通知在应用程序运行时可以正常运行 - 无论是作为活动应用程序还是在后台运行 - 但在应用程序未运行时无法正常工作。

我尝试在应用程序中注销launchOptions NSDictionary:didFinishLaunchingWithOptions:查看它带来了什么负载 - 但它出现了"(null)"。所以它基本上什么都没有 - 哪些不合理因为它不应该包含通知的负载?

任何人都有任何想法如何在应用程序未运行时如何使Push Notifications工作?

我的意思是当应用程序处于未运行状态时如何处理推送通知。如果您收到许多通知&你没有打开应用程序,也没有点击系统的通知面板。你是如何保留这些推动以便以后检索的。

7 个答案:

答案 0 :(得分:35)

1) 当应用程序在后台运行时当应用程序在前台运行时 application:didReceiveRemoteNotification:方法将在下面调用。

- (void)application:(UIApplication *)application didReceiveRemoteNotification:(NSDictionary *)userInfo
{
    if (application.applicationState == UIApplicationStateInactive)
    {
        // opened from a push notification when the app was on background
        NSLog(@"userInfo->%@", [userInfo objectForKey:@"aps"]);
    }
    else if(application.applicationState == UIApplicationStateActive)
    {
        // a push notification when the app is running. So that you can display an alert and push in any view
        NSLog(@"userInfo->%@", [userInfo objectForKey:@"aps"]);
    }
}

2) 当应用程序未启动(关闭)时,将调用application:didFinishedLaunchingWithOptions方法。

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
    if (launchOptions != nil)
    {
        // opened from a push notification when the app is closed
        NSDictionary* userInfo = [launchOptions objectForKey:UIApplicationLaunchOptionsRemoteNotificationKey];
        if (userInfo != nil)
        {
             NSLog(@"userInfo->%@", [userInfo objectForKey:@"aps"]);
        }
    }
    else
    {
        // opened app without a push notification.
    }
}

3)无法删除特定通知。从用户打开应用程序时,从应用程序中删除所有通知以便用户无法在通知中心显示的方法是将应用徽章设置为0。

答案 1 :(得分:10)

根据您的问题,当您打开应用程序时无法保留所有通知,更好的是,您可以调用api按照后端/服务器的时间戳获取所有通知,这就是Facebook的工作方式。

答案 2 :(得分:7)

该应用程序不会在后台处理推送通知,一旦您按下通知,操作系统就会唤醒应用程序。您可以通过以下方式捕捉这一时刻:

    - (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
    { 

        if ([launchOptions objectForKey:UIApplicationLaunchOptionsRemoteNotificationKey]) {
      // Your app has been awoken by a notification...
        }
   }

答案 3 :(得分:6)

您可以使用getDeliveredNotifications(completionHandler:)方法检索发送到您应用的通知。请注意,这仅返回当前显示在通知中心的通知,而不是用户已手动清除的通知。

UNUserNotificationCenter.current().getDeliveredNotifications { notifications in

    // notifications: An array of UNNotification objects representing the local
    // and remote notifications of your app that have been delivered and are still
    // visible in Notification Center. If none of your app’s notifications are
    // visible in Notification Center, the array is empty.

    // As said in the documentation, this closure may be executed in a background
    // thread, so if you want to update your UI you'll need to do the following:
    DispatchQueue.main.sync { /* or .async {} */ 
        // update UI
    }
}

答案 4 :(得分:3)

在应用程序端无法处理此问题。 您需要在服务器上维护未读徽章计数。 当应用程序被杀死时,徽章值将从服务器更新。

因此,当您随时打开应用程序时,您需要调用Web服务来获取所需的通知并更新tabbar的标记(如果使用)。

答案 5 :(得分:1)

在终止状态下收到通知后执行操作-iOS 13-场景委托

最近,我遇到一个问题,当我的应用程序处于终止状态时,我收到了远程推送通知。在最新的iOS版本中,Scene委托负责处理视图生命周期方法,而不是App Delegate。

较旧的iOS版本-由App Delegate处理 当应用终止并且接收到远程推送通知时,有效负载会反映在应用委托的didfinishLaunchingWithOptions方法中。使用此方法的启动参数,可以获取有效载荷数据并执行任何交互。

新的iOS版本-由Scene Delegate处理 类似地,当应用终止并且接收到远程推送通知时,有效负载会反映在场景委托的场景(willConnectTo会话)中。使用此方法的connectingOption参数,可以获取有效载荷数据并执行任何交互。

提示:将视图控制器设置为根视图控制器后,要执行任何交互或将此有效负载传递给另一个视图控制器,请保持几秒钟的延迟以传递数据。

示例代码:

guard let windowScene = (scene as? UIWindowScene) else { return }
window = UIWindow(frame: windowScene.coordinateSpace.bounds)
window?.windowScene = windowScene
 
if defaults.string(forKey: UserDefaultsKeys.TenantID.rawValue) != nil && connectionOptions.notificationResponse != nil {
   
  let rootViewController = UINavigationController(rootViewController: DashboardVC())
  window?.rootViewController = rootViewController
  window?.makeKeyAndVisible()
   
  DispatchQueue.main.asyncAfter(deadline: .now() + 1.0) {
    NotificationCenter.default.post(
      name: .passApnsDataToDashboardNotification,
      object: nil,
      userInfo: connectionOptions.notificationResponse?.notification.request.content.userInfo)
  }
   
}

答案 6 :(得分:0)

您可以通过以下通知启动以前终止的应用后显示提醒:

<tbody> <tr id='addr_work0' th:each="workRow, rowStat : *{workHistoryDetails.allWorkHistoryData}"> <td th:text="${rowStat.index + 1}"></td> <td><input type="text" name='work_name0' placeholder='Company Name' class="form-control" th:field="*{workHistoryDetails.allWorkHistoryData[__${rowStat.index}__].companyName}"/></td> <td><input type="text" name='work_city0' placeholder='Company city' class="form-control" th:field="*{workHistoryDetails.allWorkHistoryData[__${rowStat.index}__].city}"/></td> <td><input type="text" name='work_title0' placeholder='Job Title' class="form-control" th:field="*{workHistoryDetails.allWorkHistoryData[__${rowStat.index}__].jobTitle}"/></td> <td><input name="is_current0" type="checkbox" value="" class="form-control" style="text-align: center;" th:field="*{workHistoryDetails.allWorkHistoryData[__${rowStat.index}__].currentJob}"> </td> <td><input type="text" name='work_start0' placeholder='Start Date' class="form-control" th:field="*{workHistoryDetails.allWorkHistoryData[__${rowStat.index}__].startDate}"/></td> <td><input type="text" name='work_end0' placeholder='End Date' class="form-control" th:field="*{workHistoryDetails.allWorkHistoryData[__${rowStat.index}__].endDate}"/></td> <td><a class="btn btn-primary btn-md" id="work_done0" name="work_done0">Work done</a></td> </tr> <tr id='addr_work1'></tr> </tbody>