private static function getServerP256() { $generator = CurveFactory::getGeneratorByName('nist-p256'); $privateKeySerializer = new PemPrivateKeySerializer(new DerPrivateKeySerializer()); $privateKey = $generator->createPrivateKey(); $privateKeyStr = $privateKeySerializer->serialize($privateKey); $publicKeySerializer = new PemPublicKeySerializer(new DerPublicKeySerializer()); $publicKey = $privateKey->getPublicKey(); $publicKeyStr = $publicKeySerializer->serialize($publicKey); return array('private' => $privateKeyStr, 'public' => $publicKeyStr); }
function setVAPIDInfo($privateKey, $audience, $subject) { if (!USE_VAPID || !$privateKey || !$audience || !$subject) { return; } $builder = new Builder(); $token = $builder->setAudience($audience)->setExpiration(time() + 86400)->setSubject($subject)->sign(new Sha256(), new Key($privateKey))->getToken(); $this->additionalHeaders['Authorization'] = 'Bearer ' . $token; $privKeySerializer = new PemPrivateKeySerializer(new DerPrivateKeySerializer()); $privateKeyObject = $privKeySerializer->parse($privateKey); $publicKeyObject = $privateKeyObject->getPublicKey(); $pointSerializer = new UncompressedPointSerializer(EccFactory::getAdapter()); $this->additionalHeaders['Crypto-Key'] = 'p256ecdsa=' . Base64Url::encode(hex2bin($pointSerializer->serialize($publicKeyObject->getPoint()))); }
function get_public_key($privateKey) { $publicKeyVal = __('Your private key is invalid.', 'web-push'); error_reporting(E_ERROR); try { $privKeySerializer = new PemPrivateKeySerializer(new DerPrivateKeySerializer()); $privateKeyObject = $privKeySerializer->parse($privateKey); $publicKeyObject = $privateKeyObject->getPublicKey(); $pointSerializer = new UncompressedPointSerializer(EccFactory::getAdapter()); $publicKeyVal = Base64Url::encode(hex2bin($pointSerializer->serialize($publicKeyObject->getPoint()))); } catch (Exception $e) { // Ignore exceptions while getting the public key from the private key. } error_reporting(E_ALL); return $publicKeyVal; }
public static function generate_vapid_options() { if (USE_VAPID) { if (!get_option('webpush_vapid_key')) { $generator = EccFactory::getNistCurves()->generator256(); $privKeySerializer = new PemPrivateKeySerializer(new DerPrivateKeySerializer()); update_option('webpush_vapid_key', $privKeySerializer->serialize($generator->createPrivateKey())); } if (!get_option('webpush_vapid_subject')) { update_option('webpush_vapid_subject', 'mailto:' . get_option('admin_email')); } if (!get_option('webpush_vapid_audience')) { $parsedURL = parse_url(home_url('/', 'https')); update_option('webpush_vapid_audience', $parsedURL['scheme'] . '://' . $parsedURL['host'] . (isset($parsedURL['port']) ? ':' . $parsedURL['port'] : '')); } } }
function test_generate_vapid_options() { if (!USE_VAPID) { return; } // Test that when the plugin is installed it has valid VAPID info. $privKeySerializer = new PemPrivateKeySerializer(new DerPrivateKeySerializer()); $privateKeyObject = $privKeySerializer->parse(get_option('webpush_vapid_key')); $publicKeyObject = $privateKeyObject->getPublicKey(); $this->assertEquals('mailto:admin@example.org', get_option('webpush_vapid_subject')); $this->assertEquals('https://example.org', get_option('webpush_vapid_audience')); // Test regenerating the VAPID info. update_option('webpush_vapid_key', ''); update_option('webpush_vapid_subject', ''); update_option('webpush_vapid_audience', ''); WebPush_DB::generate_vapid_options(); $privKeySerializer = new PemPrivateKeySerializer(new DerPrivateKeySerializer()); $privateKeyObject = $privKeySerializer->parse(get_option('webpush_vapid_key')); $publicKeyObject = $privateKeyObject->getPublicKey(); $this->assertEquals('mailto:admin@example.org', get_option('webpush_vapid_subject')); $this->assertEquals('https://example.org', get_option('webpush_vapid_audience')); }
/** * This method takes the required VAPID parameters and returns the required * header to be added to a Web Push Protocol Request. * * @param string $audience This must be the origin of the push service * @param string $subject This should be a URL or a 'mailto:' email address * @param string $publicKey The decoded VAPID public key * @param string $privateKey The decoded VAPID private key * @param int $expiration The expiration of the VAPID JWT. (UNIX timestamp) * * @return array Returns an array with the 'Authorization' and 'Crypto-Key' values to be used as headers */ public static function getVapidHeaders($audience, $subject, $publicKey, $privateKey, $expiration = null) { $expirationLimit = time() + 43200; // equal margin of error between 0 and 24h if (!isset($expiration) || $expiration > $expirationLimit) { $expiration = $expirationLimit; } $header = array('typ' => 'JWT', 'alg' => 'ES256'); $jwtPayload = json_encode(array('aud' => $audience, 'exp' => $expiration, 'sub' => $subject), JSON_UNESCAPED_SLASHES | JSON_NUMERIC_CHECK); $generator = EccFactory::getNistCurves()->generator256(); $privateKeyObject = $generator->getPrivateKeyFrom(gmp_init(bin2hex($privateKey), 16)); $pemSerialize = new PemPrivateKeySerializer(new DerPrivateKeySerializer()); $pem = $pemSerialize->serialize($privateKeyObject); $jwk = JWKFactory::createFromKey($pem, null); $jws = JWSFactory::createJWSToCompactJSON($jwtPayload, $jwk, $header); return array('Authorization' => 'WebPush ' . $jws, 'Crypto-Key' => 'p256ecdsa=' . Base64Url::encode($publicKey)); }
/** * @param InputInterface $input * @param OutputInterface $output * @param QuestionHelper $helper * @param string $curveName * @param bool $useEncryption * @return array */ public function generateKeyData(InputInterface $input, OutputInterface $output, QuestionHelper $helper, $curveName, $useEncryption) { if (!is_bool($useEncryption)) { throw new \InvalidArgumentException('useEncryption parameter must be a boolean'); } /** * @var GeneratorPoint $generator */ list(, $generator) = Curves::load($curveName); $key = $generator->createPrivateKey(); if ($useEncryption) { $password = $this->promptForPassword($input, $output, $helper); $encrypted = new EncryptedPrivateKey($key, 'AES-128-CBC', random_bytes(16)); $serializer = new EncryptedPrivateKeySerializer(new DerPrivateKeySerializer()); $keyData = $serializer->serialize($encrypted, $password); } else { $serializer = new PemPrivateKeySerializer(new DerPrivateKeySerializer()); $keyData = $serializer->serialize($key); } $adapter = EccFactory::getAdapter(); $publicKey = $key->getPublicKey(); $publicSerializer = new SshPublicKeySerializer($adapter, new UncompressedPointSerializer($adapter)); $publicData = $publicSerializer->serialize($curveName, $publicKey); $localUser = posix_getpwuid(posix_geteuid()); $localHost = gethostname(); $publicData = sprintf("ecdsa-sha2-%s %s %s@%s\n", $curveName, $publicData, $localUser['name'], $localHost); return [$keyData, $publicData]; }