发送 APNS 使用 p12 文件(C#)

public static bool PushWithP12(string apnToken, string message)
        {
            _log.DebugFormat("[Apns] step 1");

            _log.DebugFormat("Token = " + apnToken);

            ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls | SecurityProtocolType.Tls11 | SecurityProtocolType.Tls12 | SecurityProtocolType.Ssl3;
            // var file = File.ReadAllBytes(ConfigurationManager.AppSettings["ApnsCertificate"]);
            var config = new ApnsConfiguration(ApnsConfiguration.ApnsServerEnvironment.Sandbox, ConfigurationManager.AppSettings["ApnsCertificate"], ConfigurationManager.AppSettings["ApnsPassword"]);

            // Create a new broker
            var apnsBroker = new ApnsServiceBroker(config);
            _log.DebugFormat("[Apns] step 2");
            // Wire up events
            apnsBroker.OnNotificationFailed += (notification, aggregateEx) =>
            {
                _log.DebugFormat("[Apns] step 3");
                aggregateEx.Handle(ex =>
                {
                    _log.DebugFormat("[Apns] step 4");
                    // See what kind of exception it was to further diagnose
                    if (ex is ApnsNotificationException)
                    {
                        _log.DebugFormat("[Apns] step 5");
                        var notificationException = (ApnsNotificationException)ex;
                        _log.DebugFormat("[Apns] step 6");
                        // Deal with the failed notification
                        var apnsNotification = notificationException.Notification;
                        var statusCode = notificationException.ErrorStatusCode;

                        _log.ErrorFormat($"Apple Notification Failed: ID={apnsNotification.Identifier}, Code={statusCode}");
                        return false;
                    }
                    else
                    {
                        // Inner exception might hold more useful information like an ApnsConnectionException
                        _log.ErrorFormat($"Apple Notification Failed for some unknown reason : {ex.InnerException}");
                        return false;
                    }

                    // Mark it as handled
                    //return true;
                });
            };
            _log.DebugFormat("[Apns] step 7");
            apnsBroker.OnNotificationSucceeded += (notification) =>
            {
                _log.InfoFormat("Apple Notification Sent!");
            };

            _log.DebugFormat("[Apns] step 8");
            // Start the broker
            apnsBroker.Start();
            _log.DebugFormat("[Apns] step 9");

            // Queue a notification to send
            var apnsObj = new PayLoadEntity()
            {
                aps = new Aps()
                {
                    alert = message
                }
            };
            var apnsStr = JsonConvert.SerializeObject(apnsObj);
            _log.DebugFormat("[Apns] step 9.1");
            _log.DebugFormat(apnsStr);
            apnsBroker.QueueNotification(new ApnsNotification
            {
                DeviceToken = apnToken,
                Payload = JObject.Parse(apnsStr)
            });

            _log.DebugFormat("[Apns] step 10");

            // Stop the broker, wait for it to finish
            // This isn't done after every message, but after you're
            // done with the broker
            apnsBroker.Stop();
            _log.DebugFormat("[Apns] step 11");
            return true;
        }

// 发送 APNS 使用 p8 文件(c#)

 

 static async void TokenBasedAuthenticationAPNsPush(string message, string token)
        {
            string algorithm = "ES256";

            string apnsKeyId = "{your_key_id}"; // get from apple dev account
            string teamId = "get from your membership info";
            string authKeyPath = "apns.p8"; // generate from apple account

            string bundleId = "your app id";
            string registrationId = token;

            var privateKeyContent = System.IO.File.ReadAllText(authKeyPath);
            var privateKey = privateKeyContent.Split('\n')[1];

            var secretKeyFile = Convert.FromBase64String(privateKey);
            var secretKey = CngKey.Import(secretKeyFile, CngKeyBlobFormat.Pkcs8PrivateBlob);

            var expiration = DateTime.Now.ToUniversalTime() - new DateTime(1970, 1, 1, 0, 0, 0, 0, DateTimeKind.Utc);
            var expirationSeconds = (long)expiration.TotalSeconds;

            var payload = new Dictionary<string, object>()
            {
                { "iss", teamId },
                { "iat", expirationSeconds }
            };
            var header = new Dictionary<string, object>()
            {
                { "alg", algorithm },
                { "kid", apnsKeyId }
            };

            string accessToken = Jose.JWT.Encode(payload, secretKey, JwsAlgorithm.ES256, header);
            ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls | SecurityProtocolType.Tls11 | SecurityProtocolType.Tls12 | SecurityProtocolType.Ssl3;

            //Development server:api.development.push.apple.com:443
            //Production server:api.push.apple.com:443

            string host = "api.development.push.apple.com";
            //string host = "api.push.apple.com";
            int port = 443;

            // Uri to request
            var uri = new Uri(string.Format("https://{0}:{1}/3/device/{2}", host, port, registrationId));

            var payloadData = JObject.FromObject(new
            {
                aps = new
                {
                    alert = message
                }
            });

            byte[] data = System.Text.Encoding.UTF8.GetBytes(payloadData.ToString());

            var handler = new Http2MessageHandler();
            var httpClient = new HttpClient(handler);
            var requestMessage = new HttpRequestMessage();
            requestMessage.RequestUri = uri;
            requestMessage.Headers.Add("authorization", string.Format("bearer {0}", accessToken));
            requestMessage.Headers.Add("apns-id", Guid.NewGuid().ToString());
            requestMessage.Headers.Add("apns-expiration", "0");
            requestMessage.Headers.Add("apns-priority", "10");
            requestMessage.Headers.Add("apns-topic", bundleId);
            requestMessage.Method = HttpMethod.Post;
            requestMessage.Content = new ByteArrayContent(data);

            try
            {
                var responseMessage = await httpClient.SendAsync(requestMessage);

                if (responseMessage.StatusCode == System.Net.HttpStatusCode.OK)
                {
                    string responseUuid = string.Empty;
                    IEnumerable<string> values;
                    if (responseMessage.Headers.TryGetValues("apns-id", out values))
                    {
                        responseUuid = values.First();
                    }
                    Console.WriteLine(string.Format("\n\r*******Send Success [{0}]", responseUuid));
                }
                else
                {
                    var body = await responseMessage.Content.ReadAsStringAsync();
                    var json = new JObject();
                    json = JObject.Parse(body);

                    var reasonStr = json.Value<string>("reason");
                    Console.WriteLine("\n\r*******Failure reason => " + reasonStr);
                }

                Console.ReadKey();
            }
            catch (Exception ex)
            {
                var info = "";
                DumpAllInfoOfException(ex, ref info);
                Console.WriteLine("\n\r*******Exception message => " + ex.Message);
                Console.WriteLine(info);
            }
        }

下面这种方式是NODEJS+p8文件实现的

function Send_APNS(param_msg, param_device){
	var apn = require('apn');

	// Set up apn with the APNs Auth Key
	var apnProvider = new apn.Provider({
		 token: {
			key: 'apns.p8', // Path to the key p8 file
			keyId: 'xxx', // The Key ID of the p8 file (available at https://developer.apple.com/account/ios/certificate/key)
			teamId: 'xxxx', // The Team ID of your Apple Developer Account (available at https://developer.apple.com/account/#/membership/)
		},
		production: false // Set to true if sending a notification to a production iOS app
	});

	// Enter the device token from the Xcode console
	var deviceToken = param_device;

	// Prepare a new notification
	var notification = new apn.Notification();

	// Specify your iOS app's Bundle ID (accessible within the project editor)
	notification.topic = 'nec.com.sg.BCMS';

	// Set expiration to 1 hour from now (in case device is offline)
	notification.expiry = Math.floor(Date.now() / 1000) + 3600;

	// Set app badge indicator
	notification.badge = 3;

	// Play ping.aiff sound when the notification is received
	notification.sound = 'ping.aiff';

	// Display the following message (the actual notification text, supports emoji)
	notification.alert = param_msg;

	// Send any extra payload data with the notification which will be accessible to your app in didReceiveRemoteNotification
	notification.payload = {id: 1};

	// Actually send the notification
	apnProvider.send(notification, deviceToken).then(function(result) {
		// Check the result for any failed devices
		console.log(result);
	});
}

Iphone 消息通知(APNS)的3种方式 -- C# 和 nodejs的更多相关文章

  1. 聊聊业务系统中投递消息到mq的几种方式

    背景 电商中有这样的一个场景: 下单成功之后送积分的操作,我们使用mq来实现 下单成功之后,投递一条消息到mq,积分系统消费消息,给用户增加积分 我们主要讨论一下,下单及投递消息到mq的操作,如何实现 ...

  2. 聊聊mq中消息消费的几种方式

    mq系列文章 对mq了解不是很多的,可以看一下下面两篇文章: 聊聊mq的使用场景 聊聊业务系统中投递消息到mq的几种方式 聊聊消息消费的几种方式 如何确保消息至少消费一次 如何保证消息消费的幂等性 本 ...

  3. 源码详解openfire保存消息记录_修改服务端方式

    实现openfire消息记录通常有两种方式,修改服务端和添加消息记录插件. 今天,简单的说明一下修改服务端方式实现消息记录保存功能. 实现思路 修改前: 默认的,openfire只提供保存离线记录至o ...

  4. WINDOWS硬件通知应用程序的常方法(五种方式:异步过程调用APC,事件方式VxD,消息方式,异步I/O方式,事件方式WDM)

    摘要:在目前流行的Windows操作系统中,设备驱动程序是操纵硬件的最底层软件接口.为了共享在设备驱动程序设计过程中的经验,给出设备驱动程序通知应用程序的5种方法,详细说明每种方法的原理和实现过程,并 ...

  5. RocketMQ(6)---发送普通消息(三种方式)

    发送普通消息(三种方式) RocketMQ 发送普通消息有三种实现方式:可靠同步发送.可靠异步发送.单向(Oneway)发送. 注意 :顺序消息只支持可靠同步发送. GitHub地址: https:/ ...

  6. 横竖屏事件响应(viewWillLayoutSubviews和通知)两种方式

    转载:http://blog.csdn.net/nogodoss/article/details/17246489 最近搞横竖屏,获得一些心得,特记录下来. 做横竖屏最重要的是确定横竖屏响应的接口.目 ...

  7. ActiveMQ持久化消息的三种方式

    详见:http://blog.yemou.net/article/query/info/tytfjhfascvhzxcyt362 本文只介绍三种方式,分别是持久化为文件,MYSql,Oracle.下面 ...

  8. Kafka生产者发送消息的三种方式

    Kafka是一种分布式的基于发布/订阅的消息系统,它的高吞吐量.灵活的offset是其它消息系统所没有的. Kafka发送消息主要有三种方式: 1.发送并忘记 2.同步发送 3.异步发送+回调函数 下 ...

  9. ios消息队列APNS实现和证书申请

    iOS消息推送的工作机制可以简单的用下图来概括: Provider是指某个iPhone软件的Push服务器,APNS是Apple Push Notification Service的缩写,是苹果的服务 ...

随机推荐

  1. 20145335《java程序设计》第三次实验报告

    20145335郝昊<java程序设计>第三次实验报告 实验目的与要求 以结对编程的方式编写一个软件,Blog中要给出结对同学的Blog网址,可以拍照展现结对编程 情况,可以参考一下其他学 ...

  2. [翻译]纠正PostCSS的4大认识误区

    市面上已经有很多的前端工具,再来引入新的前端工具,价值大不大?这主要取决于,它是否给开发人员提供了新的功能,是否值得花时间和精力去学习和使用? PostCSS出现时有一个很有趣的现象.像sass和le ...

  3. iOS开发中的地图开发

    显示地图: 1.导入头文件 #import <MapKit/MapKit.h> 如果同时需要用户定位的话还需要 #import <CoreLocation/CoreLocation. ...

  4. poj_2528 Mayor's posters (线段树经典题+离散化方法)

    由于题面中给定的wall最大长度为10 000 000:若简单用线段树势必会超时. 而注意到题面中规定了输入海报的个数<=1000:因此不妨离散化,使得线段中叶节点仅含有1000个,那么线段最大 ...

  5. C#中将一个引用赋值null的作用

    有类A,以及A类型的变量a和b.初始化a之后,将a赋给b.之后将a赋为null.之后b还是可以使用. 思维误区:本来以为a=null之后,b也应该等于null. 实际测试效果如下 class Prog ...

  6. 设计模式——迭代器(Iterator)模式

    概述 迭代器模式简单的说(按我目前的理解)就是一个类提供一个对外迭代的接口,方面调用者迭代.这个迭代接口至少包括两个方法:hasNext()--用于判断是否还有下一个,next()--用于取出下一个对 ...

  7. Android6.0------权限申请管理(单个权限和多个权限申请)

    Android开发时,到6.0系统上之后,有的权限就得申请才能用了. Android将权限分为正常权限 和 危险权限 Android系统权限分为几个保护级别.需要了解的两个最重要保护级别是 正常权限  ...

  8. bzo1016: [JSOI2008]最小生成树计数

    现在给出了一个简单无向加权图.你不满足于求出这个图的最小生成树,而希望知道这个图中有多少个不同的最小生成树.(如果两颗最小生成树中至少有一条边不同,则这两个最小生成树就是不同的).由于不同的最小生成树 ...

  9. LabVIEW之生产者/消费者模式

    LabVIEW之生产者/消费者设计模式 彭会锋

  10. 修改tomcat默认端口号8080

    1.背景 在默认情况下,tomcat的端口是8080,使用了两个tomcat,那么就需要修改其中的一个的端口号才能使得两个同时工作. 2.方法 2.1改动一 那么,如何修改tomcat的端口号呢?首先 ...