[IOS]推送通知简述及开发实践

 

[IOS]推送通知简述及开发实践 


推送通知简述及开发实践


转自: http://luoyl.info/blog/2012/02/apple_push_notification_guide/



一.关于推送通知

推送通知,也被叫做远程通知,是在iOS3.0以后被引入的功能。是当程序没有启动或不在前台运行时,告诉用户有新消息的一种途径,是从外部服务器发送到应用程序上的。一般说来,当要显示消息或下载数据的时候,通知是由远程服务器(程序的提供者)发送,然后通过苹果的推送通知服务(ApplePush Notification Service,简称apns)推送到设备的程序上。

推送的新消息可能是一条信息、一项即将到期的日程或是一份远程服务器上的新数据。在系统上展现的时候,可以显示警告信息或在程序icon上显示数字,同时,也可以播放警告音。一旦用户注意到程序有新的信息、时间或是数据,他们可以运行程序并访问新的内容。也可以选择忽略通知,这时程序将不会被激活。

iPhone, iPad和iPodtouch上同一时刻只有一个app在前台运行。大多数程序在后台运行的时候,可以对某些用户感兴趣的内容做出回应(定时、或数据等)。推送通知能让程序在这些事件发生的时候通知用户。

作为提供者为程序开发和部署推送通知,必须通过iOS Developer ProgramPortal获得SSL证书。每个证书限用于一个程序,使用程序的bundleID作为标识。证书有两种用途的:一种是针对sandbox(用于开发和测试),另外一种针对发布产品。这两种运行环境拥有为各自指定的IP地址并且需要不同的证书。还必须为两种不同的环境获取各自的provisioningprofiles。

APNS提供了两项基本的服务:消息推送和反馈服务。

消息推送:使用流式TCP套接字将推送通知作为二进制数据发送给APNs。消息推送有分别针对开发和测试用的sandbox、发布产品的两个接口,每个都有各自的地址和端口。不管用哪个接口,都需要通过TLS或SSL,使用SSL证书来建立一个安全的信道。提供者编制通知信息,然后通过这个信道将其发送给APNs。
注:sandbox:  
gateway.sandbox.push.apple.com:219
产品接口:gateway.push.apple.com:2195

反馈服务:可以得到针对某个程序的发送失败记录。提供者应该使用反馈服务周期性检查哪些设备一直收不到通知,不需要重复发送通知到这些设备,降低推送服务器的负担。
注:sandbox:feedback.push.apple.com:2196
产品接口:feedback.sandbox.push.apple.com:2196

二.Apple Push Notification的工作机制

下面是一个完整推送流程图
 从上图,我们可以看到。

  1.   首先是应用程序注册消息推送。
  2.  IOS跟APNSServer要deviceToken。应用程序接受deviceToken。
  3.  应用程序将deviceToken发送给PUSH服务端程序(Provider)。
  4.  服务端程序向APNS服务发送消息。
  5.  APNS服务将消息发送给iPhone应用程序。

无论是iPhone客户端跟APNS,还是Provider和APNS都需要通过证书进行连接的:

图中,

1. Provider是指某个iPhone软件的Push服务器,是我们将要开发的服务器。

2. APNS 是Apple Push Notification Service(ApplePush服务器)的缩写,是苹果的服务器。

上图可以分为三个阶段:

第一阶段:推送服务器(provider)把要发送的消息、目的iPhone的标识打包,发给APNS;

第二阶段:APNS在自身的已注册Push服务的iPhone列表中,查找有相应标识的iPhone,并把消息发到iPhone;

第三阶段:iPhone把发来的消息传递给相应的应用程序,并且按照设定弹出Push通知。

三.开发证书和推送证书的配置

1. 使用开发者帐号登录IOS Provisioning ,选择或新建一个AppId,这里以“info.luoyl.iostest”为例

2. 创建完后,进入App Id列表,可以看到新建的AppId默认是没有激活推送功能的,点击Configure链接,进入推送功能激活页面:

3. 在“Enable for Apple Push Notificationservice”选项上打勾,然后在行点“configure”按钮:

