diff --git a/src/Auth.php b/src/Auth.php index d8afa2b..b80d3e6 100644 --- a/src/Auth.php +++ b/src/Auth.php @@ -623,11 +623,16 @@ public static function validate_token( $token = null, $refresh = false ) { */ public static function get_auth_header() { + /** + * Filter target HTTP Header. + */ + $header_name = apply_filters( 'graphql_jwt_auth_header_name', 'HTTP_AUTHORIZATION' ); + /** * Looking for the HTTP_AUTHORIZATION header, if not present just * return the user. */ - $auth_header = isset( $_SERVER['HTTP_AUTHORIZATION'] ) ? $_SERVER['HTTP_AUTHORIZATION'] : false; + $auth_header = isset( $_SERVER[ $header_name] ) ? $_SERVER[ $header_name ] : false; /** * Double check for different auth header string (server dependent) diff --git a/vendor/composer/ClassLoader.php b/vendor/composer/ClassLoader.php index fce8549..6d0c3f2 100644 --- a/vendor/composer/ClassLoader.php +++ b/vendor/composer/ClassLoader.php @@ -37,11 +37,13 @@ * * @author Fabien Potencier * @author Jordi Boggiano - * @see http://www.php-fig.org/psr/psr-0/ - * @see http://www.php-fig.org/psr/psr-4/ + * @see https://www.php-fig.org/psr/psr-0/ + * @see https://www.php-fig.org/psr/psr-4/ */ class ClassLoader { + private $vendorDir; + // PSR-4 private $prefixLengthsPsr4 = array(); private $prefixDirsPsr4 = array(); @@ -57,10 +59,17 @@ class ClassLoader private $missingClasses = array(); private $apcuPrefix; + private static $registeredLoaders = array(); + + public function __construct($vendorDir = null) + { + $this->vendorDir = $vendorDir; + } + public function getPrefixes() { if (!empty($this->prefixesPsr0)) { - return call_user_func_array('array_merge', $this->prefixesPsr0); + return call_user_func_array('array_merge', array_values($this->prefixesPsr0)); } return array(); @@ -300,6 +309,17 @@ public function getApcuPrefix() public function register($prepend = false) { spl_autoload_register(array($this, 'loadClass'), true, $prepend); + + if (null === $this->vendorDir) { + return; + } + + if ($prepend) { + self::$registeredLoaders = array($this->vendorDir => $this) + self::$registeredLoaders; + } else { + unset(self::$registeredLoaders[$this->vendorDir]); + self::$registeredLoaders[$this->vendorDir] = $this; + } } /** @@ -308,13 +328,17 @@ public function register($prepend = false) public function unregister() { spl_autoload_unregister(array($this, 'loadClass')); + + if (null !== $this->vendorDir) { + unset(self::$registeredLoaders[$this->vendorDir]); + } } /** * Loads the given class or interface. * * @param string $class The name of the class - * @return bool|null True if loaded, null otherwise + * @return true|null True if loaded, null otherwise */ public function loadClass($class) { @@ -323,6 +347,8 @@ public function loadClass($class) return true; } + + return null; } /** @@ -367,6 +393,16 @@ public function findFile($class) return $file; } + /** + * Returns the currently registered loaders indexed by their corresponding vendor directories. + * + * @return self[] + */ + public static function getRegisteredLoaders() + { + return self::$registeredLoaders; + } + private function findFileWithExtension($class, $ext) { // PSR-4 lookup diff --git a/vendor/composer/InstalledVersions.php b/vendor/composer/InstalledVersions.php new file mode 100644 index 0000000..b3a4e16 --- /dev/null +++ b/vendor/composer/InstalledVersions.php @@ -0,0 +1,337 @@ + + * Jordi Boggiano + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Composer; + +use Composer\Autoload\ClassLoader; +use Composer\Semver\VersionParser; + +/** + * This class is copied in every Composer installed project and available to all + * + * See also https://getcomposer.org/doc/07-runtime.md#installed-versions + * + * To require it's presence, you can require `composer-runtime-api ^2.0` + */ +class InstalledVersions +{ + private static $installed; + private static $canGetVendors; + private static $installedByVendor = array(); + + /** + * Returns a list of all package names which are present, either by being installed, replaced or provided + * + * @return string[] + * @psalm-return list + */ + public static function getInstalledPackages() + { + $packages = array(); + foreach (self::getInstalled() as $installed) { + $packages[] = array_keys($installed['versions']); + } + + if (1 === \count($packages)) { + return $packages[0]; + } + + return array_keys(array_flip(\call_user_func_array('array_merge', $packages))); + } + + /** + * Returns a list of all package names with a specific type e.g. 'library' + * + * @param string $type + * @return string[] + * @psalm-return list + */ + public static function getInstalledPackagesByType($type) + { + $packagesByType = array(); + + foreach (self::getInstalled() as $installed) { + foreach ($installed['versions'] as $name => $package) { + if (isset($package['type']) && $package['type'] === $type) { + $packagesByType[] = $name; + } + } + } + + return $packagesByType; + } + + /** + * Checks whether the given package is installed + * + * This also returns true if the package name is provided or replaced by another package + * + * @param string $packageName + * @param bool $includeDevRequirements + * @return bool + */ + public static function isInstalled($packageName, $includeDevRequirements = true) + { + foreach (self::getInstalled() as $installed) { + if (isset($installed['versions'][$packageName])) { + return $includeDevRequirements || empty($installed['versions'][$packageName]['dev_requirement']); + } + } + + return false; + } + + /** + * Checks whether the given package satisfies a version constraint + * + * e.g. If you want to know whether version 2.3+ of package foo/bar is installed, you would call: + * + * Composer\InstalledVersions::satisfies(new VersionParser, 'foo/bar', '^2.3') + * + * @param VersionParser $parser Install composer/semver to have access to this class and functionality + * @param string $packageName + * @param string|null $constraint A version constraint to check for, if you pass one you have to make sure composer/semver is required by your package + * @return bool + */ + public static function satisfies(VersionParser $parser, $packageName, $constraint) + { + $constraint = $parser->parseConstraints($constraint); + $provided = $parser->parseConstraints(self::getVersionRanges($packageName)); + + return $provided->matches($constraint); + } + + /** + * Returns a version constraint representing all the range(s) which are installed for a given package + * + * It is easier to use this via isInstalled() with the $constraint argument if you need to check + * whether a given version of a package is installed, and not just whether it exists + * + * @param string $packageName + * @return string Version constraint usable with composer/semver + */ + public static function getVersionRanges($packageName) + { + foreach (self::getInstalled() as $installed) { + if (!isset($installed['versions'][$packageName])) { + continue; + } + + $ranges = array(); + if (isset($installed['versions'][$packageName]['pretty_version'])) { + $ranges[] = $installed['versions'][$packageName]['pretty_version']; + } + if (array_key_exists('aliases', $installed['versions'][$packageName])) { + $ranges = array_merge($ranges, $installed['versions'][$packageName]['aliases']); + } + if (array_key_exists('replaced', $installed['versions'][$packageName])) { + $ranges = array_merge($ranges, $installed['versions'][$packageName]['replaced']); + } + if (array_key_exists('provided', $installed['versions'][$packageName])) { + $ranges = array_merge($ranges, $installed['versions'][$packageName]['provided']); + } + + return implode(' || ', $ranges); + } + + throw new \OutOfBoundsException('Package "' . $packageName . '" is not installed'); + } + + /** + * @param string $packageName + * @return string|null If the package is being replaced or provided but is not really installed, null will be returned as version, use satisfies or getVersionRanges if you need to know if a given version is present + */ + public static function getVersion($packageName) + { + foreach (self::getInstalled() as $installed) { + if (!isset($installed['versions'][$packageName])) { + continue; + } + + if (!isset($installed['versions'][$packageName]['version'])) { + return null; + } + + return $installed['versions'][$packageName]['version']; + } + + throw new \OutOfBoundsException('Package "' . $packageName . '" is not installed'); + } + + /** + * @param string $packageName + * @return string|null If the package is being replaced or provided but is not really installed, null will be returned as version, use satisfies or getVersionRanges if you need to know if a given version is present + */ + public static function getPrettyVersion($packageName) + { + foreach (self::getInstalled() as $installed) { + if (!isset($installed['versions'][$packageName])) { + continue; + } + + if (!isset($installed['versions'][$packageName]['pretty_version'])) { + return null; + } + + return $installed['versions'][$packageName]['pretty_version']; + } + + throw new \OutOfBoundsException('Package "' . $packageName . '" is not installed'); + } + + /** + * @param string $packageName + * @return string|null If the package is being replaced or provided but is not really installed, null will be returned as reference + */ + public static function getReference($packageName) + { + foreach (self::getInstalled() as $installed) { + if (!isset($installed['versions'][$packageName])) { + continue; + } + + if (!isset($installed['versions'][$packageName]['reference'])) { + return null; + } + + return $installed['versions'][$packageName]['reference']; + } + + throw new \OutOfBoundsException('Package "' . $packageName . '" is not installed'); + } + + /** + * @param string $packageName + * @return string|null If the package is being replaced or provided but is not really installed, null will be returned as install path. Packages of type metapackages also have a null install path. + */ + public static function getInstallPath($packageName) + { + foreach (self::getInstalled() as $installed) { + if (!isset($installed['versions'][$packageName])) { + continue; + } + + return isset($installed['versions'][$packageName]['install_path']) ? $installed['versions'][$packageName]['install_path'] : null; + } + + throw new \OutOfBoundsException('Package "' . $packageName . '" is not installed'); + } + + /** + * @return array + * @psalm-return array{name: string, version: string, reference: string, pretty_version: string, aliases: string[], dev: bool, install_path: string} + */ + public static function getRootPackage() + { + $installed = self::getInstalled(); + + return $installed[0]['root']; + } + + /** + * Returns the raw installed.php data for custom implementations + * + * @deprecated Use getAllRawData() instead which returns all datasets for all autoloaders present in the process. getRawData only returns the first dataset loaded, which may not be what you expect. + * @return array[] + * @psalm-return array{root: array{name: string, version: string, reference: string, pretty_version: string, aliases: string[], dev: bool, install_path: string}, versions: array} + */ + public static function getRawData() + { + @trigger_error('getRawData only returns the first dataset loaded, which may not be what you expect. Use getAllRawData() instead which returns all datasets for all autoloaders present in the process.', E_USER_DEPRECATED); + + if (null === self::$installed) { + // only require the installed.php file if this file is loaded from its dumped location, + // and not from its source location in the composer/composer package, see https://github.com/composer/composer/issues/9937 + if (substr(__DIR__, -8, 1) !== 'C') { + self::$installed = include __DIR__ . '/installed.php'; + } else { + self::$installed = array(); + } + } + + return self::$installed; + } + + /** + * Returns the raw data of all installed.php which are currently loaded for custom implementations + * + * @return array[] + * @psalm-return list}> + */ + public static function getAllRawData() + { + return self::getInstalled(); + } + + /** + * Lets you reload the static array from another file + * + * This is only useful for complex integrations in which a project needs to use + * this class but then also needs to execute another project's autoloader in process, + * and wants to ensure both projects have access to their version of installed.php. + * + * A typical case would be PHPUnit, where it would need to make sure it reads all + * the data it needs from this class, then call reload() with + * `require $CWD/vendor/composer/installed.php` (or similar) as input to make sure + * the project in which it runs can then also use this class safely, without + * interference between PHPUnit's dependencies and the project's dependencies. + * + * @param array[] $data A vendor/composer/installed.php data set + * @return void + * + * @psalm-param array{root: array{name: string, version: string, reference: string, pretty_version: string, aliases: string[], dev: bool, install_path: string}, versions: array} $data + */ + public static function reload($data) + { + self::$installed = $data; + self::$installedByVendor = array(); + } + + /** + * @return array[] + * @psalm-return list}> + */ + private static function getInstalled() + { + if (null === self::$canGetVendors) { + self::$canGetVendors = method_exists('Composer\Autoload\ClassLoader', 'getRegisteredLoaders'); + } + + $installed = array(); + + if (self::$canGetVendors) { + foreach (ClassLoader::getRegisteredLoaders() as $vendorDir => $loader) { + if (isset(self::$installedByVendor[$vendorDir])) { + $installed[] = self::$installedByVendor[$vendorDir]; + } elseif (is_file($vendorDir.'/composer/installed.php')) { + $installed[] = self::$installedByVendor[$vendorDir] = require $vendorDir.'/composer/installed.php'; + if (null === self::$installed && strtr($vendorDir.'/composer', '\\', '/') === strtr(__DIR__, '\\', '/')) { + self::$installed = $installed[count($installed) - 1]; + } + } + } + } + + if (null === self::$installed) { + // only require the installed.php file if this file is loaded from its dumped location, + // and not from its source location in the composer/composer package, see https://github.com/composer/composer/issues/9937 + if (substr(__DIR__, -8, 1) !== 'C') { + self::$installed = require __DIR__ . '/installed.php'; + } else { + self::$installed = array(); + } + } + $installed[] = self::$installed; + + return $installed; + } +} diff --git a/vendor/composer/autoload_classmap.php b/vendor/composer/autoload_classmap.php index 94f131b..ceae75a 100644 --- a/vendor/composer/autoload_classmap.php +++ b/vendor/composer/autoload_classmap.php @@ -6,6 +6,7 @@ $baseDir = dirname($vendorDir); return array( + 'Composer\\InstalledVersions' => $vendorDir . '/composer/InstalledVersions.php', 'Firebase\\JWT\\BeforeValidException' => $vendorDir . '/firebase/php-jwt/src/BeforeValidException.php', 'Firebase\\JWT\\ExpiredException' => $vendorDir . '/firebase/php-jwt/src/ExpiredException.php', 'Firebase\\JWT\\JWT' => $vendorDir . '/firebase/php-jwt/src/JWT.php', diff --git a/vendor/composer/autoload_real.php b/vendor/composer/autoload_real.php index 97fa063..a06712a 100644 --- a/vendor/composer/autoload_real.php +++ b/vendor/composer/autoload_real.php @@ -13,19 +13,24 @@ public static function loadClassLoader($class) } } + /** + * @return \Composer\Autoload\ClassLoader + */ public static function getLoader() { if (null !== self::$loader) { return self::$loader; } + require __DIR__ . '/platform_check.php'; + spl_autoload_register(array('ComposerAutoloaderInitb81212723df6ec6a4125604686c14dbf', 'loadClassLoader'), true, true); - self::$loader = $loader = new \Composer\Autoload\ClassLoader(); + self::$loader = $loader = new \Composer\Autoload\ClassLoader(\dirname(\dirname(__FILE__))); spl_autoload_unregister(array('ComposerAutoloaderInitb81212723df6ec6a4125604686c14dbf', 'loadClassLoader')); $useStaticLoader = PHP_VERSION_ID >= 50600 && !defined('HHVM_VERSION') && (!function_exists('zend_loader_file_encoded') || !zend_loader_file_encoded()); if ($useStaticLoader) { - require_once __DIR__ . '/autoload_static.php'; + require __DIR__ . '/autoload_static.php'; call_user_func(\Composer\Autoload\ComposerStaticInitb81212723df6ec6a4125604686c14dbf::getInitializer($loader)); } else { diff --git a/vendor/composer/autoload_static.php b/vendor/composer/autoload_static.php index ccc36a0..32fb435 100644 --- a/vendor/composer/autoload_static.php +++ b/vendor/composer/autoload_static.php @@ -29,6 +29,7 @@ class ComposerStaticInitb81212723df6ec6a4125604686c14dbf ); public static $classMap = array ( + 'Composer\\InstalledVersions' => __DIR__ . '/..' . '/composer/InstalledVersions.php', 'Firebase\\JWT\\BeforeValidException' => __DIR__ . '/..' . '/firebase/php-jwt/src/BeforeValidException.php', 'Firebase\\JWT\\ExpiredException' => __DIR__ . '/..' . '/firebase/php-jwt/src/ExpiredException.php', 'Firebase\\JWT\\JWT' => __DIR__ . '/..' . '/firebase/php-jwt/src/JWT.php', diff --git a/vendor/composer/installed.json b/vendor/composer/installed.json index a0b0f80..8061dbd 100644 --- a/vendor/composer/installed.json +++ b/vendor/composer/installed.json @@ -1,50 +1,52 @@ -[ - { - "name": "firebase/php-jwt", - "version": "v5.1.0", - "version_normalized": "5.1.0.0", - "source": { - "type": "git", - "url": "https://github.com/firebase/php-jwt.git", - "reference": "4566062c68f76f43d44f1643f4970fe89757d4c6" - }, - "dist": { - "type": "zip", - "url": "https://api.github.com/repos/firebase/php-jwt/zipball/4566062c68f76f43d44f1643f4970fe89757d4c6", - "reference": "4566062c68f76f43d44f1643f4970fe89757d4c6", - "shasum": "" - }, - "require": { - "php": ">=5.3.0" - }, - "require-dev": { - "phpunit/phpunit": "^4.8|^5" - }, - "time": "2020-02-24T23:15:03+00:00", - "type": "library", - "installation-source": "dist", - "autoload": { - "psr-4": { - "Firebase\\JWT\\": "src" - } - }, - "notification-url": "https://packagist.org/downloads/", - "license": [ - "BSD-3-Clause" - ], - "authors": [ - { - "name": "Neuman Vong", - "email": "neuman+pear@twilio.com", - "role": "Developer" +{ + "packages": [ + { + "name": "firebase/php-jwt", + "version": "v4.0.0", + "version_normalized": "4.0.0.0", + "source": { + "type": "git", + "url": "https://github.com/firebase/php-jwt.git", + "reference": "dccf163dc8ed7ed6a00afc06c51ee5186a428d35" }, - { - "name": "Anant Narayanan", - "email": "anant@php.net", - "role": "Developer" - } - ], - "description": "A simple library to encode and decode JSON Web Tokens (JWT) in PHP. Should conform to the current spec.", - "homepage": "https://github.com/firebase/php-jwt" - } -] + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/firebase/php-jwt/zipball/dccf163dc8ed7ed6a00afc06c51ee5186a428d35", + "reference": "dccf163dc8ed7ed6a00afc06c51ee5186a428d35", + "shasum": "" + }, + "require": { + "php": ">=5.3.0" + }, + "time": "2016-07-18T04:51:16+00:00", + "type": "library", + "installation-source": "dist", + "autoload": { + "psr-4": { + "Firebase\\JWT\\": "src" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "BSD-3-Clause" + ], + "authors": [ + { + "name": "Neuman Vong", + "email": "neuman+pear@twilio.com", + "role": "Developer" + }, + { + "name": "Anant Narayanan", + "email": "anant@php.net", + "role": "Developer" + } + ], + "description": "A simple library to encode and decode JSON Web Tokens (JWT) in PHP. Should conform to the current spec.", + "homepage": "https://github.com/firebase/php-jwt", + "install-path": "../firebase/php-jwt" + } + ], + "dev": false, + "dev-package-names": [] +} diff --git a/vendor/composer/installed.php b/vendor/composer/installed.php new file mode 100644 index 0000000..a404138 --- /dev/null +++ b/vendor/composer/installed.php @@ -0,0 +1,32 @@ + array( + 'pretty_version' => 'dev-develop', + 'version' => 'dev-develop', + 'type' => 'wordpress-plugin', + 'install_path' => __DIR__ . '/../../', + 'aliases' => array(), + 'reference' => '6f4c18ada3382f51c8aa690aaec3bad994af13f3', + 'name' => 'wp-graphql/wp-graphql-jwt-authentication', + 'dev' => false, + ), + 'versions' => array( + 'firebase/php-jwt' => array( + 'pretty_version' => 'v4.0.0', + 'version' => '4.0.0.0', + 'type' => 'library', + 'install_path' => __DIR__ . '/../firebase/php-jwt', + 'aliases' => array(), + 'reference' => 'dccf163dc8ed7ed6a00afc06c51ee5186a428d35', + 'dev_requirement' => false, + ), + 'wp-graphql/wp-graphql-jwt-authentication' => array( + 'pretty_version' => 'dev-develop', + 'version' => 'dev-develop', + 'type' => 'wordpress-plugin', + 'install_path' => __DIR__ . '/../../', + 'aliases' => array(), + 'reference' => '6f4c18ada3382f51c8aa690aaec3bad994af13f3', + 'dev_requirement' => false, + ), + ), +); diff --git a/vendor/composer/platform_check.php b/vendor/composer/platform_check.php new file mode 100644 index 0000000..7621d4f --- /dev/null +++ b/vendor/composer/platform_check.php @@ -0,0 +1,26 @@ += 50300)) { + $issues[] = 'Your Composer dependencies require a PHP version ">= 5.3.0". You are running ' . PHP_VERSION . '.'; +} + +if ($issues) { + if (!headers_sent()) { + header('HTTP/1.1 500 Internal Server Error'); + } + if (!ini_get('display_errors')) { + if (PHP_SAPI === 'cli' || PHP_SAPI === 'phpdbg') { + fwrite(STDERR, 'Composer detected issues in your platform:' . PHP_EOL.PHP_EOL . implode(PHP_EOL, $issues) . PHP_EOL.PHP_EOL); + } elseif (!headers_sent()) { + echo 'Composer detected issues in your platform:' . PHP_EOL.PHP_EOL . str_replace('You are running '.PHP_VERSION.'.', '', implode(PHP_EOL, $issues)) . PHP_EOL.PHP_EOL; + } + } + trigger_error( + 'Composer detected issues in your platform: ' . implode(' ', $issues), + E_USER_ERROR + ); +} diff --git a/vendor/firebase/php-jwt/README.md b/vendor/firebase/php-jwt/README.md index 9c8b545..d4589b1 100644 --- a/vendor/firebase/php-jwt/README.md +++ b/vendor/firebase/php-jwt/README.md @@ -23,7 +23,7 @@ Example use \Firebase\JWT\JWT; $key = "example_key"; -$payload = array( +$token = array( "iss" => "http://example.org", "aud" => "http://example.com", "iat" => 1356999524, @@ -36,7 +36,7 @@ $payload = array( * https://tools.ietf.org/html/draft-ietf-jose-json-web-algorithms-40 * for a list of spec-compliant algorithms. */ -$jwt = JWT::encode($payload, $key); +$jwt = JWT::encode($token, $key); $decoded = JWT::decode($jwt, $key, array('HS256')); print_r($decoded); @@ -58,87 +58,12 @@ $decoded_array = (array) $decoded; JWT::$leeway = 60; // $leeway in seconds $decoded = JWT::decode($jwt, $key, array('HS256')); -?> -``` -Example with RS256 (openssl) ----------------------------- -```php - "example.org", - "aud" => "example.com", - "iat" => 1356999524, - "nbf" => 1357000000 -); - -$jwt = JWT::encode($payload, $privateKey, 'RS256'); -echo "Encode:\n" . print_r($jwt, true) . "\n"; - -$decoded = JWT::decode($jwt, $publicKey, array('RS256')); - -/* - NOTE: This will now be an object instead of an associative array. To get - an associative array, you will need to cast it as such: -*/ - -$decoded_array = (array) $decoded; -echo "Decode:\n" . print_r($decoded_array, true) . "\n"; ?> ``` Changelog --------- -#### 5.0.0 / 2017-06-26 -- Support RS384 and RS512. - See [#117](https://github.com/firebase/php-jwt/pull/117). Thanks [@joostfaassen](https://github.com/joostfaassen)! -- Add an example for RS256 openssl. - See [#125](https://github.com/firebase/php-jwt/pull/125). Thanks [@akeeman](https://github.com/akeeman)! -- Detect invalid Base64 encoding in signature. - See [#162](https://github.com/firebase/php-jwt/pull/162). Thanks [@psignoret](https://github.com/psignoret)! -- Update `JWT::verify` to handle OpenSSL errors. - See [#159](https://github.com/firebase/php-jwt/pull/159). Thanks [@bshaffer](https://github.com/bshaffer)! -- Add `array` type hinting to `decode` method - See [#101](https://github.com/firebase/php-jwt/pull/101). Thanks [@hywak](https://github.com/hywak)! -- Add all JSON error types. - See [#110](https://github.com/firebase/php-jwt/pull/110). Thanks [@gbalduzzi](https://github.com/gbalduzzi)! -- Bugfix 'kid' not in given key list. - See [#129](https://github.com/firebase/php-jwt/pull/129). Thanks [@stampycode](https://github.com/stampycode)! -- Miscellaneous cleanup, documentation and test fixes. - See [#107](https://github.com/firebase/php-jwt/pull/107), [#115](https://github.com/firebase/php-jwt/pull/115), - [#160](https://github.com/firebase/php-jwt/pull/160), [#161](https://github.com/firebase/php-jwt/pull/161), and - [#165](https://github.com/firebase/php-jwt/pull/165). Thanks [@akeeman](https://github.com/akeeman), - [@chinedufn](https://github.com/chinedufn), and [@bshaffer](https://github.com/bshaffer)! - #### 4.0.0 / 2016-07-17 - Add support for late static binding. See [#88](https://github.com/firebase/php-jwt/pull/88) for details. Thanks to [@chappy84](https://github.com/chappy84)! - Use static `$timestamp` instead of `time()` to improve unit testing. See [#93](https://github.com/firebase/php-jwt/pull/93) for details. Thanks to [@josephmcdermott](https://github.com/josephmcdermott)! @@ -189,12 +114,6 @@ Time: 0 seconds, Memory: 2.50Mb OK (5 tests, 5 assertions) ``` -New Lines in private keys ------ - -If your private key contains `\n` characters, be sure to wrap it in double quotes `""` -and not single quotes `''` in order to properly interpret the escaped characters. - License ------- [3-Clause BSD](http://opensource.org/licenses/BSD-3-Clause). diff --git a/vendor/firebase/php-jwt/composer.json b/vendor/firebase/php-jwt/composer.json index 9f1a42c..1a5e93b 100644 --- a/vendor/firebase/php-jwt/composer.json +++ b/vendor/firebase/php-jwt/composer.json @@ -23,7 +23,5 @@ "Firebase\\JWT\\": "src" } }, - "require-dev": { - "phpunit/phpunit": "^4.8|^5" - } + "minimum-stability": "dev" } diff --git a/vendor/firebase/php-jwt/package.xml b/vendor/firebase/php-jwt/package.xml new file mode 100644 index 0000000..a95b056 --- /dev/null +++ b/vendor/firebase/php-jwt/package.xml @@ -0,0 +1,77 @@ + + + JWT + pear.php.net + A JWT encoder/decoder. + A JWT encoder/decoder library for PHP. + + Neuman Vong + lcfrs + neuman+pear@twilio.com + yes + + + Firebase Operations + firebase + operations@firebase.com + yes + + 2015-07-22 + + 3.0.0 + 3.0.0 + + + beta + beta + + BSD 3-Clause License + +Initial release with basic support for JWT encoding, decoding and signature verification. + + + + + + + + + + + + + 5.1 + + + 1.7.0 + + + json + + + hash + + + + + + + + 0.1.0 + 0.1.0 + + + beta + beta + + 2015-04-01 + BSD 3-Clause License + +Initial release with basic support for JWT encoding, decoding and signature verification. + + + + diff --git a/vendor/firebase/php-jwt/src/JWT.php b/vendor/firebase/php-jwt/src/JWT.php index af20661..6d30e94 100644 --- a/vendor/firebase/php-jwt/src/JWT.php +++ b/vendor/firebase/php-jwt/src/JWT.php @@ -1,7 +1,6 @@ array('openssl', 'SHA256'), 'HS256' => array('hash_hmac', 'SHA256'), - 'HS384' => array('hash_hmac', 'SHA384'), 'HS512' => array('hash_hmac', 'SHA512'), + 'HS384' => array('hash_hmac', 'SHA384'), 'RS256' => array('openssl', 'SHA256'), - 'RS384' => array('openssl', 'SHA384'), - 'RS512' => array('openssl', 'SHA512'), ); /** * Decodes a JWT string into a PHP object. * - * @param string $jwt The JWT - * @param string|array|resource $key The key, or map of keys. - * If the algorithm used is asymmetric, this is the public key - * @param array $allowed_algs List of supported verification algorithms - * Supported algorithms are 'ES256', 'HS256', 'HS384', 'HS512', 'RS256', 'RS384', and 'RS512' + * @param string $jwt The JWT + * @param string|array $key The key, or map of keys. + * If the algorithm used is asymmetric, this is the public key + * @param array $allowed_algs List of supported verification algorithms + * Supported algorithms are 'HS256', 'HS384', 'HS512' and 'RS256' * * @return object The JWT's payload as a PHP object * @@ -71,13 +64,16 @@ class JWT * @uses jsonDecode * @uses urlsafeB64Decode */ - public static function decode($jwt, $key, array $allowed_algs = array()) + public static function decode($jwt, $key, $allowed_algs = array()) { $timestamp = is_null(static::$timestamp) ? time() : static::$timestamp; if (empty($key)) { throw new InvalidArgumentException('Key may not be empty'); } + if (!is_array($allowed_algs)) { + throw new InvalidArgumentException('Algorithm not allowed'); + } $tks = explode('.', $jwt); if (count($tks) != 3) { throw new UnexpectedValueException('Wrong number of segments'); @@ -89,9 +85,8 @@ public static function decode($jwt, $key, array $allowed_algs = array()) if (null === $payload = static::jsonDecode(static::urlsafeB64Decode($bodyb64))) { throw new UnexpectedValueException('Invalid claims encoding'); } - if (false === ($sig = static::urlsafeB64Decode($cryptob64))) { - throw new UnexpectedValueException('Invalid signature encoding'); - } + $sig = static::urlsafeB64Decode($cryptob64); + if (empty($header->alg)) { throw new UnexpectedValueException('Empty algorithm'); } @@ -101,16 +96,8 @@ public static function decode($jwt, $key, array $allowed_algs = array()) if (!in_array($header->alg, $allowed_algs)) { throw new UnexpectedValueException('Algorithm not allowed'); } - if ($header->alg === 'ES256') { - // OpenSSL expects an ASN.1 DER sequence for ES256 signatures - $sig = self::signatureToDER($sig); - } - if (is_array($key) || $key instanceof \ArrayAccess) { if (isset($header->kid)) { - if (!isset($key[$header->kid])) { - throw new UnexpectedValueException('"kid" invalid, unable to lookup correct key'); - } $key = $key[$header->kid]; } else { throw new UnexpectedValueException('"kid" empty, unable to lookup correct key'); @@ -122,7 +109,7 @@ public static function decode($jwt, $key, array $allowed_algs = array()) throw new SignatureInvalidException('Signature verification failed'); } - // Check the nbf if it is defined. This is the time that the + // Check if the nbf if it is defined. This is the time that the // token can actually be used. If it's not yet that time, abort. if (isset($payload->nbf) && $payload->nbf > ($timestamp + static::$leeway)) { throw new BeforeValidException( @@ -154,7 +141,7 @@ public static function decode($jwt, $key, array $allowed_algs = array()) * @param string $key The secret key. * If the algorithm used is asymmetric, this is the private key * @param string $alg The signing algorithm. - * Supported algorithms are 'ES256', 'HS256', 'HS384', 'HS512', 'RS256', 'RS384', and 'RS512' + * Supported algorithms are 'HS256', 'HS384', 'HS512' and 'RS256' * @param mixed $keyId * @param array $head An array with header elements to attach * @@ -169,7 +156,7 @@ public static function encode($payload, $key, $alg = 'HS256', $keyId = null, $he if ($keyId !== null) { $header['kid'] = $keyId; } - if (isset($head) && is_array($head)) { + if ( isset($head) && is_array($head) ) { $header = array_merge($head, $header); } $segments = array(); @@ -189,7 +176,7 @@ public static function encode($payload, $key, $alg = 'HS256', $keyId = null, $he * @param string $msg The message to sign * @param string|resource $key The secret key * @param string $alg The signing algorithm. - * Supported algorithms are 'ES256', 'HS256', 'HS384', 'HS512', 'RS256', 'RS384', and 'RS512' + * Supported algorithms are 'HS256', 'HS384', 'HS512' and 'RS256' * * @return string An encrypted message * @@ -201,7 +188,7 @@ public static function sign($msg, $key, $alg = 'HS256') throw new DomainException('Algorithm not supported'); } list($function, $algorithm) = static::$supported_algs[$alg]; - switch ($function) { + switch($function) { case 'hash_hmac': return hash_hmac($algorithm, $msg, $key, true); case 'openssl': @@ -210,9 +197,6 @@ public static function sign($msg, $key, $alg = 'HS256') if (!$success) { throw new DomainException("OpenSSL unable to sign data"); } else { - if ($alg === 'ES256') { - $signature = self::signatureFromDER($signature, 256); - } return $signature; } } @@ -238,18 +222,14 @@ private static function verify($msg, $signature, $key, $alg) } list($function, $algorithm) = static::$supported_algs[$alg]; - switch ($function) { + switch($function) { case 'openssl': $success = openssl_verify($msg, $signature, $key, $algorithm); - if ($success === 1) { - return true; - } elseif ($success === 0) { - return false; + if (!$success) { + throw new DomainException("OpenSSL unable to verify data: " . openssl_error_string()); + } else { + return $signature; } - // returns 1 on success, 0 on failure, -1 on error. - throw new DomainException( - 'OpenSSL error: ' . openssl_error_string() - ); case 'hash_hmac': default: $hash = hash_hmac($algorithm, $msg, $key, true); @@ -295,7 +275,7 @@ public static function jsonDecode($input) $obj = json_decode($json_without_bigints); } - if ($errno = json_last_error()) { + if (function_exists('json_last_error') && $errno = json_last_error()) { static::handleJsonError($errno); } elseif ($obj === null && $input !== 'null') { throw new DomainException('Null result with non-null input'); @@ -315,7 +295,7 @@ public static function jsonDecode($input) public static function jsonEncode($input) { $json = json_encode($input); - if ($errno = json_last_error()) { + if (function_exists('json_last_error') && $errno = json_last_error()) { static::handleJsonError($errno); } elseif ($json === 'null' && $input !== null) { throw new DomainException('Null result with non-null input'); @@ -363,10 +343,8 @@ private static function handleJsonError($errno) { $messages = array( JSON_ERROR_DEPTH => 'Maximum stack depth exceeded', - JSON_ERROR_STATE_MISMATCH => 'Invalid or malformed JSON', JSON_ERROR_CTRL_CHAR => 'Unexpected control character found', - JSON_ERROR_SYNTAX => 'Syntax error, malformed JSON', - JSON_ERROR_UTF8 => 'Malformed UTF-8 characters' //PHP >= 5.3.3 + JSON_ERROR_SYNTAX => 'Syntax error, malformed JSON' ); throw new DomainException( isset($messages[$errno]) @@ -378,7 +356,7 @@ private static function handleJsonError($errno) /** * Get the number of bytes in cryptographic strings. * - * @param string $str + * @param string * * @return int */ @@ -389,126 +367,4 @@ private static function safeStrlen($str) } return strlen($str); } - - /** - * Convert an ECDSA signature to an ASN.1 DER sequence - * - * @param string $sig The ECDSA signature to convert - * @return string The encoded DER object - */ - private static function signatureToDER($sig) - { - // Separate the signature into r-value and s-value - list($r, $s) = str_split($sig, (int) (strlen($sig) / 2)); - - // Trim leading zeros - $r = ltrim($r, "\x00"); - $s = ltrim($s, "\x00"); - - // Convert r-value and s-value from unsigned big-endian integers to - // signed two's complement - if (ord($r[0]) > 0x7f) { - $r = "\x00" . $r; - } - if (ord($s[0]) > 0x7f) { - $s = "\x00" . $s; - } - - return self::encodeDER( - self::ASN1_SEQUENCE, - self::encodeDER(self::ASN1_INTEGER, $r) . - self::encodeDER(self::ASN1_INTEGER, $s) - ); - } - - /** - * Encodes a value into a DER object. - * - * @param int $type DER tag - * @param string $value the value to encode - * @return string the encoded object - */ - private static function encodeDER($type, $value) - { - $tag_header = 0; - if ($type === self::ASN1_SEQUENCE) { - $tag_header |= 0x20; - } - - // Type - $der = chr($tag_header | $type); - - // Length - $der .= chr(strlen($value)); - - return $der . $value; - } - - /** - * Encodes signature from a DER object. - * - * @param string $der binary signature in DER format - * @param int $keySize the nubmer of bits in the key - * @return string the signature - */ - private static function signatureFromDER($der, $keySize) - { - // OpenSSL returns the ECDSA signatures as a binary ASN.1 DER SEQUENCE - list($offset, $_) = self::readDER($der); - list($offset, $r) = self::readDER($der, $offset); - list($offset, $s) = self::readDER($der, $offset); - - // Convert r-value and s-value from signed two's compliment to unsigned - // big-endian integers - $r = ltrim($r, "\x00"); - $s = ltrim($s, "\x00"); - - // Pad out r and s so that they are $keySize bits long - $r = str_pad($r, $keySize / 8, "\x00", STR_PAD_LEFT); - $s = str_pad($s, $keySize / 8, "\x00", STR_PAD_LEFT); - - return $r . $s; - } - - /** - * Reads binary DER-encoded data and decodes into a single object - * - * @param string $der the binary data in DER format - * @param int $offset the offset of the data stream containing the object - * to decode - * @return array [$offset, $data] the new offset and the decoded object - */ - private static function readDER($der, $offset = 0) - { - $pos = $offset; - $size = strlen($der); - $constructed = (ord($der[$pos]) >> 5) & 0x01; - $type = ord($der[$pos++]) & 0x1f; - - // Length - $len = ord($der[$pos++]); - if ($len & 0x80) { - $n = $len & 0x1f; - $len = 0; - while ($n-- && $pos < $size) { - $len = ($len << 8) | ord($der[$pos++]); - } - } - - // Value - if ($type == self::ASN1_BIT_STRING) { - $pos++; // Skip the first contents octet (padding indicator) - $data = substr($der, $pos, $len - 1); - if (!$ignore_bit_strings) { - $pos += $len - 1; - } - } elseif (!$constructed) { - $data = substr($der, $pos, $len); - $pos += $len; - } else { - $data = null; - } - - return array($pos, $data); - } }