iOS原生实现推送
一、iOS推送机制
Provider是给你手机应用发出推送消息的服务器,而APNS(Apple Push Notification Service)则是苹果消息推送服务器。你本地的服务器当需要给应用推送一条消息的时候,先要将消息发出到苹果推送服务器,然后再由苹果推送服务器将消息发到安装了该应用的手机。
接下来再看一张解释图:
根据上图的逻辑:
1. iOS应用需要去注册APNS消息推送功能;
2.当苹果APNS推送服收到来自你应用的注册消息就会给客户端返回一串device token(很重要);
3.将应用收到的device Token传给本地的Push服务器;
4.当你需要为应用推送消息的时候,你本地的推送服务器会将消息;以及Device Token打包发送到苹果的APNS服;
5.APNS再将消息推送给目的iphone。
证书分为开发推送证书和生产推送证书,当在开发真机测试时使用开发推送证书.p12,在AdHoc(打包测试)及上线时使用生产推送证书.p12。
三、后台集成推送环境(集成以开发环境为实例)
接下来我们打开终端将他们生成.pem文件:
1. 把aps_development .cer文件生成.pcm文件,cd到push文件夹下
yangliang:~ apple$ openssl x509 -in aps_development.cer-inform der -out PushCert.pem
2. 将开发证书p.12生产.pem文件:
yangliang:Jpush apple$ openssl pkcs12 -nocerts -outPushCertKey.pem -in 生产证书.p12
进行该步骤是要验证证书的秘钥(需要验证两次密码ABC123)
Enter Import Password:
MAC verified OK
Enter PEM pass phrase:
Verifying - Enter PEM pass phrase:
yangliang:Jpush apple$
上边输入的密码则是你导出证书所设的密码,即ABC123 接着还会让你输入.pem文件的密码,还是使用ABC123好了,防止混淆。
这样我们在push文件夹中就又得到了两个文件,。
3. 把PushCert.pem和PushCertKey.pem合并为一个pem文件:
yangliang:Jpush apple$ cat PushCert.pem pushCertKey.pem> ck.pem
在push文件夹中又多了一个ck.pem文件,以上我们把需要使用的文件都准备好了
四、测试环境
为了测试证书工作的状况,我们可以使用“telnet gateway.sandbox.push.apple.com2195”来检测一下,如果显示:
yangliang:Jpush apple$ telnetgateway.sandbox.push.apple.com 2195
Trying 17.188.137.58...
Connected to gateway.sandbox.push-apple.com.akadns.net.
Escape character is '^]'.
则表示成功。
最后使用我们生成的证书和私钥来设置一个安全的链接去链接苹果服务器:
yangliang:Jpush apple$ openssl s_client -connectgateway.sandbox.push.apple.com:2195 -cert PushChatCert.pem -key PushKey.pem
需要输入密码(ABC123我们刚才所设置的)。
当返回下面数据时则表示连接成功:
CONNECTED(00000003)
depth=1 /C=US/O=Entrust, Inc./OU=Seewww.entrust.net/legal-terms/OU=(c) 2012 Entrust, Inc. - for authorized useonly/CN=Entrust Certification Authority - L1K
verify error:num=20:unable to get localissuer certificate
verify return:0
---
Certificate chain
0s:/C=US/ST=California/L=Cupertino/O=AppleInc./CN=gateway.sandbox.push.apple.com
i:/C=US/O=Entrust, Inc./OU=See www.entrust.net/legal-terms/OU=(c) 2012Entrust, Inc. - for authorized use only/CN=Entrust Certification Authority -L1K
1s:/C=US/O=Entrust, Inc./OU=See www.entrust.net/legal-terms/OU=(c) 2012 Entrust,Inc. - for authorized use only/CN=Entrust Certification Authority - L1K
i:/O=Entrust.net/OU=www.entrust.net/CPS_2048 incorp. by ref. (limitsliab.)/OU=(c) 1999 Entrust.net Limited/CN=Entrust.net Certification Authority(2048)
---
Server certificate
-----BEGIN CERTIFICATE-----
MIIFUTCCBDmgAwIBAgIRAP/KN+WwyNu6AAAAAFDYCGYwDQYJKoZIhvcNAQELBQAw
gboxCzAJBgNVBAYTAlVTMRYwFAYDVQQKEw1FbnRydXN0LCBJbmMuMSgwJgYDVQQL
Ex9TZWUgd3d3LmVudHJ1c3QubmV0L2xlZ2FsLXRlcm1zMTkwNwYDVQQLEzAoYykg
MjAxMiBFbnRydXN0LCBJbmMuIC0gZm9yIGF1dGhvcml6ZWQgdXNlIG9ubHkxLjAs
BgNVBAMTJUVudHJ1c3QgQ2VydGlmaWNhdGlvbiBBdXRob3JpdHkgLSBMMUswHhcN
MTYwNTA1MTcyMjM1WhcNMTgwNTAyMTc1MjM0WjB0MQswCQYDVQQGEwJVUzETMBEG
A1UECBMKQ2FsaWZvcm5pYTESMBAGA1UEBxMJQ3VwZXJ0aW5vMRMwEQYDVQQKEwpB
cHBsZSBJbmMuMScwJQYDVQQDEx5nYXRld2F5LnNhbmRib3gucHVzaC5hcHBsZS5j
b20wggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDu8g0rJ6zbAczB/gpg
QSDkK9ftwW38Z8bAgsV1uZXvYfjmq8h69bIy0v1TMie03mEMSm/WVHWisCFSJSIG
11QX3Z6mgw+Qff4M3VccSTZaPiEofCp/feUXQqzImBhe4/RVyem9n6ZURAYyWYN9
4xTedpSgvQQb5aTnEpmTGMgxL7pKBRRErtKB6PlqixJ176AisR4Q2KxVYwGakM9e
a34qj+qbVu+v6B8XXV1CUA4OmS59dpQ5YXBYdHFEaqaDs+IhUrElB2hAg7Gcc649
O/EeQqjs8VwsmGM+FYIftvfkyCfeJz1Lfk9fdNMcAm4jWh/n2LzqPT1fZaDS9L1E
z1vjAgMBAAGjggGVMIIBkTAOBgNVHQ8BAf8EBAMCBaAwHQYDVR0lBBYwFAYIKwYB
BQUHAwEGCCsGAQUFBwMCMDMGA1UdHwQsMCowKKAmoCSGImh0dHA6Ly9jcmwuZW50
cnVzdC5uZXQvbGV2ZWwxay5jcmwwSwYDVR0gBEQwQjA2BgpghkgBhvpsCgEFMCgw
JgYIKwYBBQUHAgEWGmh0dHA6Ly93d3cuZW50cnVzdC5uZXQvcnBhMAgGBmeBDAEC
AjBoBggrBgEFBQcBAQRcMFowIwYIKwYBBQUHMAGGF2h0dHA6Ly9vY3NwLmVudHJ1
c3QubmV0MDMGCCsGAQUFBzAChidodHRwOi8vYWlhLmVudHJ1c3QubmV0L2wxay1j
aGFpbjI1Ni5jZXIwKQYDVR0RBCIwIIIeZ2F0ZXdheS5zYW5kYm94LnB1c2guYXBw
bGUuY29tMB8GA1UdIwQYMBaAFIKicHTdvFM/z3vU981/p2DGCky/MB0GA1UdDgQW
BBQilGEKLJhxmPA0qq6OtdmvSADjszAJBgNVHRMEAjAAMA0GCSqGSIb3DQEBCwUA
A4IBAQB9KaD/0IUHBykbu1detIDPgDCkvEkcTg+Aoge6h1yj1wkSv3d94mJif+jy
/p9Yz0Uf69d7tMAK8nrefin4cBFSdJpj9HSk0AUaQoDFAz+BLuGMN8J05iwWKYf+
IkS7sr+z3RgGkFyH9XCMAu+MrvCz/r+SIuM6AO2/F/iwmBU1UrerbCjBfPxM+sNB
BU0lUv0w0Xm3/ZyDh+Em0u15vM8D4NtkK6v0K+3GdgBU6xGgpX68eqszSIbkRzMu
Hke/uLEPEGV/r6N1NSgQqbajUVgqUCrG3GPHsmuVHCFWSP1YYc+2FwKYOLEUgbma
yYBeaZ+LYzqYxyZzBvj+jTaRKi56
-----END CERTIFICATE-----
subject=/C=US/ST=California/L=Cupertino/O=AppleInc./CN=gateway.sandbox.push.apple.com
issuer=/C=US/O=Entrust, Inc./OU=Seewww.entrust.net/legal-terms/OU=(c) 2012 Entrust, Inc. - for authorized use only/CN=EntrustCertification Authority - L1K
---
Acceptable client certificate CA names
/C=US/O=Apple Inc./OU=Apple CertificationAuthority/CN=Apple Root CA
/C=US/O=Apple Inc./OU=Apple CertificationAuthority/CN=Apple Application Integration Certification Authority
/C=US/O=Apple Inc./OU=Apple WorldwideDeveloper Relations/CN=Apple Worldwide Developer Relations CertificationAuthority
/C=US/ST=CA/L=Cupertino/O=AppleInc./OU=Internet Software and Services/CN=iCloudTest/[email protected]
/CN=Apple Application Integration 2Certification Authority/OU=Apple Certification Authority/O=Apple Inc./C=US
---
SSL handshake has read 3522 bytes and written2155 bytes
---
New, TLSv1/SSLv3, Cipher is AES256-SHA
Server public key is 2048 bit
Secure Renegotiation IS supported
Compression: NONE
Expansion: NONE
SSL-Session:
Protocol : TLSv1
Cipher : AES256-SHA
Session-ID:
Session-ID-ctx:
Master-Key:7BD6F71EAF67BDB0ED6186E7471DDC701E255FE10CD6647DBC82A05D83BE682BC704E293EE85AC6A5B094DB70542E2A9
Key-Arg : None
Start Time: 1480319802
Timeout : 300 (sec)
Verify return code: 0 (ok)
---
五.服务器端推送脚本(PHP):
将iOSJpush.php这个推送脚本也放在push文件夹中(iOSJpush.php见附件):
deviceToken填写你接收到的token,passPhrase则填写你的ck.pem设置的密码(即ristone2016)。
使用终端进入到push文件夹,在终端输入
$ php iOSJpush.php
Connected to APNS
Message successfully delivered
若显示以上提示则表示推送成功了。
附上推送图片:
iOSJpush.php
// ??????????deviceToken???????????????
//ios10
//$deviceToken = '715458212b09cf55c3385cc665f76a187f5abcd9db3f1888a9a69a60ee14413d';
//ios9
$deviceToken = 'e0cba87a9c99769c5fe1051fa3ac5b8fade2aaa6e732742c39a8dad3d46d4111';
// Put your private key's passphrase here:
$passphrase = 'ABC123';
// Put your alert message here:
$message = '[晨读]马上到吃饭时间了';
////////////////////////////////////////////////////////////////////////////////
$ctx = stream_context_create();
stream_context_set_option($ctx, 'ssl','local_cert', 'ck.pem');
stream_context_set_option($ctx, 'ssl','passphrase', $passphrase);
// Open a connection to the APNS server
//??????????
//$fp = stream_socket_client(?ssl://gateway.push.apple.com:2195?, $err, $errstr, 60, //STREAM_CLIENT_CONNECT, $ctx);
//?????????????appstore??????
$fp = stream_socket_client(
'ssl://gateway.sandbox.push.apple.com:2195', $err,
$errstr, 60, STREAM_CLIENT_CONNECT|STREAM_CLIENT_PERSISTENT, $ctx);
if (!$fp)
exit("Failed to connect: $err $errstr". PHP_EOL);
echo'Connected to APNS' . PHP_EOL;
// Create the payload body
$body['aps'] =array(
'alert' => $message,
'sound' =>'default',
'badge' =>+1,
'type' =>1
);
// Encode the payload as JSON
$payload = json_encode($body);
// Build the binary notification
$msg = chr(0). pack('n',32) . pack('H*', $deviceToken). pack('n', strlen($payload)). $payload;
// Send it to the server
$result = fwrite($fp, $msg, strlen($msg));
if (!$result)
echo'Message not delivered' . PHP_EOL;
else
echo'Message successfully delivered'. PHP_EOL;
// Close the connection to the server
fclose($fp);
?>