zoukankan      html  css  js  c++  java
  • 使用PushSharp给iOS应用推送消息

    使用PushSharp给iOS应用推送消息

    2013-12-14 11:21 by 囧月, 372 阅读, 4 评论, 收藏编辑

    PushSharp是一个C#编写的服务端类库,用于推送消息到各种客户端,支持iOS(iPhone/iPad)、Android、Windows Phone、Windows 8、Amazo、Blackberry等设备。

    官方网站:https://github.com/Redth/PushSharp

    当前最新稳定版本为2.0.4,支持通过NuGet获取(https://www.nuget.org/packages/PushSharp/)

    主要特点

    提供了易于使用的API,支持以下平台的消息推送:

    100%的托管代码完全兼容Mono平台。

    安装

    PushSharp主要包含以下程序集:

    • PushSharp.Core:(必选)核心组件
    • PushSharp.Apple:APNS,用于iOS及OSX
    • PushSharp.Android:C2DM及GCM,用于Android设备
    • PushSharp.Windows:用于Windows 8
    • PushSharp.WindowsPhone:用于WP设备
    • PushSharp.Amazon.Adm:用于Amazon的设备
    • PushSharp.Blackberry:用于黑莓设备
    • PushSharp.Google.Chrome:用于Chrome

    其中,PushSharp.Core为必须的组件,其他的可以根据自己需要来选择对应平台。

    平常使用只需要用NuGet来获取程序集即可:

    1
    Install-Package PushSharp

    这样会把主流平台的程序集(Apple/Android/Windows/WindowsPhone)都下载下来,可以根据自己需要删除用不到的平台组件。

    假如需要使用Blackberry等NuGet包里没有的组件,则需要到官方网站(https://github.com/Redth/PushSharp)获取源码自行编译。

    对于Apple平台,只需要PushSharp.Core和PushSharp.Apple组件即可。

    证书配置

    官方WIKI提供了详细的证书配置步骤:

    Apple平台证书创建流程:

    • 创建AppID
    • 为AppID配置用于APP签名的证书:分别有开发环境(Development)和生产环境(Production)的证书
    • 编辑AppID启用消息推送
    • 为AppID创建用于消息推送(APNS)的证书(包括Development和Production)
    • 下载以上证书并安装到Key Chain(钥匙串)
    • 导出用于消息推送(APNS)的证书为.p12格式,并为它设置密码:用于在服务端推送消息

    对于Apple平台需要特别说明:

    • Provisioning Protal现在已经变成了Certificates, Identifiers & Profiles,可以从Member Center点进去或者iOS Developer Center找到
    • 对于已经发布的APP要启用消息推送功能,需要在Identifiers – App IDs找到对应的ID创建好APNS证书之后,再重新生成用于APP签名的证书,否则用于注册消息推送的代码(RegisterForRemoteNotificationTypes)不会正常工作,即返回的deviceToken为null
    • 在使用Development证书调试应用程序时服务端需要使用Development APNS证书来推送消息,使用Production证书发布到AppStore后推送消息需要使用Production APNS证书来推送消息

    客户端启用消息推送

    启用消息推送都是在AppDelegate里注册来完成的。

    对于使用objc语言编写的客户端:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    - (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
    {
        if (application.enabledRemoteNotificationTypes == UIRemoteNotificationTypeNone)
        {
            [application registerForRemoteNotificationTypes:
             UIRemoteNotificationTypeAlert |
             UIRemoteNotificationTypeBadge |
             UIRemoteNotificationTypeSound];
        }
        application.applicationIconBadgeNumber = -1;
        // Override point for customization after application launch.
        return YES;
    }
     
    - (void)application:(UIApplication *)application didRegisterForRemoteNotificationsWithDeviceToken:(NSData *)deviceToken
    {
        NSString *pushToken = [[[[deviceToken description]
                                 stringByReplacingOccurrencesOfString:@"<"withString:@""]
                                stringByReplacingOccurrencesOfString:@">" withString:@""]
                               stringByReplacingOccurrencesOfString: @" " withString: @""];
        [[NSUserDefaults standardUserDefaults] setObject:pushToken forKey:@"pushtoken"]; // 保存起来
    }

    对于使用MonoTouch的客户端:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    public override bool FinishedLaunching(UIApplication app, NSDictionary options)
    {
        app.RegisterForRemoteNotificationTypes(
            UIRemoteNotificationType.Alert |
            UIRemoteNotificationType.Badge |
            UIRemoteNotificationType.Sound);
        app.ApplicationIconBadgeNumber = -1;
        // ...
        return true;
    }
     
    public override void RegisteredForRemoteNotifications(UIApplication application, NSData deviceToken)
    {
        string tokenStr = token.Description;
        string pushToken = tokenStr.Replace("<", string.Empty).Replace(">", string.Empty).Replace(" ", string.Empty);
        NSUserDefaults.StandardUserDefaults.SetString(pushToken, "pushtoken");
    }
     
    public override void FailedToRegisterForRemoteNotifications(UIApplication application, NSError error)
    {
     
    }
     
    public override void DidReceiveRemoteNotification(UIApplication application, NSDictionary userInfo, Action<UIBackgroundFetchResult> completionHandler)
    {
     
    }

    在接收到deviceToken的时候先存储在NSUserDefaults中,在用户登录的时候再取出来一起发送到服务端:

    1
    2
    NSString *pushToken = [[NSUserDefaults standardUserDefaults] stringForKey:@"pushtoken"]; //objc
    string pushToken = NSUserDefaults.StandardUserDefaults.StringForKey("pushtoken"); //MonoTouch

    服务端在用户登录成功之后,把接收到用户的用户名与pushToken关联起来,在推送消息的时候就可以针对指定用户来推送,具体的过程略。

    而对于不需要用户登录的app,可以在接收到deviceToken的时候直接发送到服务端。

    更多的客户端配置参考PushSharp源码的Client.SamplesPushSharp.Client目录。

    服务端推送消息

    1
    2
    3
    4
    5
    6
    7
    8
    9
    var pusher = new PushBroker();
    pusher.RegisterAppleService(new ApplePushChannelSettings(File.ReadAllBytes("yourAppId.p12"), "证书的密码"));
    pusher.QueueNotification(
                    new AppleNotification()
                        .ForDeviceToken(pushToken) // 从数据库等地方获取设备的pushToken
                        .WithAlert("测试iOS消息推送 - 囧月")
                        .WithBadge(1)
                        .WithSound("default")
                );

    在RegisterAppleService方法中可以注册多个APNS证书,PushSharp可以自动检测是Development/Production,这时候需要为证书设置标识:

    1
    2
    pusher.RegisterAppleService(new ApplePushChannelSettings(File.ReadAllBytes("yourAppId.p12"), "证书的密码"), "证书标识如youAppId_development");
    pusher.RegisterAppleService(new ApplePushChannelSettings(File.ReadAllBytes("yourAppId.p12"), "证书的密码"), "证书标识如youAppId_production");

    此外,可以注册各种事件来获得各种状态:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    pusher.OnDeviceSubscriptionChanged += pusher_OnDeviceSubscriptionChanged;
    pusher.OnDeviceSubscriptionExpired += pusher_OnDeviceSubscriptionExpired;
    pusher.OnNotificationSent += pusher_OnNotificationSent;
    pusher.OnNotificationFailed += pusher_OnNotificationFailed;
    pusher.OnNotificationRequeue += pusher_OnNotificationRequeue;
    pusher.OnChannelCreated += pusher_OnChannelCreated;
    pusher.OnChannelDestroyed += pusher_OnChannelDestroyed;
    pusher.OnChannelException += pusher_OnChannelException;
    pusher.OnServiceException += pusher_OnServiceException;
     
    static void pusher_OnNotificationFailed(object sender, INotification notification, Exception error)
    {
        var n = (AppleNotification)notification;
        //error.Message ...获取推送出错的信息
    }
     
    static void pusher_OnNotificationSent(object sender, INotification notification)
    {
        //消息推送成功后
        var n = (AppleNotification)notification;
        //n.Payload.Alert.Body  获取推送的消息内容...
    }
     
    static void pusher_OnDeviceSubscriptionExpired(object sender, string expiredSubscriptionId, DateTime expirationDateUtc, INotification notification)
    {
        // 从数据库删除过期的expiredSubscriptionId
    }
     
    static void pusher_OnDeviceSubscriptionChanged(object sender, string oldSubscriptionId, string newSubscriptionId, INotification notification)
    {
        // 把数据库中的oldSubscriptionId更新为newSubscriptionId
    }

    更多请参考源码的PushSharp.Sample目录。

    参考

    官方网站:https://github.com/Redth/PushSharp 可以获取最新源码及各种例子

    WIKI:https://github.com/Redth/PushSharp/wiki  详细说明了各平台证书配置的方法

    Xamarin相关文档:http://docs.xamarin.com/guides/cross-platform/application_fundamentals/notifications/ios/remote_notifications_in_ios/ 

  • 相关阅读:
    Flex动画
    八大排序算法
    Android switch语句“case expressions must be constant expressions”
    MySQL修改root密码的多种方法
    Android中ListView控件onItemClick事件中获取listView传递的数据
    超详细Android接入支付宝支付实现,有图有真相
    Android蓝牙开发---与蓝牙模块进行通信
    Leecode no.19 删除链表的倒数第 N 个结点
    玩转java静态/动态代理
    Leecode no.198. 打家劫舍
  • 原文地址:https://www.cnblogs.com/Leo_wl/p/3474873.html
Copyright © 2011-2022 走看看