如何实现IOS APP被杀掉后依然可以接收到个推消息通知

news/2024/7/20 21:58:27 标签: ios, 个推, Swift, Notification, Extension

背景

项目已经集成了个推SDK,但是在离线场景下无法收到推送消息,离线场景主要分2种情况,一种是用户将APP切换到了后台,一种是用户将APP杀掉了。
针对场景一:我们可以将APP支持后台运行,比如项目中使用到了后台持续定位功能,后台音频等(Xcode中可以查看支持哪些后台模式),可以增加接收到离线通知的概率。

后台模式
针对场景二:我们需要集成NotificationServiceExtension,下面就主要介绍一下如何集成

NotificationServiceExtension_6">新增NotificationServiceExtension

在XCode中,按照以下步骤操作

新增一个target

新增Target
选择<a class=Notification Service Extension" />

NotificationService_11">配置好NotificationService的包名和签名

Bundle一般就用自己APP的包名加上NotificationService,如 com.edenwang.www.NotificationService

NotificationService_14">将下载的个推SDK中的NotificationService代码复制到项目中

个推SDK下载地址

https://docs.getui.com/download.html

下载<a class=个推SDK" />

NotificationService_19">解压开找到NotificationService

解压后的代码结构

NotificationServiceswiftNotificationServiceswift_22">将压缩包中NotificationService.swift文件内容替换项目中的NotificationService.swift

NotificationServiceentitlements_24">Info.plist和NotificationService.entitlements

在这里插入图片描述
记得将NotificationService.entitlements中包名更新成自己的

新建一个空的OC文件

Empty.m是新建的一个空的Objective-C文件,这个文件不能少。这个是咨询个推的技术人员后才得知的,说是混编的问题,如果是Swift项目需要加一个OC文件,如果是OC项目需要加一个空的Swift文件。可以查看下载的个推SDK中其他方式的实现作对比。

其他文件复制

复制NotificationService-Bridging-Header.h

打包测试

为了快速测试,需要将个推的后台运行临时关掉 GeTuiSdk.runBackgroundEnable(false)
安装到手机上后,将APP退出到后台后,稍等片刻,在个推控制台上查询当前设备的CID,检查CID的状态是否为离线,如果已经为离线了,可以通过个推的控制台推送测试消息,然后观察手机上收到的消息是否包含[Success]字符,如果有,说明大功告成了。

Swift">  override func didReceive(_ request: UNNotificationRequest, withContentHandler contentHandler: @escaping (UNNotificationContent) -> Void) {
    self.contentHandler = contentHandler
    guard let bestAttemptContent = request.content.mutableCopy() as? UNMutableNotificationContent else { return }
   
    // [ 测试代码 ] TODO:语音播报
    let cnt: Double = 123 //读取apns中播报信息
    let name = ApnsHelper.makeMp3FromExt(cnt)
    let sound = UNNotificationSound(named: UNNotificationSoundName(name))
    bestAttemptContent.sound = sound
    
    // [ 测试代码 ] TODO: 用户可以在这里处理通知样式的修改,eg:修改标题,开发阶段可以用于判断是否运行通知扩展
//    bestAttemptContent.title = "\(bestAttemptContent.title) [WillIn]"
    
    // [ GTSDK ] 统计APNs到达情况和多媒体推送支持接口, 建议使用该接口
    GeTuiExtSdk.handelNotificationServiceRequest(request, withAttachmentsComplete: { [weak self] (attachments: Array?, errors: Array?) in
      guard let handler = self?.contentHandler else { return }
      // [ 测试代码 ] TODO:日志打印,如果APNs处理有错误,可以在这里查看相关错误详情
      // print("处理个推APNs展示遇到错误:\(String(describing: errors))")
      
      // [ 测试代码 ] TODO:用户可以在这里处理通知样式的修改,eg:修改标题,开发阶段可以用于判断是否运行通知扩展
      bestAttemptContent.title = "\(bestAttemptContent.title) [Success]"
      if let attachment = attachments as? [UNNotificationAttachment], !attachment.isEmpty {
        // 设置通知中的多媒体附件
        bestAttemptContent.attachments = attachment
      }
      // 展示推送的回调处理需要放到个推回执完成的回调中
      handler(bestAttemptContent)
    })
  }

然后你可以在这个代码基础上定制自己的业务逻辑。


http://www.niftyadmin.cn/n/5320257.html

相关文章

c++学习笔记-STL案例-机房预约系统2-创建身份类

前言 衔接上一篇“c学习笔记-STL案例-机房预约系统1-准备工作”&#xff0c;本文主要包括&#xff1a;创建身份类&#xff0c;建立了整个系统的框架&#xff0c;Identity基类&#xff0c;派生类&#xff1a;Sudent、Teacher、Manager&#xff0c;基类无实现源文件&#xff0c;…

在vue中使用高德地图点击打点,搜索打点,高德地图组件封装

一。安装高德地图 npm install amap/amap-jsapi-loader --save二、在index.html文件中引入高德地图JavaScript API&#xff1a; <!DOCTYPE html> <html lang"en"> <head><meta charset"UTF-8"><meta http-equiv"X-UA-Co…

学习笔记-mysql基础(DDL,DML,DQL)

一.DDL DDL,Data Definition Language,数据库定义语言,该语言包括以下内容: 对数据库的常用操作对表结构的常用操作修改表结构 1.对数据库的常用操作 -- 查看所有的数据库 show databases -- 创建数据库 create database [if not exists] test [charsetutf8] -- 切换 选择 …

中国聚对苯二甲酸丙二醇酯行业市场调研报告(2024版)

内容简介&#xff1a; 与PET和PBT相比&#xff0c;PTT独特的螺旋状结构&#xff0c;使其具有较高的拉伸回弹性、易于染色性、耐污性以及良好的机械性能等优点&#xff0c;因此被广泛应用于地毯、织布面料、非织造布等领域&#xff0c;还可以作为工程塑料应用于电子电器、汽车、…

java面试题(21):private修饰的方法可以通过反射访问,那么private的意义是什么?

1 反射简介 Java&#xff0c;在一个类中&#xff0c;为了不让外界访问到某些属性和方法&#xff0c;通常将其设置为private&#xff0c;用正常的方式&#xff08;对象名.属性名&#xff0c;对象名.方法名&#xff09;将无法访问此属性与方法&#xff0c;但有没有其他方法可以访…

《LIO-SAM阅读笔记》-为何要引入增量式里程计?

前言&#xff1a; LIO-SAM在后端中同时维护着两个里程计&#xff0c;一个是增量式里程计&#xff0c;一个是优化后的里程计&#xff0c;其中优化后的里程计是经过imu、回环、gps因子图联合优化后的结果&#xff0c;是整个系统中最准确的位姿估计&#xff0c;那么为什么还需要维…

sqlite3 jdbc 只读模式

sqlite3 jdbc 只读 无效方法: “jdbc:sqlite:/bal/work_home/fn.db?readonlytrue” 导致 fn.db?readonlytrue 会被当成是数据库文件名 “jdbc:sqlite:/bal/work_home/fn.db?jdbc.explicit_readonlytrue” 参考了pragmaReadOnly sqlite3 jdbc 只读 有效方法 举例 package…

蓝桥杯 python 第二题 数列排序

这里给出一种解法 """ # 错的 n int(input()) dp[int(i) for i in input().split(" ")] dp.sort() print(" ".join(str(i) for i in dp)) """#这个是对的 num int(input())l list(map(int, input().split()))l.sort()pr…