iOS推送服务的变更

1.推送条幅和功能的变化

 我们首先来看看推送消息是如何在手机上显示的

iOS 8
iOS 9(1)
iOS 9(2)

相对于iOS8,iOS9增加了输入框按钮,也就是为UIMutableUserNotificationAction增加了behavior属性

iOS 10(1)
iOS 10(2)

相对于iOS 9,iOS 10增加了subTitle和附件等

2.调用函数库的变化

iOS8和iOS 9使用同一套函数方法,所有的相关类声明在UIUserNotificationSettings.h和UILocalNotification.h文件中,iOS8和iOS9唯一的区别是iOS9支持输入框按钮,也就是iOS 9的UIMutableUserNotificationAction类增加了behavior和parameters属性。在iOS10中,新增了一个框架UserNotifications,提供了一套新的解决方案,所有的操作都是通过UNUserNotificationCenter执行的。

3.注册方式的变化

在这三个大的版本中,虽然注册推送的方式在不断的变化,到iOS 10甚至换了一个框架,但是推送服务的核心理念一直没变,在这里,我们可以做一个简单的划分,把注册推送服务粗略的分为下列几步:

1.创建通知分类(notificationcategory)2.创建通知设置(notificationsetting)3.注册到app

在iOS8和iOS 9的版本中,注册推送服务


在iOS 10的版本中,注册推送服务

在文章开头图片上推送条幅下面还带有按钮,那么如何给推送消息添加按钮呢,这个时候就需要用到通知分类(notification category)了。我们先看两段代码:

        在iOS 8和iOS 9中创建category
在iOS 10中创建category

从上面两个图可以知道,不管是在哪个版本,创建通知分类(notificationcategory)的步骤都是一样的,首先会先创建notification action,然后再添加到通知分类中。一般情况下一个通知分类中会有一到两个notification action,通过notificationaction来控制按钮的一些属性。一个通知分类最多可以有两个按钮,多余的会被忽略。

4.代理方法的变化

在用到推送服务的时候,如果不需要再推送条幅下面增加按钮,那么我们平常就只需要使用下图中的这个代理方法了

在iOS8和iOS 9中当我们点击推送的条幅(注意不是条幅下面的按钮)或者收到推送消息时app处于前台状态,就会调用上图中的回调方法

图中两个分别是本地推送和远程推送的通知,本地推送可以通过nitification这个参数获取userInfo和角标数,远程推送需要通过userInfo,这个userInfo是由应用服务器的推送消息中的Payload来决定的,一些自定义数据可以在这里获取。

而当我们需要为推送消息加一些点击事件,比如直接通过点击条幅中的回复按钮来回复聊天消息,那么在点击回复按钮之后,就会执行下图中的代理方法。

iOS 8中点击条幅按钮会调用的代理方法
iOS 9中点击条幅按钮会调用的代理方法

如图所示,分别是在iOS 8和iOS 9中的本地推送和远程推送的代理方法,当我们点击推送条幅中的按钮时,会调用上图中的代理方法,iOS 8和iOS 9使用的是同一套函数库,为什么我们还需要区分开来写呢。因为这个代理方法在iOS8和iOS 9中有一些区别,我们通过对比可以知道,iOS9中的方法比iOS 8多了一个参数responseInfo,那么这个参数有什么作用呢?文章开头我们说iOS9比iOS8多了一个输入框按钮,我们可以通过这个responseInfo参数获取用户在输入框中输入的字符串,通过responseInfo[UIUserNotificationActionResponseTypedTextKey]来获取。

在处理点击事件时,我们如何知道点击的按钮是哪个呢?通过对比参数identifier和定义notification action时设置的identifier,可以知道是哪个按钮。

接下来,我们看看iOS 10是如何处理这些事件的。

在iOS 10中, 一般情况下,我们只需要处理这两个代理方法就可以了。

iOS 10新增的变化除了之前所说的那些以外,还有一个显著的变化,就是当推送消息到达时,即使你的app处于前台,仍然可以显示推送条幅。而在iOS 10之前,app必须是在后台状态才能显示。当然,即使是iOS 10,你需要达到这种效果,还需要一些配置,你需要实现上图中的第一个代理方法,并且调用completionHandler(),这样子就可以在前台收到推送条幅了。另外,上图中的第一个代理只有在app处于前台的时候才会调用。当app处于前台时,通过completionHandler()这个block来控制推送消息是以什么样的形式通知用户,一般情况下只需要像图中那样调用就可以了。

