均是第三方提供的用于更有利地钦点推送目标的

2019-09-11 20:50栏目:大奖888官网登录
TAG:

本文旨在对 iOS 推送进行一个完整的剖析,如果你之前对推送一无所知,那么在你认真地阅读了全文后必将变成一个推送老手,你将会对其中的各种细节和原理有充分的理解。以下是 pikacode 使用 iOS 推送的一些经验,欢迎互相交流,指出错漏之处。

准备篇

本文旨在对 iOS 推送进行一个完整的剖析,如果你之前对推送一无所知,那么在你认真地阅读了全文后必将变成一个推送老手,你将会对其中的各种细节和原理有充分的理解。以下是 pikacode 使用 iOS 推送的一些经验,欢迎互相交流,指出错漏之处。

推送服务可以说是所有 App 的标配,不论是哪种类型的 App,推送都从很大程度上决定了 App 的 打开率、使用率、存活率 。因此,熟知并掌握推送原理及方法,对每一个开发者来说都是必备技能,对每一个依赖 App 的公司来说都至关重要。

Tip 1:推送通知(Push Notification)必须购买Apple开发者账号,并使用特定的推送证书

  • 使用免费账号不能推送。
  • 如果使用第三方推送服务,比如【极光推送】,也必须购买开发者账号。因为所有的第三方都会将推送请求发送至APNs(Apple Push Notification service 苹果推送通知服务),所有推送均是由APNs下发。
  • 如何注册及正确的配置证书,参考这里iOS-推送证书设置指南;

推送服务可以说是所有 App 的标配,不论是哪种类型的 App,推送都从很大程度上决定了 App 的 打开率、使用率、存活率 。因此,熟知并掌握推送原理及方法,对每一个开发者来说都是必备技能,对每一个依赖 App 的公司来说都至关重要。

从 iOS 10 新增的 UserNotifications Framework 可以发现,Apple 整合了原有散乱的 API,并且增加了许多强大的功能。以 Apple 官方的角度来看,也必然是相当重视推送服务对 App 的影响、以及对 Apple iOS 生态圈长远发展的影响。

原理篇

从 iOS 10 新增的UserNotifications Framework可以发现,Apple 整合了原有散乱的 API,并且增加了许多强大的功能。以 Apple 官方的角度来看,也必然是相当重视推送服务对 App 的影响、以及对 Apple iOS 生态圈长远发展的影响。

  • 使用免费帐号不能推送。
  • 那如果我们使用的是第三方推送服务呢?比如「极光推送」。也必须购买开发者帐号。因为所有的第三方都会将推送请求发至 APNs(Apple Push Notification service 苹果推送通知服务),所有推送均是由 APNs 下发。
  • 如何注册及正确的配置证书,参考这里 iOS 证书设置指南。

Tip 2:推送通知本身是iOS系统的行为

所以在App没有运行(没有在前台也没有在后台)的时候:

  • 仍然可以推送及接收(通知中心通知、顶部横幅、刷新App右上角的小圆点【即badge,以下简称角标】等都会有系统来控制和展示)。
  • 收到推送时,是无法在App的代码中获取到通知内容的。因为沙盒机制,此时App的任何代码都不可能被执行。

准备篇

Tip 3:手机向APNs注册推送服务

  1. 在代码中注册推送服务:
