iOS不倒,博客不停
JPush的文檔說明挺不錯,非常詳細(xì)!為什么還要寫這篇簡書?主要是為了記錄自己開發(fā)過程,也給一些朋友提供一點(diǎn)點(diǎn)幫助.首先是JPush的文檔地址:JPush文檔
紅色部分是 APNs 推送谒获,JPush 代理開發(fā)者的應(yīng)用(需要基于開發(fā)者提供的應(yīng)用證書)斤葱,向蘋果 APNs 服務(wù)器推送忿族。由 APNs Server 推送到 iOS 設(shè)備上宵喂。
藍(lán)色部分是 JPush 應(yīng)用內(nèi)推送部分蜂莉,即 App 啟動時,內(nèi)嵌的 JPush SDK 會開啟長連接到 JPush Server怪与,從而 JPush Server 可以推送消息到 App 里
APNs 通知
APNs 通知:是指通過向 Apple APNs 服務(wù)器發(fā)送通知夺刑,到達(dá) iOS 設(shè)備,由 iOS 系統(tǒng)提供展現(xiàn)的推送分别。用戶可以通過 IOS 系統(tǒng)的 “設(shè)置” >> “通知” 進(jìn)行設(shè)置,開啟或者關(guān)閉某一個 App 的推送能力存淫。
JPush iOS SDK 不負(fù)責(zé) APNs 通知的展現(xiàn)耘斩,只是向 JPush 服務(wù)器端上傳 Device Token 信息,JPush 服務(wù)器端代理開發(fā)者向 Apple APNs 推送通知桅咆。
獲取 APNs 推送內(nèi)容
應(yīng)用內(nèi)消息
應(yīng)用內(nèi)消息:JPush iOS SDK 提供的應(yīng)用內(nèi)消息功能括授,在 App 在前臺時能夠收到推送下來的消息。App 可使用此功能來做消息下發(fā)動作岩饼。
此消息不經(jīng)過 APNs 服務(wù)器荚虚,完全由 JPush 提供功能支持。
APNs通知與應(yīng)用內(nèi)消息對比
如果只需要發(fā)送通知籍茧,則可以忽略應(yīng)用內(nèi)消息的處理版述。對于兩種消息的代碼處理可以參考API 部分的描述。
JPush API v3 支持同時一次調(diào)用同時推送 APNs 通知與 JPush 應(yīng)用內(nèi)消息寞冯。這在某些應(yīng)用場景里是有意義的渴析。
OK,原理了解之后,下面開始集成.
- 1:下載JPush的SDK:SDK下載地址
- 2:在JPush平臺注冊應(yīng)用,這里的目的:
- A:交付授權(quán),因為在這里開發(fā)者需要上傳應(yīng)用的推送開發(fā)證書,推送生產(chǎn)證書,這樣JPush平臺就能去蘋果服務(wù)器拿去一個推送關(guān)鍵字段:DeviceToken,相當(dāng)于授權(quán)碼.
- B:平臺注冊,還會生成一個:AppKey和一個MasterSecret.這兩個東西相當(dāng)于一個登陸賬號,一個登陸密碼.這樣生成出來,JPush就能根據(jù)MasterSecret.去校驗** AppKey,然后去找綁定在這個 AppKey上面的生產(chǎn),開發(fā)證書授權(quán)的DeviceToken**去蘋果服務(wù)器推送消息.
- 3 導(dǎo)入SDK
將SDK包解壓晚伙,在Xcode中選擇“Add files to 'Your project name'...”,將解壓后的lib子文件夾(包含JPUSHService.h俭茧、jpush-ios-x.x.x.a咆疗,jcore-ios-x.x.x.a)添加到你的工程目錄中。
添加Framework:
- CFNetwork.framework
- CoreFoundation.framework
- CoreTelephony.framework
- SystemConfiguration.framework
- CoreGraphics.framework
- Foundation.framework
- UIKit.framework
- Security.framework
- libz.tbd (Xcode7以下版本是libz.dylib)
- AdSupport.framework (獲取IDFA需要母债;如果不使用IDFA午磁,請不要添加)
- UserNotifications.framework (Xcode8及以上)
- libresolv.tbd (JPush 2.2.0及以上版本需要, Xcode7以下版本是libresolv.dylib)
*4:編譯與開啟推送功能
*5:ATS
<key>NSAppTransportSecurity</key>
<dict>
<key>NSAllowsArbitraryLoads</key>
<true/>
</dict>
*6:添加頭文件和添加代理
請將以下代碼添加到 AppDelegate.m 引用頭文件的位置。
// 引入JPush功能所需頭文件
#import "JPUSHService.h"
// iOS10注冊APNs所需頭文件
#ifdef NSFoundationVersionNumber_iOS_9_x_Max
#import <UserNotifications/UserNotifications.h>
#endif
// 如果需要使用idfa功能所需要引入的頭文件(可選)
#import <AdSupport/AdSupport.h>
為AppDelegate添加Delegate
< JPUSHRegisterDelegate >
- 7:核心代碼: 添加初始化代碼
添加初始化APNs代碼###
請將以下代碼添加到
-(BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
//Required
//notice: 3.0.0及以后版本注冊可以這樣寫毡们,也可以繼續(xù)用之前的注冊方式
JPUSHRegisterEntity * entity = [[JPUSHRegisterEntity alloc] init];
entity.types = JPAuthorizationOptionAlert|JPAuthorizationOptionBadge|JPAuthorizationOptionSound;
if ([[UIDevice currentDevice].systemVersion floatValue] >= 8.0) {
// 可以添加自定義categories
// NSSet<UNNotificationCategory *> *categories for iOS10 or later
// NSSet<UIUserNotificationCategory *> *categories for iOS8 and iOS9
}
[JPUSHService registerForRemoteNotificationConfig:entity delegate:self];
添加初始化JPush代碼###
// Optional
// 獲取IDFA
// 如需使用IDFA功能請?zhí)砑哟舜a并在初始化方法的advertisingIdentifier參數(shù)中填寫對應(yīng)值
// NSString *advertisingId = [[[ASIdentifierManager sharedManager] advertisingIdentifier] UUIDString];
// Required
// init Push
// notice: 2.1.5版本的SDK新增的注冊方法漓踢,改成可上報IDFA,如果沒有使用IDFA直接傳nil
// 如需繼續(xù)使用pushConfig.plist文件聲明appKey等配置內(nèi)容漏隐,請依舊使用[JPUSHService setupWithOption:launchOptions]方式初始化喧半。
[JPUSHService setupWithOption:launchOptions appKey:appKey
channel:channel
apsForProduction:isProduction
advertisingIdentifier:nil];
注冊APNs成功并上報DeviceToken###
- (void)application:(UIApplication *)applicationdidRegisterForRemoteNotificationsWithDeviceToken:(NSData *)deviceToken {
/// Required - 注冊 DeviceToken
[JPUSHService registerDeviceToken:deviceToken];
}
實(shí)現(xiàn)注冊APNs失敗接口(可選)###
- (void)application:(UIApplication *)application didFailToRegisterForRemoteNotificationsWithError:(NSError *)error {
//Optional
NSLog(@"did Fail To Register For Remote Notifications With Error: %@",error);
}
添加處理APNs通知回調(diào)方法###
下面這幾個方法也是核心代碼,這是對通知的回調(diào)方法,通知達(dá)到之后會調(diào)用這下面的方法,所以說也是必須要實(shí)現(xiàn)的.JPush考慮很周全,涉及到了各個版本,但是方法太多,要是能一個方法處理完就更好了.
#pragma mark- JPUSHRegisterDelegate
// iOS 10 Support
- (void)jpushNotificationCenter:(UNUserNotificationCenter *)center willPresentNotification:(UNNotification *)notification withCompletionHandler:(void (^)(NSInteger))completionHandler {
// Required
NSDictionary * userInfo = notification.request.content.userInfo;
if([notification.request.trigger isKindOfClass:[UNPushNotificationTrigger class]]) {
[JPUSHService handleRemoteNotification:userInfo];
}
completionHandler(UNNotificationPresentationOptionAlert); // 需要執(zhí)行這個方法,選擇是否提醒用戶青责,有Badge挺据、Sound、Alert三種類型可以選擇設(shè)置
}
// iOS 10 Support
- (void)jpushNotificationCenter:(UNUserNotificationCenter *)center didReceiveNotificationResponse:(UNNotificationResponse *)response withCompletionHandler:(void (^)())completionHandler {
// Required
NSDictionary * userInfo = response.notification.request.content.userInfo;
if([response.notification.request.trigger isKindOfClass:[UNPushNotificationTrigger class]]) {
[JPUSHService handleRemoteNotification:userInfo];
}
completionHandler(); // 系統(tǒng)要求執(zhí)行這個方法
}
- (void)application:(UIApplication *)application didReceiveRemoteNotification:(NSDictionary *)userInfo fetchCompletionHandler:(void (^)(UIBackgroundFetchResult))completionHandler {
// Required, iOS 7 Support
[JPUSHService handleRemoteNotification:userInfo];
completionHandler(UIBackgroundFetchResultNewData);
}
- (void)application:(UIApplication *)application didReceiveRemoteNotification:(NSDictionary *)userInfo {
// Required,For systems with less than or equal to iOS6
[JPUSHService handleRemoteNotification:userInfo];
}
調(diào)用,成功打印:###
2016-08-19 17:12:12.745823 219b28[1443:286814] | JPUSH | I - [JPUSHLogin]
----- login result -----
uid:5460310207
registrationID:171976fa8a8620a14a4
程序到這,也就基本集成完畢:
8:還有推送的一些新特性極光新特性地址
這樣就能給你推送添加操作:
具體代碼:
UNNotificationAction *closeAction = [UNNotificationAction actionWithIdentifier:@"close" title:@"關(guān)閉" options:UNNotificationActionOptionDestructive];
UNNotificationAction *enterAction = [UNNotificationAction actionWithIdentifier:@"enter" title:@"進(jìn)入" options:UNNotificationActionOptionForeground];
UNNotificationAction *unLockAction = [UNNotificationAction actionWithIdentifier:@"unLock" title:@"解鎖" options:UNNotificationActionOptionAuthenticationRequired];
UNTextInputNotificationAction *inputAction = [UNTextInputNotificationAction actionWithIdentifier:@"input" title:@"輸入" options:UNNotificationActionOptionAuthenticationRequired]; UNNotificationCategory *category = [UNNotificationCategory categoryWithIdentifier:@"comment-reply" actions:@[inputAction,enterAction,unLockAction,closeAction] intentIdentifiers:@[] options:UNNotificationCategoryOptionNone];
[[UNUserNotificationCenter currentNotificationCenter] setNotificationCategories:[NSSet setWithObject:category]];
iOS 10 想要對這些操作action處理:
- (void)jpushNotificationCenter:(UNUserNotificationCenter *)center didReceiveNotificationResponse:(UNNotificationResponse *)response withCompletionHandler:(void (^)())completionHandler {
// Required
NSString *identifier = response.actionIdentifier;
if ([identifier isEqualToString:@"close"]) {
//對輸入的文字作處理
NSLog(@"close");
}else if ([identifier isEqualToString:@"input"]){
//
NSLog(@"input");
}else if ([identifier isEqualToString:@"enter"]){
//enter
NSLog(@"enter");
}else if ([identifier isEqualToString:@"unLock"]){
//enter
NSLog(@"unLock");
}
NSLog(@"didReceiveNotificationResponse:response == %@",response);
NSLog(@"didReceiveNotificationResponse:center == %@",center);
NSDictionary * userInfo = response.notification.request.content.userInfo;
if([response.notification.request.trigger isKindOfClass: [UNPushNotificationTrigger class]]) {
[JPUSHService handleRemoteNotification:userInfo];
}
completionHandler(); // 系統(tǒng)要求執(zhí)行這個方法
}
iOS 9 想要對這些操作action處理:
- (void)application:(UIApplication *)applicationhandleActionWithIdentifier:(NSString *)identifier forRemoteNotification:(NSDictionary *)userInfo completionHandler:(void (^)())completionHandler {
if ([identifier isEqualToString:@"close"]) {
//對輸入的文字作處理
NSLog(@"close");
NSLog(@"forRemoteNotification == %@",userInfo);
}else if ([identifier isEqualToString:@"input"]){
//
NSLog(@"input");
NSLog(@"forRemoteNotification == %@",userInfo);
}else if ([identifier isEqualToString:@"enter"]){
//enter
NSLog(@"enter");
NSLog(@"forRemoteNotification == %@",userInfo);
}else if ([identifier isEqualToString:@"unLock"]){
//enter
NSLog(@"unLock");
NSLog(@"forRemoteNotification == %@",userInfo);
}
completionHandler();
}
iOS 8 想要對這些操作action處理:
- (void)application:(UIApplication *)application handleActionWithIdentifier:(NSString *)identifier forLocalNotification:(UNNotificationRequest *)notificatio completionHandler:(void (^)())completionHandler {
if ([identifier isEqualToString:@"close"]) {
//對輸入的文字作處理
NSLog(@"close");
NSLog(@"forRemoteNotification == %@",userInfo);
}else if ([identifier isEqualToString:@"input"]){
//
NSLog(@"input");
NSLog(@"forRemoteNotification == %@",userInfo);
}else if ([identifier isEqualToString:@"enter"]){
//enter
NSLog(@"enter");
NSLog(@"forRemoteNotification == %@",userInfo);
}else if ([identifier isEqualToString:@"unLock"]){
//enter
NSLog(@"unLock");
NSLog(@"forRemoteNotification == %@",userInfo);
}
completionHandler();
}
上面三個方法還可以對附件:attachment操作處理;
9:這里還介紹一下關(guān)于設(shè)置tags和alias
/*!
* 下面的接口是可選的
* 設(shè)置標(biāo)簽和(或)別名(若參數(shù)為nil脖隶,則忽略扁耐;若是空對象,則清空产阱;詳情請 參考文檔:https://docs.jiguang.cn/jpush/client/iOS/ios_api/)
* setTags:alias:fetchCompletionHandle:是新的設(shè)置標(biāo)簽別名的方法婉称,不再需要顯示聲明回調(diào)函數(shù),只需要在block里面處理設(shè)置結(jié)果即可.
* WARN: 使用block時需要注意循環(huán)引用問題
*/
+ (void)setTags:(NSSet *)tags alias:(NSString *)alias callbackSelector(SEL)cbSelector object:(id)theTarget;
10:設(shè)置Badge
+ (BOOL)setBadge:(int)value
清空J(rèn)Push服務(wù)器中存儲的badge值构蹬,即 [setBadge:0]
+ (void)resetBadge
11:API 用于移除待推送或已在通知中心顯示的推送(支持iOS10王暗,并兼容iOS10以下版本)
+ (void)removeNotification:(JPushNotificationIdentifier *)identifier;
iOS10以上identifier設(shè)置為nil,則移除所有在通知中心顯示推送和待推送請求庄敛,也可以通過設(shè)置identifier.delivered和identifier.identifiers來移除相應(yīng)在通知中心顯示推送或待推送請求俗壹,identifier.identifiers如果設(shè)置為nil或空數(shù)組則移除相應(yīng)標(biāo)志下所有在通知中心顯示推送或待推送請求;iOS10以下identifier設(shè)置為nil藻烤,則移除所有推送绷雏,identifier.delivered屬性無效,另外可以通過identifier.notificationObj傳入特定推送對象來移除此推送怖亭。
12:極光還有下面的功能(因為項目沒有集成,沒有仔細(xì)研究):極光響應(yīng)SDK地址
- AddNotification: 廣告推送
- FindNotification: 查詢推送
- SetLocalNotification: 地理推送
- clearAllLocalNotification:用于清除所有注冊的通知
花了一周時間學(xué)習(xí)極光推送,雖然時間有點(diǎn)長,但是對于我自己來說很不錯了,沉下心來慢慢學(xué)東西,不管外面iOS多么多么慘,但是只要一天iOS不倒,我還會堅持學(xué)習(xí),堅持學(xué)