至于上图中的第二个代理,则是在点击条幅和条幅中的按钮时会被调用,这一点需要注意一下。同样的,我们要区分是哪个点击事件,和在iOS 8、iOS 9中一样,也是根据action的identifier,只不过iOS 10的这个属性没有通过参数直接暴露出来,它被封装在参数response中,可以通过response.actionIdentifier获取,当我们点击条幅(不是按钮)时,response.actionIdentifier返回的是com.apple.UNNotificationDefaultActionIdentifier。

5.iOS 10的UNNotificationRequest

在iOS 10中,如果想要创建一个本地推送,那就必须创建一个UNNotificationRequest对象,然后通过UNUserNotificationCenter发出。那么如何创建UNNotificationRequest呢,请看下图:

UNNotificationRequest的创建

从上图可以看出,在iOS 10中,要创建一个UNNotificationRequest对象,一个UNNotificationRequest需要一个UNMutableNotificationContent对象用来定义推送内容和一个UNNotificaitonTrigger对象用来定义触发条件。

UNMutableNotificationContent对象除了定义body、title等一般的属性外,还可以添加附件对象UNNotificationAttachment,附件可以是图片、音频、视频,系统在执行request之前,会先验证这些附件是否必须满足下面的条件,如果不能满足,request不会被执行。

附件UNNotificationAttachment需要满足相应的条件

至于UNNotificaitonTrigger对象,我们一般使用它的子类,它有四种子类,分别是:

UNTimeIntervalNotificationTrigger定义距离当前时间多少秒之后触发本地推送

UNCalendarIntervalNotificationTrigger定义哪个时间点触发本地推送

UNLocationIntervalNotificationTrigger定义进入或离开一个经纬度范围时触发本地推送

UNPushIntervalNotificationTrigger当推送信息来自APNs时,request的触发器是这个类型

iOS 10的本地和远程推送的代理方法都是执行的同样的回调方法,所以需要通过判断response参数的notification.request.trigger的类型是否是UNPushIntervalNotificationTrigger,来判断是否是远程推送。

6.远程推送的附件添加

本地推送添加附件非常简单,只需要给UNNotificationRequest对象的content属性添加一个UNNotificationAttachment附件对象。但是在进行远程推送时,并不需要我们来创建UNNotificationRequest对象,这个时候我们就需要借助于UNNotificationServiceExtension对象。

UNNotificationServiceExtension有两个方法,分别是:

在第一个方法中,我们可以根据request参数重新定义一个UMMutableNotificationContent对象,这样我们就能加上一个附件了。比如我们可以让推送服务器推送一个图片url过来,然后在这个方法里面下载图片,将图片作为附件加入到UMMutableNotificationContent对象中,最后调用contentHandler这个block提交修改的内容。

执行第一个方法时,会有一定的时间限制,如果没有及时执行完方法,系统会在时间到期之前调用第二个方法,给你最后一次提交修改的机会。如果时间到期了,你还是没有提交你修改的内容(就是没有执行contentHandler这个block),系统会使用原来的那个内容。

使用这个UNNotificationServiceExtension对象时,我们不能直接使用它,需要自己创建一个它的子类,并重写它的这两个方法。具体如何创建以及使用可以参考//www.greatytc.com/p/f77d070a8812

最后推荐一个,好用的服务端推送工具NWPusher https://github.com/noodlewerk/NWPusher,它是使用oc编写的,可以在mac和iphone两个端运行,如果你有兴趣的话,建议读一读源码,可以帮助你了解整个推送服务的运行机制

参考链接:

//www.greatytc.com/p/ff14939b6639

//www.greatytc.com/p/f77d070a8812

demo:https://github.com/ZZZZou/WPushDemo

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 219,427评论 6 508
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 93,551评论 3 395
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 165,747评论 0 356
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 58,939评论 1 295
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 67,955评论 6 392
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 51,737评论 1 305
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 40,448评论 3 420
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 39,352评论 0 276
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 45,834评论 1 317
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,992评论 3 338
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 40,133评论 1 351
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 35,815评论 5 346
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 41,477评论 3 331
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 32,022评论 0 22
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 33,147评论 1 272
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 48,398评论 3 373
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 45,077评论 2 355

推荐阅读更多精彩内容