4. 此时会弹出一窗口,点“continue”

5.弹出证书上传页面,证书选择事先做好的“CertificateSigningRequest.certSigningRequest”,然后点“Generate”按钮;

6. 接下来会有“Your APNs SSL Certificate has beengenerated.”提示,点“continue”:

7. 下载刚生成的证书“aps_development.cer”到电脑:

8. 至此,appid的Development Push SSL Certificate已经变成“Enabled”状态了:

9. 制作一开发者测试证书,appid指定为“info.luoyl.iostest”, 下载后双击安装到电脑上:

10. 双击在步骤7下载的“aps_development.cer”安装到keychain Access上:

11. 选中pushServices证书,右键导出证书为个人信息交换(.p12)格式文件,这里我命名为“aps_development.p12”,点存储时会弹出一个密码设置窗口,可留空不填:

12. 在终端执行下面的命令,把刚才导出的个人信息交换(.p12)格式文件加密转换成推送服务器的推送证书:

  1. openssl pkcs12 -clcerts -nokeys -out cert.pem -in aps_development.p12  
  2. openssl pkcs12 -nocerts -out key.pem -in aps_development.p12  
  3. openssl rsa -in key.pem -out key.unencrypted.pem  
  4. cat cert.pem key.unencrypted.pem iostest_push_dev.pems  

上面的命令在执行时有4处是需要输入密码的,其中1和2直接回车,3必须设定一个key如“push”,在4处输入3设定的key“push”;
命令执行完后生成的“iostest_push_dev.pem”就是我们推送服务器要使用的推送证书;

经过以上步骤的配置,已经完成了开发推送功能所需要的条件了,接下来将会新建一个ios应用来体验完成推送功能,在ios应用需要实现的接口。

 

四.开发带有推送功能的IOS应用

为使应用能支持推送功能,我们的项目配置时要注意:

  1. Bundle Identifier、CodeSigning指定的开发证书绑定的AppId要和推送证书绑定的AppId一致(见下图);
  2.  如果项目中的开发证书在AppId激活推送功能前已经创建了,这时必须重新生成一个。支持推送功能的开发证书会比旧证书多出一项名为 “aps-environment”的授权串,如果继续使用旧证书,在程序启动尝试注册推送功能时会出现“未找到应用程序的“aps-environment”的权利字符串 ”的错误;
  3. 测试需要用真机,模拟器不支持。


 

在代码方面,推送的注册、监听和处理都集中在AppDelegate类里:

1.(BOOL)application:(UIApplication *)applicationdidFinishLaunchingWithOptions:(NSDictionary *)launchOptions
在该方法体里主要实现两个功能:
一是完成推送功能的注册请求,即在程序启动时弹出是否使用推送功能;
二是实现的程序启动是通过推送消息窗口触发的,在这里可以处理推送内容;

  1. (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions  
  2. {   
  3.     self.window [[[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]] autorelease];  
  4.     // Override point for customization after application launch.   
  5.     self.viewController [[[ViewController alloc] init] autorelease];  
  6.     self.window.rootViewController self.viewController;  
  7.     [self.window setBackgroundColor:[UIColor colorWithPatternImage:[UIImage imageNamed:@"background.png"]]];  
  8.     [self.window makeKeyAndVisible];  
  9.       
  10.     [[UIApplication sharedApplication] registerForRemoteNotificationTypes:(UIRemoteNotificationTypeAlert UIRemoteNotificationTypeBadge UIRemoteNotificationTypeSound)];  
  11.       
  12.     //判断程序是不是由推送服务完成的   
  13.     if (launchOptions)  
  14.         NSDictionary* pushNotificationKey [launchOptions objectForKey:UIApplicationLaunchOptionsRemoteNotificationKey];  
  15.         if (pushNotificationKey)  
  16.             UIAlertView *alert [[UIAlertView alloc]initWithTitle:@"推送通知"   
  17.                                                            message:@"这是通过推送窗口启动的程序,你可以在这里处理推送内容"  
  18.                                                           delegate:nil   
  19.                                                  cancelButtonTitle:@"知道了"   
  20.                                                  otherButtonTitles:nil, nil];  
  21.             [alert show];  
  22.             [alert release];  
  23.          
  24.      
  25.     return YES;  
  26. }   

 

  2.  接收从苹果服务器返回的唯一的设备token,该token是推送服务器发送推送消息的依据,所以需要发送回推送服务器保存
  1. (void)application:(UIApplication *)app didRegisterForRemoteNotificationsWithDeviceToken:(NSData *)deviceToken  
  2.     NSString* token [NSString stringWithFormat:@"%@",deviceToken];  
  3.     NSLog(@"apns -> 生成的devToken:%@"token);  
  4.     //把deviceToken发送到我们的推送服务器   
  5.     DeviceSender* sender [[[DeviceSender alloc]initWithDelegate:self ]autorelease];  
  6.     [sender sendDeviceToPushServer:token ];      
  7. }   

 

