轻松搞定iOS远程消息推送

一、引言
IOS中消息的推送有两种方式,分别是本地推送和远程推送,本地推送在http://www.jb51.net/article/93602.htm这篇博客中有详细的介绍,这里主要讨论远程推送的流程与配置过程。

二、远程推送机制的原理

1、从一张很火的图说起
搜索IOS远程推送,你总能看到一张如下的流程示意图,因为这张图确实很火,所以我也将它引用在此:

这张图示意的很清晰,大致意思是这样:你的应用服务端将消息发送到apple的APNS服务器,APNS服务器将消息推送到指定的Iphone,最后由Iphone负责将消息推送至你的APP。在此先不说这个过程是如何实现的,仅仅看这个流程,你可能会觉得,在你们服务端和客户端之间增加了一个apple的APNS,不是增加开发者的负担么?其实结果恰恰相反,因为apple对推送的统一管理,使我们开发者的工作变得异常简单。

2、服务端如何连接到客户端的

如果你是做android开发的,你一定非常了解长链接与心跳包。事实上,大部分的android应用的推送也确实是通过长链接来实现的。因为android系统的开放性,APP是很容易做到自启动和后台长链接的,而心跳验证,就是始终保证长链接属于接通状态,然后由服务端直接推送消息。如果IOS开发者也采用这种思路,就十分困难了,在IOS中想要保持一个APP服务始终不被系统杀死,我只能说太难了。通过上面的流程图,对比android的推送思路,我们很容易明白,IOS中其实也始终有一个长链接,那就是系统本身,这个长链接始终与APNS服务器相连,然后统一管理所有应用程序的推送。

3、这是IOS推送机制的优势?

下面的这些,只是我个人的一些看法。系统并无优劣,优劣在于个人喜好。

1、因为推送的服务端是appleID的验证用户,推送可靠性会高。

2、所有推送消息由APNS统一管理,效率高。

3、在客户端只需系统维护一个长链接,节省了用户流量消耗和手机的性能消耗,并且提高了安全性,使得有恶意推送和流氓软件的几率降低。

三、分分钟让你的APP收到远程推送

1、工欲善其事、必先利其器——创建推送证书
(1)请求CSR文件

在MAC应用程序中找到钥匙串访问,打开它。

点击选项栏中的钥匙串访问中的证书助理:

选择从证书颁发机构申请证书:

填写电子邮件和名称,选择储存到磁盘,然后继续。

这时,我们存储的地方有了这样一个文件:CertificateSigningRequest.certSigningRequest。

(2)导出密钥文件

打开钥匙串,会发现多了一对密钥,名字就是上面你填写的常用名称。

我们选择专用密钥进行导出,然后设置一个我们自己的密码:

这时候我们又有了一个后缀名为.p12的文件。

(3)创建AppId

到https://developer.apple.com的member Center:

用你付过费的开发者appleID登陆后,选择Certificates:

如果你的项目已经创建了APP id,则可以不用重新创建,但是你创建的APP id必须要支持远程推送。如果还没有创建,点击加号,创建一个:

之后的界面中APP ID有两种类型:Explicit和Wildcard,分别是特殊的和通配的,我们需要推送功能,这个ID不能是通配的,所以我们选择第一个。

这里需要填的的Bundle ID必须和我们App中的一致:

在APP ID的服务设置中,将Push Notification勾选上,点击continue。
分分钟搞定IOS远程消息推送

之后点击submit,最后点击Done。这时我们的APP IDs列表中会出现我们刚才创建的APP ID。

(4)创建证书

点击我们刚才创建的APP ID,你会看到Push Notification一行为未设定的。我们点击Edit。

在Push Notifications设置里是如下界面,development是开发证书,Production是产品证书,我们现在需要测试,所以用Development证书,上线时要使用Production证书。点击Create Certificate。

接着点击continue,如下界面会让我们选择一个CSR文件,我们第一步创建的文件在这里派上用场了,选择那个文件,点击Generate。

将创建好的证书下载到电脑中:

至此,我们已经有了三个文件了,分别是CSR文件,.p12文件,.cer文件。要将这三个文件放在同一个目录下。.cer文件分为测试和产品两个,需要哪个自行选择。写了这么多,我们的准备工作可算是做完了,不要灰心,其实你的推送工作基本上也就做完了。只是申请过程麻烦了一些,但工程的代码,我们几乎不用怎么配置。

2、兵马未动、粮草先行——服务端进行信息推送的设置

(1)处理证书

打开终端cd到我们上面得到的三个文件所在的目录。

在终端执行如下命令:

$ openssl x509 -in aps_development.cer -inform der -out PushCert.pem

aps_development.cer是刚才生成的.cer文件的文件名。会在当前文件夹中生成一个pem文件,这是我们服务端对应的证书。

再执行如下命令:

$ openssl pkcs12 -nocerts -out PushKey.pem -in key.p12

key.p12是上面生成的.p12文件的文件名。这时终端会让输入密码,这里的密码就是上面我们设置的密钥的密码。输入密码后回车,如果密码正确,会让我们输入新密码(一定切记),输入两次后,终端会提示成功创建PushKey.pem文件。