#ifdef __IPHONE_8_0
    if ([[UIApplication sharedApplication] respondsToSelector:@selector(registerUserNotificationSettings:)]) {
        UIUserNotificationSettings *settings = [UIUserNotificationSettings settingsForTypes:UIUserNotificationTypeBadge | UIUserNotificationTypeSound | UIUserNotificationTypeAlert categories:nil];
        [[UIApplication sharedApplication] registerUserNotificationSettings:settings];
    } else {
        UIRemoteNotificationType myTypes = UIRemoteNotificationTypeBadge | UIRemoteNotificationTypeAlert | UIRemoteNotificationTypeSound;
        [[UIApplication sharedApplication] registerForRemoteNotificationTypes:myTypes];
#else
        UIRemoteNotificationType myTypes = UIRemoteNotificationTypeBadge | UIRemoteNotificationTypeAlert | UIRemoteNotificationTypeSound;
        [[UIApplication sharedApplication] registerForRemoteNotificationTypes:myTypes];
#endif
  1. 在第一次触发这段代码的时候,会有一个系统弹窗,询问你是否允许该App要给你推送信息。当你选择允许的时候,系统会打包“App + 手机唯一标识 + 证书”信息发送至“APNs服务器”,注册推送服务,APNs系统会对该手机安装的该App是否有推送权限进行验证。所以必须是加入了Apple Device 的手机,使用对应App的推送证书才能够成功注册。

  2. 如果注册成功,则可以在AppDelegate.m的如下方法中获取到deviceToken,它是对“该手机 + 该App ”组合的一个唯一标识。当使用远程推送时,只需要将推送消息发给指定的deviceToken就可以使推送信息传达给指定手机的指定App上。因此如果你使用第三方,就需要在这个方法里将deviceToken传给第三方。(iOS 9 为了更好的保护用户隐私,会出现多次重复/安装App导致deviceToken不断变化的情况。有时会出现一条推送手机会收到2次的问题,属于iOS 9 的系统问题)。

-(void)application:(UIApplication *)application didRegisterForRemoteNotificationsWithDeviceToken:(NSData *)deviceToken {  
    [JPUSHService registerDeviceToken:deviceToken];//将 deviceToken 传给极光推送
}
  1. 如果以上步骤均成功,此时你能够取到第三方提供的设备注册 id。能否取到该 id 值,可以作为判断设备是否能够成功推送的标准(点Tip 6 - Registration ID)。因为当你取到该值时,必然:
  • 推送证书配置正确(你拥有了推送权限)。
  • 设备成功在APNs注册并返回了deviceToken(APNs能识别你的设备了)。
  • 返回的deviceToken传给第三方,成功在第三方生成了唯一标识注册 id(第三方能将你的设备信息传给APNs了)。
  1. 综上,注册及接收推送必须使用真机,必须连网。

Tip 1:推送通知(Push Notification)必须购买 Apple 开发者账号,并使用特定的推送证书

  • 使用免费帐号不能推送。
  • 那如果我们使用的是第三方推送服务(以下简称第三方)呢?比如「极光推送」。也必须购买开发者帐号。因为所有的第三方都会将推送请求发至 APNs(Apple Push Notification service 苹果推送通知服务),所有推送均是由 APNs 下发。
  • 如何注册及正确的配置证书,参考这里 iOS 证书设置指南。
  • 仍然能够推送及接收(通知中心通知、顶部横幅、刷新 App 右上角的小圆点即 badge [以下简称角标] 等都会由系统来控制和展示)。
  • 收到推送时,是无法在 App 的代码中获取到通知内容的。因为沙盒机制,此时 App 的任何代码都不可能被执行。

Tip 4:推送通知从服务端 --> App代码的过程

  1. 使用你们公司或第三方的服务端向APNs发送推送请求(请参考苹果 APNs 的相关资料,或者第三方推送提供了更简单的 REST API)。
  2. APNs 接收并验证推送请求。
  3. APNs 找到设备下发推送。
  4. 手机收到推送通知,系统根据App状态进行处理:
    • 前台收到:
      • 系统会将通知内容传到didReceiveRemoteNotification
    • 后台收到:
      • 如果开启了Remote Notification,系统将推送传到didReceiveRemoteNotification:fetchCompletionHandler:,(见Tip 5 - 后台推送),否则此时代码中收不到推送。
      • 展示横幅、通知中心、声音、角标。
    • 退出收到:
      • 如果点击 推送横幅/通知中心,而启动App,系统将通知传到didFinishLaunchingWithOptions
      • 展示横幅、通知中心、声音、角标。

原理篇

  1. 在代码中注册推送服务:

    #ifdef __IPHONE_8_0if ([[UIApplication sharedApplication] respondsToSelector:@selector(registerUserNotificationSettings:)]) { UIUserNotificationSettings *settings = [UIUserNotificationSettings settingsForTypes:UIUserNotificationTypeBadge| UIUserNotificationTypeSound|UIUserNotificationTypeAlert categories:nil]; [[UIApplication sharedApplication] registerUserNotificationSettings:settings];} else { UIRemoteNotificationType myTypes = UIRemoteNotificationTypeBadge | UIRemoteNotificationTypeAlert | UIRemoteNotificationTypeSound; [[UIApplication sharedApplication] registerForRemoteNotificationTypes:myTypes];
    

推送通知内容篇

Tip 2:推送通知本身是 iOS 系统的行为,所以在 App 没有运行(没有在前台也没有在后台)的时候:

  • 仍然能够推送及接收(通知中心通知、顶部横幅、刷新 App 右上角的小圆点即badge[以下简称角标] 等都会由系统来控制和展示)。
  • 收到推送时,是无法在 App 的代码中获取到通知内容的。因为沙盒机制,此时 App 的任何代码都不可能被执行。

}#elseUIRemoteNotificationType myTypes = UIRemoteNotificationTypeBadge | UIRemoteNotificationTypeAlert | UIRemoteNotificationTypeSound;[[UIApplication sharedApplication] registerForRemoteNotificationTypes:myTypes];#endif```

