推送类型
- 本地消息推送:不需要联网,不需要服务器,客户端应用直接发出推送消息,一般通过定时器在指定的时间进行消息推送。
- 远程消息推送:客户端从苹果公司的APNS服务器注册获得当前用户的设备令牌并发送给应用的服务器,然后应用的服务器才可以通过APNS服务器间接的向客户端发送推送消息,可能会有延迟。
具体流程:
- App客户端向APNS服务器发送设备的UDID和Bundle Identifier。
- APNS服务器对传过来的信息加密生成一个deviceToken并返回给客户端。
- 客户端将当前用户的deviceToken发送给自己服务器。
- 自己应用的服务器将得到的deviceToken保存,需要的时候利用deviceToken向APNS服务器发送消息。
- APNS服务器收到自己应用服务器的推送消息时,验证传来的deviceToken,如果一致,则将消息推送到客户端。
NSNotification是同步还是异步
NSNotification默认在主线程中通知是同步的,当通知产生时,通知中心会一直等待所有的观察者都收到并且处理通知结束,然后才会返回到发送通知的地方继续执行后面的代码,但是可以将通知的发送或者将通知的处理方法放到子线程中从而避免通知阻塞。其中,通知的发送可以添加到NSNotificationQueue异步通知缓冲队列中,也不会导致通知阻塞。
NSNotificationQueue是一个缓冲队列,通常以FIFO规则维护通知队列的发送。向通知队列添加通知有3种枚举类型: NSPostASAP、NSPostWhenIdle、NSPostNow,分别表示尽快发送、空闲发送、立刻发送。
下面验证默认通知是同步的:
#define MYNotificationName @"NSNotificationName"
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(process) name:MYNotificationName object:nil];
NSLog(@"即将发送通知");
[[NSNotificationCenter defaultCenter] postNotificationName:MYNotificationName object:nil];
NSLog(@"发送通知的下一行代码");
- (void)process {
sleep(3);
NSLog(@"通知处理结束");
}
执行结果如下:
2020-12-30 22:39:56.713692+0800 test[8190:20526067] 即将发送通知
2020-12-30 22:39:59.715492+0800 test[8190:20526067] 通知处理结束
2020-12-30 22:39:59.715798+0800 test[8190:20526067] 发送通知的下一行代码
由此可见,通知是同步的。
将通知的发送语句放到子线程:
NSLog(@"即将发送通知");
dispatch_async(dispatch_get_global_queue(0, 0), ^{
[[NSNotificationCenter defaultCenter] postNotificationName:MYNotificationName object:nil];
});
NSLog(@"发送通知的下一行代码");
或者
NSLog(@"即将发送通知");
// 将通知放到通知异步缓冲队列
NSNotification *notif = [NSNotification notificationWithName:MYNotificationName object:nil];
[[NSNotificationQueue defaultQueue] enqueueNotification:notif postingStyle:NSPostASAP];
NSLog(@"发送通知的下一行代码");
将通知的处理放到子线程:
- (void)process {
dispatch_async(dispatch_get_global_queue(0, 0), ^{
sleep(3);
NSLog(@"通知处理结束");
});
}
执行结果如下:
2020-12-30 22:50:22.491123+0800 test[8258:20532310] 即将发送通知
2020-12-30 22:50:22.491815+0800 test[8258:20532310] 发送通知的下一行代码
2020-12-30 22:50:25.495750+0800 test[8258:20532458] 通知处理结束
网友评论