iOS SDK配置

本章节介绍移动推送iOS SDK的集成操作。

前提条件

样例代码

移动推送服务iOS SDK接入工程样例参见移动推送iOS Demo

集成步骤

  1. 添加依赖

    1. 方式一:手动添加

      1. 解压下载好的SDK包,在Xcode中,把SDK包目录中的framework拖入对应Target下即可,在弹出框勾选Copy items if needed

        CloudPushSDK.framework
        AlicloudUtils.framework
        UTDID.framework
      2. 在工程项目中(Build Phases -> Link Binary With Libraries)添加以下库文件。

        libz.tbd
        libresolv.tbd
        CoreTelephony.framework
        SystemConfiguration.framework
        libsqlite3.tbd
    2. 方式二:Pod集成

      1. 在Podfile中添加source,指定Master仓库和阿里云仓库。

        source 'https://github.com/CocoaPods/Specs.git'
        source 'https://github.com/aliyun/aliyun-specs.git'
      2. 在终端执行 pod repo add命令,拉取阿里云Pod仓库到本地 。

        pod repo add AliyunRepo https://github.com/aliyun/aliyun-specs.git

        或手动拉取Pod仓库工程到CocoaPods仓库(默认为~/.cocoapods/repos)。

        git clone https://github.com/aliyun/aliyun-specs.git ~/.cocoapods/repos/
        重要
        • 可执行pod repo list查看本地 Pod 仓库信息。

        • pod repo list或git clone失败一般为GitHub账号publicKey配置问题,请仔细核对错误信息,Pod命令使用参考官方文档

      3. 在您的工程中添加以下系统依赖库。

        pod 'AlicloudPush', '2.1.0'
  2. 引入头文件

    #import <CloudPushSDK/CloudPushSDK.h>
  3. Objc配置

    iOS端集成SDK时需要做 -ObjC 配置 ,即应用的 TARGETS -> Build Settings -> Linking -> Other Linker Flags ,需添加上 -ObjC 这个属性,否则推送服务无法正常使用 。

    Other Linker Flags中设定链接器参数-ObjC,加载二进制文件时,会将 Objective-C 类和 Category 一并载入 ,若工程依赖多个三方库 ,将所有 Category 一并加载后可能发生冲突,可以使用 -force_load 单独载入指定二进制文件,配置如下 :

    -force_load<framework_path>/CloudPushSDK.framework/CloudPushSDK
    重要

    -force_load指定的是二进制文件路径,而不是 Framework 目录。若指定为 Framework 目录,-force_load …path/xxx.framework,Xcode 会报出错误 ld: can’t map file, errno=22 file ‘…path/xxx.framework’ for architecture armv7。

  4. SDK初始化配置

    在Xcode中把下载好的配置文件(AliyunEmasServices-Info.plist)拖入对应App Target下即可,在弹出框勾选Copy items if needed

    说明
    • 配置文件aliyunEmasServices-Info.plist中包含SDK初始化所需的配置信息,用户只需要调用autoInit接口进行初始化,无需手动输入配置信息。

    • 下载配置文件的具体操作参考EMAS快速入门 > 下载配置文件

    请参照以下代码完成SDK的初始化。

    说明
    • 您可在下载好的配置文件中获取Appkey、AppSecret,或参考EMAS快速入门

    • 百川云推送迁移过来的用户,不要使用百川平台获取到的Appkey、AppSecret,请使用EMAS平台获取的AppKey及AppSecret,否则会发生鉴权错误。

    - (void)initCloudPush {
        // SDK初始化
        [CloudPushSDK asyncInit:@"*****" appSecret:@"*****" callback:^(CloudPushCallbackResult *res) {
            if (res.success) {
                NSLog(@"Push SDK init success, deviceId: %@.", [CloudPushSDK getDeviceId]);
            } else {
                NSLog(@"Push SDK init failed, error: %@", res.error);
            }
        }];
    }

    向苹果APNs注册获取deviceToken,并上报到阿里云推送服务器:

    /**
     *    注册苹果推送,获取deviceToken用于推送
     *
     *    @param     application
     */
    - (void)registerAPNS:(UIApplication *)application {
        if ([[[UIDevice currentDevice] systemVersion] floatValue] >= 8.0) {
            // iOS 8 Notifications
            [application registerUserNotificationSettings:
             [UIUserNotificationSettings settingsForTypes:
              (UIUserNotificationTypeSound | UIUserNotificationTypeAlert | UIUserNotificationTypeBadge)
                                               categories:nil]];
            [application registerForRemoteNotifications];
        }
        else {
            // iOS < 8 Notifications
            [[UIApplication sharedApplication] registerForRemoteNotificationTypes:
             (UIRemoteNotificationTypeAlert | UIRemoteNotificationTypeBadge | UIRemoteNotificationTypeSound)];
        }
    }
    /*
     *  苹果推送注册成功回调,将苹果返回的deviceToken上传到CloudPush服务器
     */
    - (void)application:(UIApplication *)application didRegisterForRemoteNotificationsWithDeviceToken:(NSData *)deviceToken {
        [CloudPushSDK registerDevice:deviceToken withCallback:^(CloudPushCallbackResult *res) {
            if (res.success) {
                NSLog(@"Register deviceToken success.");
            } else {
                NSLog(@"Register deviceToken failed, error: %@", res.error);
            }
        }];
    }
    /*
     *  苹果推送注册失败回调
     */
    - (void)application:(UIApplication *)application didFailToRegisterForRemoteNotificationsWithError:(NSError *)error {
        NSLog(@"didFailToRegisterForRemoteNotificationsWithError %@", error);
    }

    推送消息到来监听:

    /**
     *    注册推送消息到来监听
     */
    - (void)registerMessageReceive {
        [[NSNotificationCenter defaultCenter] addObserver:self
                                                 selector:@selector(onMessageReceived:)
                                                     name:@"CCPDidReceiveMessageNotification"
                                                   object:nil];
    }
    /**
     *    处理到来推送消息
     *
     *    @param     notification
     */
    - (void)onMessageReceived:(NSNotification *)notification {
        CCPSysMessage *message = [notification object];
        NSString *title = [[NSString alloc] initWithData:message.title encoding:NSUTF8StringEncoding];
        NSString *body = [[NSString alloc] initWithData:message.body encoding:NSUTF8StringEncoding];
        NSLog(@"Receive message title: %@, content: %@.", title, body);
    }

    通知打开监听:

    - (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
        // 点击通知将App从关闭状态启动时,将通知打开回执上报
        // [CloudPushSDK handleLaunching:launchOptions];(Deprecated from v1.8.1)
        [CloudPushSDK sendNotificationAck:launchOptions];
        return YES;
    }
    /*
     *  App处于启动状态时,通知打开回调
     */
    - (void)application:(UIApplication*)application didReceiveRemoteNotification:(NSDictionary*)userInfo {
        NSLog(@"Receive one notification.");
        // 取得APNS通知内容
        NSDictionary *aps = [userInfo valueForKey:@"aps"];
        // 内容
        NSString *content = [aps valueForKey:@"alert"];
        // badge数量
        NSInteger badge = [[aps valueForKey:@"badge"] integerValue];
        // 播放声音
        NSString *sound = [aps valueForKey:@"sound"];
        // 取得Extras字段内容
        NSString *Extras = [userInfo valueForKey:@"Extras"]; //服务端中Extras字段,key是自己定义的
        NSLog(@"content = [%@], badge = [%ld], sound = [%@], Extras = [%@]", content, (long)badge, sound, Extras);
        // iOS badge 清0
        application.applicationIconBadgeNumber = 0;
        // 通知打开回执上报
        // [CloudPushSDK handleReceiveRemoteNotification:userInfo];(Deprecated from v1.8.1)
        [CloudPushSDK sendNotificationAck:userInfo];
    }
    重要
    • iOS 10系统的设备需注意,基于工信部的要求,国行手机首次安装App时,会弹出一个询问用户“是否允许应用访问数据”的弹框。在用户点击允许前,或点击不允许,App的网络环境是不同的,会导致推送SDK的初始化失败,推送服务不能正常使用。推送各接口内部是有重试机制的,但是,建议用户在业务层,也要捕获处理SDK接口错误回调,确保正确获知SDK接口调用状态。

    • 移动推送iOS SDK已经完成ATS适配,请求都以HTTPS发出,无需在Info.plist中进行ATS配置。

    • 若SDK集成过程中出现UTDID冲突,请参考 阿里云-云产品SDK UTDID冲突解决方案

  5. 初始化成功验证

    根据SDK初始化回调结果查看是否成功。

     if (res.success) {
        NSLog(@"Push SDK init success, deviceId: %@.", [CloudPushSDK getDeviceId]);
    } else {
        NSLog(@"Push SDK init failed, error: %@", res.error);
    }

常见集成问题

  1. iOS SDK集成出错排查步骤

  2. iOS端推送失败排查步骤

  3. iOS端获取deviceToken的问题