Apple Push Notification Service with PHP Script

2019-02-10 07:42发布

问题:

I'm trying so send push notifications ton my iPhone (APNS). I read this post and try to implement it. So all my certificates are good (normaly).

Now I have this php script :

$device = '4f30e047 c8c05db9 3fa87e7d ca5325f7 738cb2c0 0b4a02d4 d4329a42 a7128173'; // My iphone deviceToken
$payload['aps'] = array('alert' => 'This is the alert text', 'badge' => 1, 'sound' => 'default');
$payload['server'] = array('serverId' => $serverId, 'name' => $name);
$output = json_encode($payload);

$apnsCert = 'apple_push_notification_production.pem';

$streamContext = stream_context_create();
stream_context_set_option($streamContext, 'ssl', 'local_cert', $apnsCert);

$apns = stream_socket_client('ssl://gateway.sandbox.push.apple.com:2195', $error, $errorString, 2, STREAM_CLIENT_CONNECT, $streamContext);

$apnsMessage = chr(0) . chr(0) . chr(32) . pack('H*', str_replace(' ', '', $device)) . chr(0) . chr(strlen($payload)) . $payload;
fwrite($apns, $apnsMessage);

//socket_close($apns); seems to be wrong here ...
fclose($apns);

When I run this script nothing happen. no error just an empty page but my iPhone doesn't receive the push notification ...

Have you got an idea?

Thanks a lot !

回答1:

no space in device token, strip them



回答2:

For development certificate you need url

'ssl://gateway.sandbox.push.apple.com:2195'
but for production
'ssl://gateway.push.apple.com:2195'



回答3:

Strip the spaces from token and even then it's not work then

$apnsHost = 'gateway.sandbox.push.apple.com';

Remove "sandbox" from this url and it will run.



回答4:

If you have more than one device and you loop through them I found that you have to create a new stream_context_create for each fwrite to prevent apple from closing the connection for a bad token.

FYI



回答5:

To send notifications success fully you have to do 1 more thing.

Replace $output = json_encode($payload);

to $payload = json_encode($payload);



回答6:

You are missing to provice certificate private key. Add this row: stream_context_set_option($streamContext, 'ssl', 'passphrase', $certificatePrivateKey);