如果app需要开启远程推送功能,自己写下来就会相对较麻烦,所以我选择了极光推送
一.证书下载
这里的证书,是创建开发环境和生产环境的证书 ,来开启你app的推送服务
首先进入苹果开发者中心
登录之后点击Certificates,Identifiers & Profiles
创建App ID
注意一点:
App ID的名字可以随便取,Bundle ID一定要注意,要推送的App项目中的Bundle ID一定要是这个Bundle ID
App Services可以现在勾上Push Notifications,也可以后面再改,然后点continue(建议直接勾,能做一次的事情何必做两次呢)
勾选了Push Notifications,所有它现在是橙色的,不然应该是灰色
出来后点击你刚创建的App ID,然后点Edit
单击你刚创建的App ID,点击edit
创建开发环境和生产环境的证书(你用Xcode编译安装的就是开发环境,用二维码或者App Store下载的就是生产环境.)
在创建证书期间,需要你上传一个证书,
打开钥匙来制作这个证书
打开MAC自带的钥匙串访问(Launchpad->其他->钥匙串访问)
点开后左上角打开证书助手,从证书颁发机构请求证书
注意:要存储到磁盘
然后选择存储路径
这时候将制作的证书上传了
下载下来,点击Done,又回跳回到开始的界面,然后还是选择你创建的App ID然后Edit,开发环境和生产环境推送证书的创建流程是一样的,自己按着步骤就能把证书全部创建并下载成功.
这时候Push Notifications应该是绿的了
打开钥匙串访问,你会发现你多了这两个证书
右键分别导出它们
设置密码(这里的密码将会在极光推送管理平台上进行验证?)
导出成功后,命名最好用英文名
二.极光推送开发者身份
ok,证书的问题先告一段落了,下一步,注册极光推送的开发者账号
如果你没有注册,先在极光官网进行注册
创建一个应用
在应用配置中导入两个证书(我这是已经验证了的,不然就是让你上传证书的按钮)
Bundle ID是导入证书后自动出现的,证书最好一个一个上传不然可能会出现验证失败的问题.
然后下载SDK
三.工程
把SDK中的Lib文件夹导入你的项目中,记得勾选Copy
导入相关库
在Build Phases中导入以下库
----Jpush-iOS10的问题
修改Capabilities
打开远程推送
打开Background Modes
修改Bundle ID 以及选择Team(推送无法在模拟机上测试)
四.代码
ok,环境搞定,开始代码
在代理的.h中
staticNSString*appKey =@"2dd13edbb353c542440ab572";
staticNSString*channel =@"Publish channel";
staticBOOLisProduction =FALSE;
h
代码1:
在代理的.m中
记得必须添加
/**
自己的信息填写
*/
- (BOOL)application:(UIApplication*)application didFinishLaunchingWithOptions:(NSDictionary*)launchOptions {
// self.window.backgroundColor = [UIColor whiteColor];
// [self.window makeKeyAndVisible];
if([[UIDevicecurrentDevice].systemVersionfloatValue] >=8.0) {
[JPUSHServiceregisterForRemoteNotificationTypes:UIUserNotificationTypeBadge|UIUserNotificationTypeSound|UIUserNotificationTypeAlertcategories:nil];
}else{
[JPUSHServiceregisterForRemoteNotificationTypes:UIUserNotificationTypeBadge|UIUserNotificationTypeSound|UIUserNotificationTypeAlertcategories:nil];
}
[JPUSHServicesetupWithOption:launchOptionsappKey:appKeychannel:channelapsForProduction:NO];
returnYES;
}
/**
Token方法中注册设备
*/
- (void)application:(UIApplication*)application didRegisterForRemoteNotificationsWithDeviceToken:(NSData*)deviceToken {
// Required
[JPUSHServiceregisterDeviceToken:deviceToken];
}
- (void)application:(UIApplication*)application didReceiveRemoteNotification:(NSDictionary*)userInfo {
// Required,For systems with less than or equal to iOS6
[JPUSHServicehandleRemoteNotification:userInfo];
}
/**
:App在后台时收到推送时的处理
*/
- (void)application:(UIApplication*)application didReceiveRemoteNotification:(NSDictionary*)userInfo fetchCompletionHandler:(void(^)(UIBackgroundFetchResult))completionHandler {
// IOS 7 Support Required
[JPUSHServicehandleRemoteNotification:userInfo];
completionHandler(UIBackgroundFetchResultNewData);
}
/**
创建didFailToRegisterForRemoteNotificationsWithError方法,处理接收推送错误的情况(一般不会…)
*/
- (void)application:(UIApplication*)application didFailToRegisterForRemoteNotificationsWithError:(NSError*)error {
//Optional
NSLog(@"did Fail To Register For Remote Notifications With Error: %@", error);
}
/**
在applicationWillEnterForeground方法(App即将进入前台)中将小红点清除
*/
- (void)applicationWillEnterForeground:(UIApplication*)application {
// Called as part of the transition from the background to the active state; here you can undo many of the changes made on entering the background.
NSLog(@"进入前台");
[UIApplicationsharedApplication].applicationIconBadgeNumber=0;
}
代码2:
/**
自己的信息填写
*/
- (BOOL)application:(UIApplication*)application didFinishLaunchingWithOptions:(NSDictionary*)launchOptions {
if([[UIDevicecurrentDevice].systemVersionfloatValue] >=10.0) {
JPUSHRegisterEntity* entity = [[JPUSHRegisterEntityalloc]init];
entity.types=UNAuthorizationOptionAlert|UNAuthorizationOptionBadge|UNAuthorizationOptionSound;
[JPUSHServiceregisterForRemoteNotificationConfig:entitydelegate:self];
}
elseif([[UIDevicecurrentDevice].systemVersionfloatValue] >=8.0) {
//可以添加自定义categories
[JPUSHServiceregisterForRemoteNotificationTypes:(UIUserNotificationTypeBadge|
UIUserNotificationTypeSound|
UIUserNotificationTypeAlert)
categories:nil];
}
else{
//categories必须为nil
[JPUSHServiceregisterForRemoteNotificationTypes:(UIRemoteNotificationTypeBadge|
UIRemoteNotificationTypeSound|
UIRemoteNotificationTypeAlert)
categories:nil];
}
[JPUSHServicesetupWithOption:launchOptionsappKey:appKey
channel:channel
apsForProduction:isProduction
advertisingIdentifier:nil];//这里是没有advertisingIdentifier的情况,有的话,大家在自行添加
//注册远端消息通知获取device token
[applicationregisterForRemoteNotifications];
returnYES;
}
/**
Token方法中注册设备
*/
- (void)application:(UIApplication*)application didRegisterForRemoteNotificationsWithDeviceToken:(NSData*)deviceToken {
// Required
[JPUSHServiceregisterDeviceToken:deviceToken];
}
- (void)application:(UIApplication*)application didReceiveRemoteNotification:(NSDictionary*)userInfo {
// Required,For systems with less than or equal to iOS6
[JPUSHServicehandleRemoteNotification:userInfo];
}
// ios 10 support处于前台时接收到通知
- (void)jpushNotificationCenter:(UNUserNotificationCenter*)center willPresentNotification:(UNNotification*)notification withCompletionHandler:(void(^)(NSInteger))completionHandler
{
NSDictionary* userInfo = notification.request.content.userInfo;
if([notification.request.triggerisKindOfClass:[UNPushNotificationTriggerclass]]) {
[JPUSHServicehandleRemoteNotification:userInfo];
//添加各种需求。。。。。
}
completionHandler(UNNotificationPresentationOptionAlert);
//处于前台时,添加需求,一般是弹出alert跟用户进行交互,这时候completionHandler(UNNotificationPresentationOptionAlert)这句话就可以注释掉了,这句话是系统的alert,显示在app的顶部,
}
/**
:App在后台时收到推送时的处理
*/
- (void)application:(UIApplication*)application didReceiveRemoteNotification:(NSDictionary*)userInfo fetchCompletionHandler:(void(^)(UIBackgroundFetchResult))completionHandler {
// IOS 7 Support Required
[JPUSHServicehandleRemoteNotification:userInfo];
completionHandler(UIBackgroundFetchResultNewData);
}
/**
创建didFailToRegisterForRemoteNotificationsWithError方法,处理接收推送错误的情况(一般不会…)
*/
- (void)application:(UIApplication*)application didFailToRegisterForRemoteNotificationsWithError:(NSError*)error {
//Optional
NSLog(@"did Fail To Register For Remote Notifications With Error: %@", error);
}
/**
在applicationWillEnterForeground方法(App即将进入前台)中将小红点清除
*/
- (void)applicationWillEnterForeground:(UIApplication*)application {
// Called as part of the transition from the background to the active state; here you can undo many of the changes made on entering the background.
NSLog(@"进入前台");
[applicationsetApplicationIconBadgeNumber:0];
[applicationcancelAllLocalNotifications];
}
遇到的一个问题:
Undefined symbols for architecture arm64:
"_dns_parse_resource_record", referenced from:
-[JPUSHSRVResolver processRecord:length:] in jpush-ios-2.2.0.a(JPUSHSRVResolver.o)
"_dns_free_resource_record", referenced from:
-[JPUSHSRVResolver processRecord:length:] in jpush-ios-2.2.0.a(JPUSHSRVResolver.o)
ld: symbol(s) not found for architecture arm64
clang: error: linker command failed with exit code 1 (use -v to see invocation)
解决方案:
添加libresolv.tbd库,即可解决问题
效果:
参考资料:(理解消息推送机制)
资料一
资料二
参考教程:(配置)
教程