Tip 5:推送通知分为 本地/远程 2 种类型:

  • 本地通知:可指定推送时间,在该时间准时弹出推送通知。
  • 远程推送通知:分为 普通推送/后台推送/静默推送 3种类型。存在延迟问题(由于Tip 1 第 2 点,APNs的不稳定及高峰时段的巨量请求所致)。
    • 普通推送:
      • 就是我们在手机上平时见到的推送通知。包含声音、横幅、角标、自定义字段。
      • App:
        • 处于前台,不会展示横幅,可通过didReceiveRemoteNotification(iOS 7 before)didReceiveRemoteNotification:fetchCompletionHandler:(iOS 7 after)获取通知内容(前台展示横幅的方法看这里)。
        • 处于后台,会展示横幅,无法获取通知内容。
        • 处于退出,会展示横幅,无法获取通知内容。
        • 点击图标启动,无法获取通知内容。
        • 点击通知横幅启动,在didFinishLaunchingWithOptions获取通知内容。
      • 通知内容类似如下:
{
        "_j_msgid" = 200806057; // 第三方附带的 id,用于统计点击
        aps = {
            alert = "显示内容";
            badge = 1; // App 角标,可推送 n、+n、-n 来实现角标的固定、增加、减少
            sound = default; // 推送声音,默认系统三全音,如需使用自己的声音,需要将声音文件拖拽&拷贝至 Xcode 工程目录任意位置,并在推送时指定其文件名
        };
        key1 = value1; // 自定义字段,可设置多组,用于处理内部逻辑
        key2 = value2;
    }
  • 后台推送
    • 各种显示效果跟普通推送完全一样。
    • 必须携带"content-available" = 1;
    • 必须携带alertbadgesound至少 1 个字段
    • 仅 iOS 7 以后支持。
    • 必须在 Xcode 工程中:TARGETS -> Capabilities -> Background Modes -> Remote notifications 开启该功能,具体参照iOS 7 Background Remote Notification。
    • App:
      • 处于前台,可通过didReceiveRemoteNotification(iOS 7 before)didReceiveRemoteNotification:fetchCompletionHandler:(iOS 7 after) 获取通知内容。
      • 处于后台,可通过 didReceiveRemoteNotification:fetchCompletion Handler: 获取通知内容 // 获取情况中与普通推送的唯一不同点,此时 iOS 系统允许开发者在 App 处于后台的情况下,执行一些代码,大概提供几分钟的时间,可以用来偷偷的刷新 UI、切换页面、下载更新包等等操作。
      • 处于退出,无法获取通知内容。
      • 点击图标启动,无法获取通知内容。
      • 点击推送横幅启动,在 didFinishLaunchingWithOptions 获取通知内容。
    • 通知内容类似如下:
json
    {
        "_j_msgid" = 2090737306;
        aps =     {
            alert = "显示内容";
            badge = 1;
            "content-available" = 1;  // 必带字段
            sound = default;
        };
        key1 = value1;
    }
  • 静默推送
    • 没有任何展示效果。
    • 必须携带 "content-available" = 1;,因此静默必然是后台的。
    • 必须不携带 alertbadgesound
    • 可携带自定义字段。
    • App :
      • 处于前台,可通过didReceiveRemoteNotification(iOS 7 before)didReceiveRemoteNotification:fetchCompletionHandler:(iOS 7 after) 获取通知内容。
      • 处于后台,可通过 didReceiveRemoteNotification:fetchCompletion Handler: 获取通知内容 //获取情况中与普通推送的唯一不同点,此时 iOS 系统允许开发者在 App 处于后台的情况下,执行一些代码,大概提供几分钟的时间,可以用来偷偷的刷新 UI、切换页面、下载更新包等等操作。
      • 处于退出,无法获取通知内容。
    • 通知内容类似如下:
json
{
        "_j_msgid" = 3938587719;
        aps =     {
            alert = "";
            "content-available" = 1;  // 必带字段
        };
        key1 = value1;
    }

Tip 3:手机向 APNs 注册推送服务

  1. 在代码中注册推送服务:
#ifdef __IPHONE_8_0 
if ([[UIApplication sharedApplication] respondsToSelector:@selector(registerUserNotificationSettings:)]) 
{ 
UIUserNotificationSettings *settings = [UIUserNotificationSettings settingsForTypes:UIUserNotificationTypeBadge| UIUserNotificationTypeSound|UIUserNotificationTypeAlert categories:nil];
[[UIApplication sharedApplication] registerUserNotificationSettings:settings]; 
} else {
UIRemoteNotificationType myTypes = UIRemoteNotificationTypeBadge | UIRemoteNotificationTypeAlert | UIRemoteNotificationTypeSound; 
[[UIApplication sharedApplication] registerForRemoteNotificationTypes:myTypes];
} 
#else 
UIRemoteNotificationType myTypes = UIRemoteNotificationTypeBadge | UIRemoteNotificationTypeAlert | UIRemoteNotificationTypeSound; 
[[UIApplication sharedApplication] registerForRemoteNotificationTypes:myTypes];
#endif
  1. 在第一次触发这段代码的时候,会有一个系统弹窗,询问你是否允许该 App 要给你推送信息。当你选择允许时,系统会打包 App+手机唯一标识+证书 信息发送至 APNs 服务器注册推送服务,APNs 系统会对该手机安装的该 App 是否有推送权限进行验证,所以必须要加入了 Apple Deveice 的手机,使用对应 App 的推送证书才能够成功的注册。
  2. 如果注册成功,则可以在AppDelegate.m的如下方法中获取到deviceToken,它是对 该手机+该App 组合的一个唯一标识,当使用远程推送时,只需将推送消息发给指定的deviceToken即可使推送信息传达给指定手机的指定 App 上。因此如果你使用第三方,就需要在这个方法里将deviceToken传给第三方。(在 iOS 9 为了更好的保护用户隐私,会出现多次重复删除/安装 App 导致deviceToken
    不断变化的情况。有时会出现一条推送手机会收到 2 次的问题,属于 iOS 9 系统问题)。