最后一步,将我们生成的两个pem文件和成为一个:

$ cat PushCert.pem PushKey.pem > ck.pem

(2)测试证书是否可用

在终端执行下面的命令:

$ telnet gateway.sandbox.push.apple.com 2195

等一小会,如果终端显示下面的情形,则证书正常。

然后执行如下命令:

openssl s_client -connect gateway.sandbox.push.apple.com:2195 -cert PushChatCert.pem -key PushKey.pem
输入密码后回车显示如下的结果则连接成功:

3、天涯海角、一步之遥——应用程序中的配置

在我们项目的AppDelegate中添加如下代码:

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
double version = [[UIDevice currentDevice].systemVersion doubleValue];//判定系统版本。
if(version>=8.0f){
 UIUserNotificationSettings *settings = [UIUserNotificationSettings settingsForTypes:(UIRemoteNotificationTypeBadge|UIRemoteNotificationTypeSound|UIRemoteNotificationTypeAlert) categories:nil];
 [[UIApplication sharedApplication] registerUserNotificationSettings:settings];

 }else{
 UIRemoteNotificationType myTypes = UIRemoteNotificationTypeBadge | UIRemoteNotificationTypeAlert | UIRemoteNotificationTypeSound;
 [[UIApplication sharedApplication] registerForRemoteNotificationTypes:myTypes];
 }
}

- (void)application:(UIApplication *)application didReceiveRemoteNotification:(NSDictionary *)userInfo{ // 处理推送消息
 NSLog(@"userinfo:%@",userInfo);
 NSLog(@"收到推送消息:%@",[[userInfo objectForKey:@"aps"] objectForKey:@"alert"]);
}
- (void)application:(UIApplication *)application didFailToRegisterForRemoteNotificationsWithError:(NSError *) error {
 NSLog(@"Registfail%@",error);
}
-(void)application:(UIApplication *)application didRegisterForRemoteNotificationsWithDeviceToken:(NSData *)deviceToken{
 NSLog(@"%@",deviceToken);//这里的Token就是我们设备要告诉服务端的Token码
}

下面是网上搜的PHP服务端的代码:

<?php
//这里填写设备的Token码
$deviceToken = '74314cc9e8f747e2fa96c2c1585c830cdf994de6b453ce9fa1c09ba396b2f9e9';
//这里是密钥密码
$passphrase = 'abcabc';
//推送的消息
$message = '这是一条推送消息';

////////////////////////////////////////////////////////////////////////////////

$ctx = stream_context_create();
stream_context_set_option($ctx, 'ssl', 'local_cert', 'ck.pem');//ck文件
stream_context_set_option($ctx, 'ssl', 'passphrase', $passphrase);

// Open a connection to the APNS server
$fp = stream_socket_client(
 'ssl://gateway.sandbox.push.apple.com:2195', $err,
 $errstr, 60, STREAM_CLIENT_CONNECT|STREAM_CLIENT_PERSISTENT, $ctx);

if (!$fp)
 exit("Failed to connect: $err $errstr" . PHP_EOL);

echo 'Connected to APNS' . PHP_EOL;

// Create the payload body
$body['aps'] = array(
 'alert' => $message,
 'sound' => 'default'
 );

// Encode the payload as JSON
$payload = json_encode($body);

// Build the binary notification
$msg = chr(0) . pack('n', 32) . pack('H*', $deviceToken) . pack('n', strlen($payload)) . $payload;

// Send it to the server
$result = fwrite($fp, $msg, strlen($msg));

if (!$result)
 echo 'Message not delivered' . PHP_EOL;
else
 echo 'Message successfully delivered' . PHP_EOL;

// Close the connection to the server
fclose($fp);

?>

把上面的PHP文件和我们的ck文件放在同一目录下。在终端的当前目录下,执行如下命令:

$php push.php

如果我们的设备王略正常,就可收到推送的消息了:

四、几点注意

1、如果终端发送信息时提示密钥不可访问之类的错误,请检查是否cd到了当前目录,如果还存在问题,将密钥部分从新生成一次。

2、注意PHP代码中的字符为英文字符。

本文已被整理到了《iOS推送教程》,欢迎大家学习阅读。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持我们。

(0)

