سؤال

أحاول إرسال إشعارات الدفع إلى iPhone باستخدام Python. لقد تصدير بلدي شهادة ومفتاح خاص في ملف P12 من وصول المفاتيح ثم تحويله إلى ملف PEM باستخدام الأمر التالي:

openssl pkcs12 -in cred.p12 -out cert.pem -nodes -clcerts

أنا استخدم apnswrapper. في بيثون للاتصال.

قمت بتشغيل التعليمات البرمجية التالية:

devicetoken = 'qun  xaa  xd ... c0  x9c  xf6  xca' # إنشاء التفاف المجمع = apnsnotificationWrapper ('/ مسار / to / cert / cert.pem'، صحيح) # إنشاء رسالة رسالة = رسالة apnsnotification () .token (devicetoken) message.badge (5) # أضف رسالة إلى tuple وأرسلها إلى Apns Server Wrapper.append (رسالة) Wrapper.notify ()

ثم أحصل على رسالة الخطأ:

SSL.SSLERROR: (1، '_ssl.c: 485: خطأ: 14094416: إجراءات SSL: SSL3_READ_BYTES: شهادة تنبيه SSLV3 غير معروفة)

يمكن لأي شخص أن يساعدني على ذلك؟

هل كانت مفيدة؟

المحلول

لقد فعلت ذلك مؤخرا هذا باستخدام Django - http://leecutsco.de/2009/07/14/14/push-on-the-iphone/

ربما يكون مفيدا؟ إنها تستفيد من أي مكتبات إضافية غير تلك المضمنة مع Python بالفعل. لن يستغرق الكثير لاستخراج طريقة send_message ().

نصائح أخرى

هل اعتبرت ملتوية صفقة؟ يؤخذ الرمز أدناه من هنا:

from struct import pack
from OpenSSL import SSL
from twisted.internet import reactor
from twisted.internet.protocol import ClientFactory, Protocol
from twisted.internet.ssl import ClientContextFactory

APNS_SERVER_HOSTNAME = "<insert the push hostname from your iPhone developer portal>"
APNS_SERVER_PORT = 2195
APNS_SSL_CERTIFICATE_FILE = "<your ssl certificate.pem>"
APNS_SSL_PRIVATE_KEY_FILE = "<your ssl private key.pem>"

class APNSClientContextFactory(ClientContextFactory):
    def __init__(self):
        self.ctx = SSL.Context(SSL.SSLv3_METHOD)
        self.ctx.use_certificate_file(APNS_SSL_CERTIFICATE_FILE)
        self.ctx.use_privatekey_file(APNS_SSL_PRIVATE_KEY_FILE)

    def getContext(self):
        return self.ctx

class APNSProtocol(Protocol):
    def sendMessage(self, deviceToken, payload):
        # notification messages are binary messages in network order
        # using the following format:
        # <1 byte command> <2 bytes length><token> <2 bytes length><payload>
        fmt = "!cH32cH%dc" % len(payload)
        command = 0
        msg = struct.pack(fmt, command, deviceToken,
                          len(payload), payload)
        self.transport.write(msg)

class APNSClientFactory(ClientFactory):
    def buildProtocol(self, addr):
        print "Connected to APNS Server %s:%u" % (addr.host, addr.port)
        return APNSProtocol()

    def clientConnectionLost(self, connector, reason):
        print "Lost connection. Reason: %s" % reason

    def clientConnectionFailed(self, connector, reason):
        print "Connection failed. Reason: %s" % reason

if __name__ == '__main__':
    reactor.connectSSL(APNS_SERVER_HOSTNAME, 
                       APNS_SERVER_PORT,
                       APNSClientFactory(), 
                       APNSClientContextFactory())
    reactor.run()

كان هناك عدد قليل من الأخطاء في التعليمات البرمجية المنشور أصلا، لذلك إليك نسخة تصحيح تعمل بالنسبة لي.

from struct import pack
from OpenSSL import SSL
from twisted.internet import reactor
from twisted.internet.protocol import ClientFactory, Protocol
from twisted.internet.ssl import ClientContextFactory
import binascii
import struct

APNS_SERVER_HOSTNAME = "gateway.sandbox.push.apple.com"
APNS_SERVER_PORT = 2195
APNS_SSL_CERTIFICATE_FILE = "<your ssl certificate.pem>"
APNS_SSL_PRIVATE_KEY_FILE = "<your ssl private key.pem>"
DEVICE_TOKEN = "<hexlified device token>"
MESSAGE = '{"aps":{"alert":"twisted test"}}'

class APNSClientContextFactory(ClientContextFactory):
    def __init__(self):
        self.ctx = SSL.Context(SSL.SSLv3_METHOD)
        self.ctx.use_certificate_file(APNS_SSL_CERTIFICATE_FILE)
        self.ctx.use_privatekey_file(APNS_SSL_PRIVATE_KEY_FILE)

    def getContext(self):
        return self.ctx

class APNSProtocol(Protocol):

    def connectionMade(self):
        print "connection made"
        self.sendMessage(binascii.unhexlify(DEVICE_TOKEN), MESSAGE)
        self.transport.loseConnection()

    def sendMessage(self, deviceToken, payload):
        # notification messages are binary messages in network order
        # using the following format:
        # <1 byte command> <2 bytes length><token> <2 bytes length><payload>
        fmt = "!cH32sH%ds" % len(payload)
        command = '\x00'
        msg = struct.pack(fmt, command, 32, deviceToken,
                          len(payload), payload)
        print "%s: %s" %(binascii.hexlify(deviceToken), binascii.hexlify(msg))
        self.transport.write(msg)

class APNSClientFactory(ClientFactory):
    def buildProtocol(self, addr):
        print "Connected to APNS Server %s:%u" % (addr.host, addr.port)
        return APNSProtocol()

    def clientConnectionLost(self, connector, reason):
        print "Lost connection. Reason: %s" % reason

    def clientConnectionFailed(self, connector, reason):
        print "Connection failed. Reason: %s" % reason

if __name__ == '__main__':
    reactor.connectSSL(APNS_SERVER_HOSTNAME,
                       APNS_SERVER_PORT,
                       APNSClientFactory(),
                       APNSClientContextFactory())
    reactor.run()

حاول التحديث بأحدث إصدار APNSWRAPPER (0.4). يوجد في دعم أداة سطر الأوامر Openssl (Openssl S_Client) الآن.

حاولت كليهما APNSWrapper و Lee Peckham's Code ولم تتمكن من الحصول عليها للعمل تحت سنو نمر مع بيثون 2.6. بعد الكثير من التجربة والخطأ يعمل أخيرا مع pyOpenSSL.

فعلت بالفعل وظيفة مع التفاصيل ومقشرات التعليمات البرمجية هنا لذلك سوف أحال لك فقط هناك.

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top