3.接收注册推送通知功能时出现的错误,并做相关处理:

  1. (void)application:(UIApplication *)app didFailToRegisterForRemoteNotificationsWithError:(NSError *)err  
  2.     NSLog(@"apns -> 注册推送功能时发生错误, 错误信息:n %@"err);  
  3.  

4. 接收到推送消息,解析处理

  1. (void)application:(UIApplication *)application didReceiveRemoteNotification:(NSDictionary *)userInfo  
  2. {   
  3.     NSLog(@"napns -> didReceiveRemoteNotification,Receive Data:n%@"userInfo);  
  4.     //把icon上的标记数字设置为0,   
  5.     application.applicationIconBadgeNumber 0;  
  6.     if ([[userInfo objectForKey:@"aps"objectForKey:@"alert"]!=NULL)  
  7.         UIAlertView* alert [[UIAlertView alloc] initWithTitle:@"**推送消息**"  
  8.                                                         message:[[userInfo objectForKey:@"aps"objectForKey:@"alert" 
  9.                                                        delegate:self  
  10.                                               cancelButtonTitle:@"关闭"  
  11.                                               otherButtonTitles:@"处理推送内容",nil];  
  12.         alert.tag alert_tag_push;  
  13.         [alert show];  
  14.      
  15. }   

通过上面的代码,基本推送功能的开发已经完成了。最后附件是一个简单的推送demo和demo运行截图,该demo需要推送服务器支持,请自行解决。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
要实现iOS,需要遵循以下步骤: 1. 创建APNS证书 首先,你需要在苹果开发者中心创建一个APNS证书。这个证书将用于安全地将消息发iOS设备。 2. 获取设备Token 每个iOS设备都有一个唯一的设备Token,用于标识该设备。你需要在你的应用中获取该设备Token,并将其发到你的服务器。 3. 编写PHP代码 使用PHP编写代码,以便将消息发到APNS服务器。你需要使用APNS证书和设备Token来建立连接,并将消息发到APNS服务器。 以下是一个简单的PHP代码示例: ``` <?php // Put your device token here (without spaces): $deviceToken = 'YOUR_DEVICE_TOKEN_HERE'; // Put your private key's passphrase here: $passphrase = 'YOUR_PASSPHRASE_HERE'; // Put your alert message here: $message = 'Hello, world!'; //////////////////////////////////////////////////////////////////////////////// $ctx = stream_context_create(); stream_context_set_option($ctx, 'ssl', 'local_cert', 'YOUR_APNS_CERTIFICATE.pem'); 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 the notification 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); ?> ``` 在上面的代码中,你需要将以下变量替换为你自己的值: - YOUR_DEVICE_TOKEN_HERE:你的设备Token。 - YOUR_PASSPHRASE_HERE:你的APNS证书密码。 - YOUR_APNS_CERTIFICATE.pem:你的APNS证书文件名和路径。 - $message:你要发的消息。 4. 测试 运行PHP代码并测试。如果一切正常,你应该会收到一个通知。 注意:在生产环境中,你需要将APNS服务器地址更改为“gateway.push.apple.com”。在示例代码中,我们使用的是开发环境的APNS服务器地址“gateway.sandbox.push.apple.com”。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值