edamov / pushok

PHP client for Apple Push Notification Service (APNs) - Send push notifications to iOS using the new APNs HTTP/2 protocol with token-based (JWT with p8 private key)
MIT License
378 stars 120 forks source link

VoIP pem certificates don't work #140

Closed grey-dev-0 closed 3 years ago

grey-dev-0 commented 3 years ago

Hello there, we're using your package with Laravel through the APN Laravel notification channel package, standard notifications work fine with a normal p8 key file, however when we try to push VoIP notifications with a pem certificate we get the following Error:

InvalidArgumentException: Unable to load the key. in /home/timeviewer/test_html/vendor/web-token/jwt-key-mgmt/KeyConverter/KeyConverter.php:192
#0 /home/timeviewer/test_html/vendor/web-token/jwt-key-mgmt/KeyConverter/KeyConverter.php(133): Jose\Component\KeyManagement\KeyConverter\KeyConverter::loadKeyFromPEM('-----BEGIN CERT...', '****')
#1 /home/timeviewer/test_html/vendor/web-token/jwt-key-mgmt/JWKFactory.php(308): Jose\Component\KeyManagement\KeyConverter\KeyConverter::loadFromKey('Bag Attributes\n...', '****')')
#2 /home/timeviewer/test_html/vendor/edamov/pushok/src/AuthProvider/Token.php(195): Jose\Component\KeyManagement\JWKFactory::createFromKey('Bag Attributes\n...', '****')', Array)
#3 /home/timeviewer/test_html/vendor/edamov/pushok/src/AuthProvider/Token.php(240): Pushok\AuthProvider\Token->generatePrivateECKey()
#4 /home/timeviewer/test_html/vendor/edamov/pushok/src/AuthProvider/Token.php(111): Pushok\AuthProvider\Token->generate()
#5 /home/timeviewer/test_html/vendor/laravel-notification-channels/apn/src/ApnServiceProvider.php(22): Pushok\AuthProvider\Token::create(Array)

Unfortunately Apple does NOT provide anyway to generate p8 keys for VoIP notifications as of now, the error seems to be originating from the web-token/jwt-key-mgmt package you're relying on to generate the token, I was going to pass this issue to the maintainers of that package but, because this issue might be more related to how APN currently works I've posted it here.

When debugging I've found out that in KeyConverter class of the mentioned jwt package the following line returns false

$res = openssl_pkey_get_private($pem);

I tired to force pass the password as a second argument to the function but, with no avail, we also tried generating multiple pem certificates for VoIP and they all yielded the same error, we'll keep trying to resolve the issue, we appreciate your support with this problem, and if we managed to find a solution I'll post it here for anyone who might be facing the same dilemma.

grey-dev-0 commented 3 years ago

Alright, the solution was pretty simple after some research in Apple's documentation, if you're going to use VoIP notifications with token-based authentication with their service i.e. using the p8 key file you'll need to append .voip at the end of your bundle ID.

E.g. your bundle id is com.something.app then you'll need to set it to com.something.app.voip, and that's how it worked with me, I think this point needs to be emphasized in the documentation - if it's not already - and, thanks @edamov for this essential package.