-(void)application:(UIApplication *)application didRegisterForRemoteNotificationsWithDeviceToken:(NSData *)deviceToken { 
[JPUSHService registerDeviceToken:deviceToken];//将 deviceToken 传给极光推送 
}

4、如果以上步骤均成功,此时你能够取到第三方提供的设备注册 id。能否取到该 id 值,可以作为判断设备是否能够成功推送的标准(见 Tip 6 - Registration ID)。因为当你取到该值时必然:

  • 推送证书配置正确(你拥有了推送权限)。
  • 设备成功在 APNs 注册并返回了deviceToken(APNs 能识别你的设备了)。
  • 返回 的deviceToken传给第三方,成功在第三方生成了唯一标识注册 id(第三方能将你的设备信息传给 APNs 了)。

5、综上,注册及接收推送必须使用真机,必须连网。

  1. 在第一次触发这段代码的时候,会有一个系统弹窗,询问你是否允许该 App 要给你推送信息。当你选择允许时,系统会打包 App+手机唯一标识+证书 信息发送至 APNs 服务器注册推送服务,APNs 系统会对该手机安装的该 App 是否有推送权限进行验证,所以必须要加入了 Apple Deveice 的手机,使用对应 App 的推送证书才能够成功的注册。

  2. 如果注册成功,则可以在 AppDelegate.m 的如下方法中获取到 deviceToken,它是对 该手机+该App 组合的一个唯一标识,当使用远程推送时,只需将推送消息发给指定的 deviceToken 即可使推送信息传达给指定手机的指定 App 上。因此如果你使用第三方,就需要在这个方法里将 deviceToken 传给第三方。(在 iOS 9 为了更好的保护用户隐私,会出现多次重复删除/安装 App 导致 deviceToken 不断变化的情况。有时会出现一条推送手机会收到 2 次的问题,属于 iOS 9 系统问题)。

    -application:(UIApplication *)application didRegisterForRemoteNotificationsWithDeviceToken:deviceToken { [JPUSHService registerDeviceToken:deviceToken];//将 deviceToken 传给极光推送}
    
  3. 如果以上步骤均成功,此时你能够取到第三方提供的设备注册 id。能否取到该 id 值,可以作为判断设备是否能够成功推送的标准(见 Tip 6 - Registration ID)。因为当你取到该值时必然:

推送目标篇

别名、标签、Registration ID 均是第三方提供的用于更方便地指定推送目标的功能。

Tip 4:推送通知从 服务端 --> App 代码 的过程

  1. 使用你们公司或第三方的服务端向 APNs 发送推送请求(请参考苹果 APNs 相关资料,或者第三方推送提供了更简单的 REST API)。
  2. APNs 接收并验证推送请求。
  3. APNs 找到设备下发推送。
  4. 手机收到推送通知,系统根据 App 状态进行处理:
  • 前台收到:

    • 系统会将通知内容传到didReceiveRemoteNotification
  • 后台收到:

    • 如果开启了Remote Notification,系统将推送传到didReceiveRemoteNotification:fetchCompletionHandler:
      (见 Tip 5 - 后台推送),否则此时代码中收不到推送。
    • 展示横幅、通知中心、声音、角标。
  • 退出收到:

    • 如果点击推送横幅/通知中心而启动 App,系统将通知传到didFinishLaunchingWithOptions
    • 展示横幅、通知中心、声音、角标。
  • 推送证书配置正确。
  • 设备成功在 APNs 注册并返回了 deviceToken(APNs 能识别你的设备了)。
  • 返回 的 deviceToken 传给第三方,成功在第三方生成了唯一标识注册 id(第三方能将你的设备信息传给 APNs 了)。

Tip 6:推送根据目标的不同可分为:

  • 广播
    • 无差别的发送给所有用户。
  • 别名 alias 推送
    • 第三方提供的功能。
    • 一个手机的一款 App 只能设置一个 alias (可修改)。
    • 建议对每一个用户都取不同的别名,以此来确定唯一的用户(也可多个用户取 1 个别名)。
    • 推送时可指定多个 alias 来下发同一内容。
    • 仅指定 alias 的用户能够收到推送。
  • 标签 tag 推送
    *第三方提供的功能。
    *可设置多个、可增加、清空。
    *用于指定多样的属性,如 『1000』+『daily』+『discount』 可用于表示月消费超过 1k、喜欢购买日用品、偏好折扣商品的用户。
    *如果要删除,需要在上次设置时,将设置的 tags 保存至 NSUserDefaults,本次剔除不需要的 tag 后,再重新设置。
    *推送时可指定多个 tag 来下发同一内容。
    *手机如果设置了推送指定的多个 tag 中任一个tag,都能够收到推送消息。如指定 『1000』+『globe』+『original』 (千元级消费者、全球购、原价),那么设置了 『100』+『globe』+『discount』(百元级消费者、全球购、折扣价)的用户可以收到该推送消息。
  • Registration ID 推送
    • 第三方提供的功能。
    • 在 Tip 3 的第 3 步时将 deviceToken 提供给第三方之后,其服务器会自动生成的指向该手机的唯一 id。
    • 可在推送时指定多个 id 来下发消息。
    • 可用于对核心用户、旗舰用户的精准推送。

推送通知内容篇

  1. 综上,注册及接收推送必须使用真机,必须连网。

应用内消息篇

Tip 5:推送通知分为 本地/远程 2 种类型:

  • 本地通知,可指定推送时间,在该时间准时弹出推送通知。
  • 远程推送通知,分为 普通推送/后台推送/静默推送 3 种类型。存在延迟问题(由于 Tip 1 第 2 点,APNs 的不稳定及高峰时段的巨量请求所致)。
  • 普通推送

    • 就是我们在手机上平时见到的推送通知。

    • 包含声音、横幅、角标、自定义字段。

    • App :

      • 处于前台,不会展示横幅,可通过didReceiveRemoteNotification
        (iOS 7 before)didReceiveRemoteNotification:fetchCompletionHandler:(iOS 7 after)获取通知内容(前台展示横幅的方法看这里)。
      • 处于后台,会展示横幅,无法获取通知内容。
      • 处于退出,会展示横幅,无法获取通知内容。
      • 点击图标启动,无法获取通知内容。
      • 点击通知横幅启动,在didFinishLaunchingWithOptions获取通知内容。
    • 通知内容类似如下:

{ 
"_j_msgid" = 200806057; // 第三方附带的 id,用于统计点击 
aps = { alert = "显示内容";
 badge = 1; // App 角标,可推送 n、+n、-n 来实现角标的固定、增加、减少 
sound = default; // 推送声音,默认系统三全音,如需使用自己的声音,需要将声音文件拖拽&拷贝至 Xcode 工程目录任意位置,并在推送时指定其文件名 
};
 key1 = value1; // 自定义字段,可设置多组,用于处理内部逻辑 key2 = value2;
}
  • 后台推送

    • 各种显示效果跟普通推送完全一样。

    • 必须携带"content-available" = 1;

    • 必须携带alertbadgesound中至少 1 个字段。

    • 仅 iOS 7 以后支持。

    • 必须在 Xcode 工程中 TARGETS - Capabilities - Background Modes - Remote notifications 开启该功能,具体可参照 iOS 7 Background Remote Notification。

    • App:

    • 处于前台,可通过didReceiveRemoteNotification
      (iOS 7 before)didReceiveRemoteNotification:fetchCompletionHandler:(iOS 7 after) 获取通知内容。

    • 处于后台,可通过didReceiveRemoteNotification:fetchCompletionHandler:获取通知内容 // 获取情况中与普通推送的唯一不同点,此时 iOS 系统允许开发者在 App 处于后台的情况下,执行一些代码,大概提供几分钟的时间,可以用来偷偷的刷新 UI、切换页面、下载更新包等等操作。

    • 处于退出,无法获取通知内容。

    • 点击图标启动,无法获取通知内容。

    • 点击推送横幅启动,在didFinishLaunchingWithOptions
      获取通知内容。

    • 通知内容类似如下:

{ 
"_j_msgid" = 2090737306; 
aps = { 
alert = "显示内容"; 
badge = 1; 
"content-available" = 1; // 必带字段 
sound = default;
 }; 
key1 = value1;
}
  • 静默推送
    • 没有任何展示效果。
      必须携带"content-available" = 1;
      ,因此静默必然是后台的。
    • 必须不携带alertbadgesound
    • 可携带自定义字段。
    • App :
      • 处于前台,可通过didReceiveRemoteNotification(iOS 7 before)didReceiveRemoteNotification:fetchCompletionHandler:(iOS 7 after) 获取通知内容。
      • 处于后台,可通过didReceiveRemoteNotification:fetchCompletionHandler:获取通知内容 //获取情况中与普通推送的唯一不同点,此时 iOS 系统允许开发者在 App 处于后台的情况下,执行一些代码,大概提供几分钟的时间,可以用来偷偷的刷新 UI、切换页面、下载更新包等等操作。
      • 处于退出,无法获取通知内容。
    • 通知内容类似如下:
{ "_j_msgid" = 3938587719;
 aps = { alert = ""; 
"content-available" = 1; // 必带字段
 };
 key1 = value1;
}

Tip 7:应用内消息(以下简称消息 )和推送通知的区别,消息:

  • 不需要 Apple 推送证书。
  • 由第三方的服务器下发,而不是 APNs。
  • 相比通知,更快速,几乎没有延迟,可用于 IM 消息的即时送达。
  • 能够长时间保留离线消息,可获取所有历史消息内容。
  • 通过长连接技术下发消息,因此:
    • 手机必须启动并与第三方服务器建立连接。
    • 如果手机启动立刻切至后台,很可能没有建立连接。
    • 手机必须处于前台才能收到消息。
    • 手机从后台切回前台,会自动重新建立连接,并收到离线消息。
  • 没有任何展示(横幅、通知中心、角标、声音),因此可以:
    • 自定义字段实现 UI 效果。
    • 完全在静默情况下处理 App 内部逻辑。
    • 使用一些 App Store 审核不会通过的功能,在审核时关闭功能,上架后通过接收消息,开启相关功能。

推送目标篇

别名、标签、Registration ID 均是第三方提供的用于更方便地指定推送目标的功能。

  1. 使用你们公司或第三方的服务端向 APNs 发送推送请求(请参考苹果 APNs 相关资料,或者第三方推送提供了更简单的 REST API)。
  2. APNs 接收并验证推送请求。
  3. APNs 找到设备下发推送。
  4. 手机收到推送通知,系统根据 App 状态进行处理:
    • 前台收到:
      • 系统会将通知内容传到 didReceiveRemoteNotification
    • 后台收到:
      • 如果开启了 Remote Notification ,系统将推送传到 didReceiveRemoteNotification:fetchCompletionHandler:(见 Tip 5 - 后台推送),否则此时代码中收不到推送。
      • 展示横幅、通知中心、声音、角标。
    • 退出收到:
      • 如果点击推送横幅/通知中心而启动 App,系统将通知传到 didFinishLaunchingWithOptions
      • 展示横幅、通知中心、声音、角标。

组合大招篇

Tip 6:推送根据目标的不同可分为:

  • 广播

  • 无差别发送给所有用户。

  • 别名 alias 推送

  • 第三方提供的功能

  • 一个手机的一款 App 只能设置一个 alias(可修改)。

  • 建议对每一个用户都取不同的别名,以此来确定唯一的用户(也可多个用户取 1 个别名)。

  • 推送时可指定多个 alias 来下发同一内容。

  • 仅指定 alias 的用户能够收到推送。

  • 标签 tag 推送

  • 第三方提供的功能。

  • 可设置多个、可增加、清空。

  • 用于指定多样的属性,如 『1000』+『daily』+『discount』 可用于表示月消费超过 1k、喜欢购买日用品、偏好折扣商品的用户。

  • 如果要删除,需要在上次设置时,将设置的 tags 保存至NSUserDefaults
    ,本次剔除不需要的 tag 后,再重新设置。

  • 推送时可指定多个 tag 来下发同一内容。

  • 手机如果设置了推送指定的多个 tag 中任一个tag,都能够收到推送消息。如指定 『1000』+『globe』+『original』 (千元级消费者、全球购、原价),那么设置了 『100』+『globe』+『discount』(百元级消费者、全球购、折扣价)的用户可以收到该推送消息。

  • Registration ID 推送

  • 第三方提供的功能。

  • 在 Tip 3 的第 3 步时将deviceToken提供给第三方之后,其服务器会自动生成的指向该手机的唯一 id。

  • 可在推送时指定多个 id 来下发消息。

  • 可用于对核心用户、旗舰用户的精准推送。

  • 本地通知,可指定推送时间,在该时间准时弹出推送通知。
  • 远程推送通知,分为 普通推送/后台推送/静默推送 3 种类型。存在延迟问题(由于 Tip 1 第 2 点,APNs 的不稳定及高峰时段的巨量请求所致)。

    • 普通推送

      • 就是我们在手机上平时见到的推送通知。

      • 包含声音、横幅、角标、自定义字段。

      • App :

        • 处于前台,不会展示横幅,可通过 didReceiveRemoteNotification(iOS 7 before)didReceiveRemoteNotification:fetchCompletionHandler:(iOS 7 after)获取通知内容(前台展示横幅的方法看这里)。
        • 处于后台,会展示横幅,无法获取通知内容。
        • 处于退出,会展示横幅,无法获取通知内容。
        • 点击图标启动,无法获取通知内容。
        • 点击通知横幅启动,在 didFinishLaunchingWithOptions 获取通知内容。
      • 通知内容类似如下:

Tip 8:tags 的组合技巧

  • 见 Tip 5 - 标签 tag 推送。
  • 可以在服务端来统计分析用户行为,然后将指定的 tags 发送至手机,手机接收后再为用户打上对应的 tags。

应用内消息篇

{"_j_msgid" = 200806057; // 第三方附带的 id,用于统计点击aps = {alert = "显示内容";badge = 1; // App 角标,可推送 n、+n、-n 来实现角标的固定、增加、减少sound = default; // 推送声音,默认系统三全音,如需使用自己的声音,需要将声音文件拖拽&拷贝至 Xcode 工程目录任意位置,并在推送时指定其文件名};key1 = value1; // 自定义字段,可设置多组,用于处理内部逻辑key2 = value2;}```

Tip 9:通知+消息的组合技巧

  • 首先来看通知和消息特性的对比:
通知 消息
送达时间 可能存在几秒延迟 几乎无延迟
获取时机 处于前台或后台能获取内容 仅处于前台能获取内容
离线内容 保留一段时间,过期会抛弃,无法查询历史内容 始终保留,可查询全部历史内容
系统展示 会展示(静默推送或App处于前台不展示) 不展示
  • 由于各自的特性都存在差异,因此二者结合使用是使得 App 推送性能最大化的必然选择:
    • 情景一:
      QQ/微信 聊天:会同时下发一组通知+消息,如果用户没有启动QQ,虽有延迟但必然能够先收到通知,在收到通知的提醒之后,用户打开App,此时收到了离线消息,即时更新 UI,与好友即时的 发送/接收 消息。(在收到通知后,断网,然后启动 App,你会发现此时手机里并不会显示刚刚通知的内容,因为它是依靠拉取消息来刷新页面的,而不是不够稳定的通知)。
    • 情景二:(有 请留言补充...)。

Tip 7:应用内消息(以下简称消息 )和推送通知的区别,消息:

  • 不需要 Apple 推送证书。

  • 由第三方的服务器下发,而不是 APNs。

  • 相比通知,更快速,几乎没有延迟,可用于 IM 消息的即时送达。

  • 能够长时间保留离线消息,可获取所有历史消息内容。

  • 通过长连接技术下发消息,因此:

  • 手机必须启动并与第三方服务器建立连接。

  • 如果手机启动立刻切至后台,很可能连接没有建立。

  • 手机必须处于前台才能收到消息。

  • 手机从后台切回前台,会自动重新建立连接,并收到离线消息。

  • 没有任何展示(横幅、通知中心、角标、声音),因此可以:

  • 自定义字段实现 UI 效果。

  • 完全在静默情况下处理 App 内部逻辑。

  • 使用一些 App Store 审核不会通过的功能,在审核时关闭功能,上架后通过接收消息,开启相关功能。

- 后台推送 - 各种显示效果跟普通推送完全一样。 - 必须携带 `"content-available" = 1;` - 必须携带 `alert`、`badge`、`sound` 中 `至少 1 个字段`。 - 仅 iOS 7 以后支持。 - 必须在 Xcode 工程中 TARGETS - Capabilities - Background Modes - Remote notifications 开启该功能,具体可参照 [iOS 7 Background Remote Notification](http://docs.jiguang.cn/client/ios_tutorials/#ios-7-background-remote-notification)。 - App: - 处于前台,可通过`didReceiveRemoteNotification`(iOS 7 before)`didReceiveRemoteNotification:fetchCompletionHandler:`(iOS 7 after) 获取通知内容。 - 处于后台,可通过 `didReceiveRemoteNotification:fetchCompletion Handler:` 获取通知内容 // 获取情况中与普通推送的唯一不同点,此时 iOS 系统允许开发者在 App 处于后台的情况下,执行一些代码,大概提供几分钟的时间,可以用来偷偷的刷新 UI、切换页面、下载更新包等等操作。 - 处于退出,无法获取通知内容。 - 点击图标启动,无法获取通知内容。 - 点击推送横幅启动,在 `didFinishLaunchingWithOptions` 获取通知内容。 - 通知内容类似如下: ```json{ "_j_msgid" = 2090737306; aps = { alert = "显示内容"; badge = 1; "content-available" = 1; // 必带字段 sound = default; }; key1 = value1;} ``` ​- 静默推送 - 没有任何展示效果。 - 必须携带 `"content-available" = 1;`,因此静默必然是后台的。 - 必须不携带 `alert`、`badge`、`sound`。 - 可携带自定义字段。 - App : - 处于前台,可通过`didReceiveRemoteNotification`(iOS 7 before)`didReceiveRemoteNotification:fetchCompletionHandler:`(iOS 7 after) 获取通知内容。 - 处于后台,可通过 `didReceiveRemoteNotification:fetchCompletion Handler:` 获取通知内容 //获取情况中与普通推送的唯一不同点,此时 iOS 系统允许开发者在 App 处于后台的情况下,执行一些代码,大概提供几分钟的时间,可以用来偷偷的刷新 UI、切换页面、下载更新包等等操作。 - 处于退出,无法获取通知内容。 - 通知内容类似如下: ```json{ "_j_msgid" = 3938587719; aps = { alert = ""; "content-available" = 1; // 必带字段 }; key1 = value1;} ```

组合大招篇

别名、标签、Registration ID 均是第三方提供的用于更方便地指定推送目标的功能。

Tip 8:tags 的组合技巧

  • 见 Tip 5 - 标签 tag 推送。
  • 可以在服务端来统计分析用户行为,然后将指定的 tags 发送至手机,手机接收后再为用户打上对应的 tags。
  • 广播
    • 无差别发送给所有用户。
  • 别名 alias 推送
    • 第三方提供的功能
    • 一个手机的一款 App 只能设置一个 alias。
    • 建议对每一个用户都取不同的别名,以此来确定唯一的用户(也可多个用户取 1 个别名)。
    • 推送时可指定多个 alias 来下发同一内容。
    • 仅指定 alias 的用户能够收到推送。
  • 标签 tag 推送
    • 第三方提供的功能。
    • 可设置多个、可增加、清空。
    • 用于指定多样的属性,如 『1000』+『daily』+『discount』 可用于表示月消费超过 1k、喜欢购买日用品、偏好折扣商品的用户。
    • 如果要删除,需要在上次设置时,将设置的 tags 保存至 NSUserDefaults,本次剔除不需要的 tag 后,再重新设置。
    • 推送时可指定多个 tag 来下发同一内容。
    • 手机如果设置了推送指定的多个 tag 中任一个tag,都能够收到推送消息。如指定 『1000』+『globe』+『original』 (千元级消费者、全球购、原价),那么设置了 『100』+『globe』+『discount』(百元级消费者、全球购、折扣价)的用户可以收到该推送消息。
  • Registration ID 推送
    • 第三方提供的功能。
    • 在 Tip 3 的第 3 步时将 deviceToken 提供给第三方之后,其服务器会自动生成的指向该手机的唯一 id。
    • 可在推送时指定多个 id 来下发消息。
    • 可用于对核心用户、旗舰用户的精准推送。

Tip 9:通知+消息的组合技巧

  • 首先来看通知和消息特性的对比:
通知 消息
送达时间 可能存在几秒延迟 几乎无延迟
获取时机 处于前台或后台能获取内容 仅处于前台能获取内容
离线内容 保留『一段时间』,过期会抛弃,无法查询历史内容

始终保留,可查询全部历史内容
系统展示 | 会展示(静默推送或App处于前台不展示) | 不展示

  • 由于各自的特性都存在差异,因此二者结合使用是使得 App 推送性能最大化的必然选择:
  • 情景一:QQ/微信 聊天。会同时下发一组通知+消息 ,如果用户没有启动 QQ,虽有延迟但必然能够先收到通知,在收到通知的提醒之后,用户打开 App,此时收到了离线消息,即时更新 UI,与好友即时地发送/接收消息。(在收到通知后,断网,然后启动 App,你会发现此时手机里并不会显示刚刚通知的内容,因为它是依靠拉取消息来刷新页面的,而不是不够稳定的通知)。
  • 情景二:(期待您的补充...)
  • 不需要 Apple 推送证书。
  • 由第三方的服务器下发,而不是 APNs。
  • 相比通知,更快速,几乎没有延迟,可用于 IM 消息的即时送达。
  • 能够长时间保留离线消息,可获取所有历史消息内容。
  • 通过长连接技术下发消息,因此:
    • 手机必须启动并与第三方服务器建立连接。
    • 如果手机启动立刻切至后台,很可能连接没有建立。
    • 手机必须处于前台才能收到消息。
    • 手机从后台切回前台,会自动重新建立连接,并收到离线消息。
  • 没有任何展示(横幅、通知中心、角标、声音),因此可以:
    • 自定义字段实现 UI 效果。
    • 完全在静默情况下处理 App 内部逻辑。
    • 使用一些 App Store 审核不会通过的功能,在审核时关闭功能,上架后通过接收消息,开启相关功能。
  • 见 Tip 5 - 标签 tag 推送。
  • 可以在服务端来统计分析用户行为,然后将指定的 tags 发送至手机,手机接收后再为用户打上对应的 tags。
  • 首先来看通知和消息特性的对比:
通知 消息
送达时间 可能存在几秒延迟 几乎无延迟
获取时机 处于前台或后台能获取内容 仅处于前台能获取内容
离线内容 保留『一段时间』,过期会抛弃,无法查询历史内容 始终保留,可查询全部历史内容
系统展示 会展示(静默推送或App处于前台不展示) 不展示
  • 由于各自的特性都�存在差异,因此二者结合使用是使得 App 推送性能最大化的必然选择:
    • 情景一:QQ/微信 聊天。会同时下发一组通知+消息 ,如果用户没有启动 QQ,虽有延迟但必然能够先收到通知,在收到通知的提醒之后,用户打开 App,此时收到了离线消息,即时更新 UI,与好友即时地发送/接收消息。(在收到通知后,断网,然后启动 App,你会发现此时手机里并不会显示刚刚通知的内容,因为它是依靠拉取消息来刷新页面的,而不是不够稳定的通知)。
    • 情景二:(期待您的补充...)

版权声明:本文由大奖888-www.88pt88.com-大奖888官网登录发布于大奖888官网登录,转载请注明出处:均是第三方提供的用于更有利地钦点推送目标的