相关推荐

  • iOS10 适配远程推送功能实现代码

    iOS10正式版发布之后,网上各种适配XCode8以及iOS10的文章满天飞.但对于iOS10适配远程推送的文章却不多.iOS10对于推送的修改还是非常大的,新增了UserNotifications Framework,今天就结合自己的项目,说一说实际适配的情况. 一.Capabilities中打开Push Notifications 开关 在XCode7中这里的开关不打卡,推送也是可以正常使用的,但是在XCode8中,这里的开关必须要打开,不然会报错: Error Domain=NSCocoa

  • iOS10推送通知开发教程

    虽然通知经常被过度使用,但是通知确实是一种获得用户关注和通知他们需要更新或行动的有效方式.iOS 10有了新的通知,如新消息.商业信息和时间表的变化.在本教程中,我将向你展示如何使用通知在你的iOS应用程序,并且显示iOS 10引入了新特性.开发iOS 10推送通知你需要最新版本的Xcode,Xcode 8测试版,这些目前都是可下载的,在下载页面. 你可以去Github下载本教程的整个工程. 开始 在Xcode中启用推送通知是很容易的,但你需要几个步骤. 创建一个新的工程,给它起一个唯一的Bun

  • iOS中的通知机制

    网上经常说iOS的通知机制是使用了观察者模式,里面有两个角色,其一是poster(发送者),另一个是observer(接受信息的订阅者).但我认为重要的角色是通知中心,它是整个通知机制的核心,有poster发送者发送的消息必定要到达通知中心,再由通知中心根据这个消息被哪些observer订阅者订阅过,就把消息往那些订阅者去分发.整体可以与现在的电子邮件结构作类比的. 但要额外说明一下,iOS的通知虽然也叫Notification通知,但是与Android中的通知是不一样的,在Android中的通

  • IOS如何在Host App 与 App Extension 之间发送通知

    如何从你的一个App发送通知给另一个App? (例:搜狗输入法下载皮肤完成后使用皮肤) 注:搜狗输入法是App.而键盘是Extension 当你为你的App 添加 App Extension时,如果想在App 发送通知给 Extension或许这篇文章可以帮助你. 了解更多内容 // 发送通知 - (void)postNotificaiton { CFNotificationCenterRef notification = CFNotificationCenterGetDarwinNotifyC

  • iOS推送之本地通知UILocalNotification

    摘要: Notification是智能手机应用编程中非常常用的一种传递信息的机制,而且可以非常好的节省资源,不用消耗资源来不停地检查信息状态(Pooling),在iOS下应用分为两种不同的Notification种类,本地和远程.本地的Notification由iOS下NotificationManager统一管理,只需要将封装好的本地Notification对象加入到系统Notification管理机制队列中,系统会在指定的时间激发将本地Notification,应用只需设计好处理Notifi

  • iOS远程推送Push开发教程

    远程推送通知 什么是远程推送通知 顾名思义,就是从远程服务器推送给客户端的通知(需要联网)远程推送服务,又称为APNs(Apple Push Notification Services) 为什么需要远程推送通知 传统获取数据的局限性 只要用户关闭了app,就无法跟app的服务器沟通,无法从服务器上获得最新的数据内容 远程推送通知可以解决以上问题 不管用户打开还是关闭app,只要联网了,都能接收到服务器推送的远程通知 远程推送通知使用须知 所有的苹果设备,在联网状态下,都会与苹果的服务器建立长连接

  • iOS开发之运动事件和远程控制

    之前我们已经学习了触摸处理和手势识别,其实这两个同属于iOS事件的触摸事件,今天我们来学习下iOS事件的另外两个事件: 一.运动事件 运动事件,是通过加速器进行触发,和触摸事件一样,继承UIResponder类的对象才能处理运动事件 UIResponder处理运动事件的方法: 复制代码 代码如下: #pragma mark 运动开始时执行 - (void)motionBegan:(UIEventSubtype)motion withEvent:(UIEvent *)event; #pragma

  • iOS10最新实现远程通知的开发教程详解

    一.iOS推送通知简介 众所周知苹果的推送通知从iOS3开始出现, 每一年都会更新一些新的用法. 譬如iOS7出现的Silent remote notifications(远程静默推送), iOS8出现的Category(分类, 也可称之为快捷回复), iOS9出现的Text Input action(文本框快捷回复). 而在iOS10, 苹果可谓是大刀阔斧般的, 对远程通知和本地通知进行了大范围的更新. iOS10推出了全新的UserNotifications框架(iOS10之前从属于UIKi

  • iOS实现远程推送原理及过程

    推送通知,是现在的应用必不可少的功能.那么在 iOS 中,我们是如何实现远程推送的呢?iOS 的远程推送原理又是什么呢?在做 iOS 远程推送时,我们会遇到各种各样的问题.那么首先让我们准备一些做推送需要的东西.我们需要一个付费的苹果开发者账号(免费的不可以做远程推送),有了开发者账号,我们可以去苹果开发者网站,配置自己所需要的推送的相关证书.然后下载证书,供我们后面使用,详细的证书配置过程,我们下面再说. 首先我们要说说iOS推送通知的基本原理: 苹果的推送服务通知是由自己专门的推送服务器AP

  • iOS消息远程推送通知

    本文实例为大家分享了iOS消息推送.iOS远程通知代码,供大家参考,具体内容如下 消息推送 /* 要开发测试消息机制的程序,必须用真机测试 推送消息的类型 UIRemoteNotificationTypeNone 不接收推送消息 UIRemoteNotificationTypeBadge 接收图标数字 UIRemoteNotificationTypeSound 接收音频 UIRemoteNotificationTypeAlert 接收消息文字 UIRemoteNotificationTypeNe

随机推荐