这是一篇来自[raywenderlich](http://www.raywenderlich.com)的教程,内容翔实!结构简单、讲解循序渐进、文章质量上乘!是一篇难的的博文!使用半瓶的英语水平翻译了一下:
1.【iOS push全方位解析】(一)push的概述(本博文)
2.【iOS push全方位解析】(二)[生成push证书,生成Provisioning Profile](http://blog.csdn.net/hherima/article/details/45583865)
3.【iOS push全方位解析】(三)[一个极简的demo,并测试一下push](http://blog.csdn.net/hherima/article/details/45624075)
[这里查看原文](http://www.raywenderlich.com/32960/apple-push-notification-services-in-ios-6-tutorial-part-1)
在iOS中,App在后台不能做太多的事情,仅被允许做一些有限的活动,这样电池寿命就得到了保护。但,如果某些有趣的时间发生,并且又希望让用户知道,即便是用户并没有正在使用该App。
比如,用户收到一条新微博,他们喜欢的队赢得了比赛,或者他们的晚饭准备好了,既然App并不在运行,所以APP不能检测到这些事件。
幸运的是Apple针对这些问题提供了解决方案。开发者可以写一个服务端的组建,替代客户端不停的检测或者在后台工作。
当遇见感兴趣的事件发生,服务端组建可以发送一个push通知到这个App;
push通知可以做下面三件事:
● 显示一条短文本消息
● 播放一段声音
● 设置在APP图标badge数量
![](https://box.kancloud.cn/2016-03-10_56e11b0f520f6.jpg)
<学习如何在app中添加push通知>
开发者可以组合这些特性,比如,播放一段声音,并设置badge数字,但是不显示文本消息。
通过这一系列的文章,你自己将实现一个简单的APP并使用push通知。下面这部分文章,你将学会怎样配置APP接受push通知,并发送一个测试消息。
本篇教程适用于中高级iOS开发,如果你还是iOS新人,你应该看看其他教程。另外强烈推荐大家看看下面两个教程
● [How To Write A Simple PHP/MySQL Web Service for an iOS App](http://www.raywenderlich.com/2941/how-to-write-a-simple-phpmysql-web-service-for-an-ios-app)
● [How To Write an iOS App That Uses A Web Service](http://www.raywenderlich.com/2965/how-to-write-an-ios-app-that-uses-a-web-service)
废话少说,我们开始吧
### Getting Started:Brief Overview
给APP推送push通知要做相当多的工作,下图是一个多方组成的拼图:
![](https://box.kancloud.cn/2016-03-10_56e11b0f6c94e.jpg)
(push工作原理图)
1. 一个App启用push通知。用户得确认,自己就会收到这些通知。
2. App 收到一个“device token”,你可以认为device token是一个地址,push通知将被发送到这儿。
3. App发送该device token到你App的Server。
4. 当有趣的事件发生后,App的Server发送一个push通知到Apple Push Notification Service(简写为APNS)
5. APNS发送一个push通知到用户的设备。
当用户设备收到push通知,设备上显示一个alert,播放一段声音或者更新App的icon。用户通过alert可以启动App,并给予了push的内容。
push通知还值得存在么,既然我们有了本地通知和多任务。本地通知仅限于设定好时间的事件,并且只有“VOIP,地图导航和后台播放”才能使APP后台运行。假如你想通知那些App已经被close的用户,还需要push通知。
本教程,我会详细阐述push通知机制,和怎么在App中构建push。内容较多,享受它吧。
### push通知需要准备什么
为了给APP添加push通知,你需要:
一台iPhone或iPad。push通知在模拟器上不好用,所以你需要在真机上测试。
iOS Developer Program membership。你需要创建一个新的App ID和provisioning profile还有SSL证书(APP Server使用)。这些都在iOS Provisioning Potral中操作。
如果你想跟随本文的例子,你还需要创建你自己的provisioning profile和SSL 证书;你不能用我的。因为拿到证书很重要,我会阐述申请一个新的证书的详细步骤。
一个服务器用来连接网络。push通知总是由Server发出的。作为开发,可以使用你的Mac作为Server,但是作为产品发布,你至少需要一个类似于VPS(Virtual Private Server)的东西。
一种廉价的共享主机托管账户是不够的,你需要在后台运行,安装SSL 证书,并且支持特定端口TLS外边连接。
大多共享主机托管提供者,不让你这么搞。可能你请求后,他会这么干。我真心建议使用VPS,比如【Linode】
### 剖析一个push通知
App Server负责创建push消息,所以,知道push消息长什么样子很有用。一个push通知是一个条短消息,包含了device token,payLoad,还有一些其他字节。payLoad是包含了真是的数据。App Server应该提供一个JSON格式的字典。一个简单push消息的payLoad像这样:
~~~
{
"aps":
{
"alert": "Hello, world!",
"sound": "default"
}
}
~~~
一对{}包含了一个字典。payload是一个字典,至少包含一项“aps”,在上面的例子中,aps包含了两个字段alert和sound。客户端收到这种push通知,显示一个alert文本“helloworld”并播放了标准效果的声音。
还可以在aps中添加其他items,比如:
~~~
{
"aps":
{
"alert":
{
"action-loc-key": "Open",
"body": "Hello, world!"
},
"badge": 2
}
}
~~~
现在alert是一个字典了。“action-loc-key”给提供可选择的文本。badge字段包含了显示在APP icon上的数字。该push不会播放声音。
JSON格式的payload有很多中配置。开可以改变播放的声音,可以提供本地化的文本,可以自定义添加字段。点击这里查看更多[Local and Push Notification Programming Guide](https://developer.apple.com/library/ios/documentation/NetworkingInternet/Conceptual/RemoteNotificationsPG/Introduction.html).
push通知本身应该是短小为目的,payload最大是256bytes,,跟短信和微博大小差不多。聪明的push 服务器不会浪费空格和换行符,生成的push消息想这样子:
~~~
{"aps":{"alert":"Hello, world!","sound":"default"}}
~~~
这样我们读起来不太容易,但是它节省了字节。payload超过256的push通知,将不会被APNS接受。
### push通知的问题
它并不可靠。没有人保证push通知将准确的派发,即使APNS服务器接受了它们。正如 App Server担心的那样,push通知是fire-and-forget。没办法知道发给APNS的push消息的状态。派发的时间也是相差很大,可能秒级可能半个小时。
另外,iPhone用户可能一直没有启用push通知功能;可能在一个wifi环境,该wifi环境阻塞了APNS的端口;可能iPhone已经关机了。APNS会尝试发送最后一个通知,当phone回到在线后。但APNS仅会尝试一定次数,超过这个次数。这个push消息就永远丢了。
![](https://box.kancloud.cn/2016-03-10_56e11b0f87a2e.jpg)
(push 并不可靠)
可能很贵。在App中添加push功能很容易也很廉价。在大用户量下,push通知变得昂贵了。比如:你在RSS变化的时候,通知你的用户。因为你控制着RSS并知道什么时候变化了。你在网站上更新,Server就发出了通知。但是,假如你的App是一个RSS feed,允许用户把自己的URL放进去。在这种情况下,你需要想出一些机制来检测更新那些资料。
实际中,你的Server需要不停的记录这些变化的feeds。如果你有大量用户,可能需要扩充服务器和宽带。这样push通知变得很昂贵并且不值得了。
理论知识差不多了,开始学习怎么做push通知吧。在开始之前,我们需要在iOS provisioning portal上做一些烦人的设置工作。
硬货是下一篇 [http://blog.csdn.net/hherima/article/details/45583865](http://blog.csdn.net/hherima/article/details/45583865)