devzyj / php-oauth2-server
PHP OAuth2 Server
1.0.1
2021-07-09 06:05 UTC
Requires
- php: ^5.5|^7.0
- defuse/php-encryption: ^2.1.0
- lcobucci/jwt: ^3.2.5
- paragonie/random_compat: >=2
This package is auto-updated.
Last update: 2024-11-09 13:07:58 UTC
README
PHP OAuth2 Server
Installation
composer require --prefer-dist "devzyj/php-oauth2-server" "~1.0.0"
or add
"devzyj/php-oauth2-server" : "~1.0.0"
Usage
/authorize?response_type=xxx
use devzyj\oauth2\server\AuthorizationServer; use devzyj\oauth2\server\authorizes\CodeAuthorize; use devzyj\oauth2\server\authorizes\ImplicitAuthorize; use devzyj\oauth2\server\exceptions\OAuthServerException; // 实例化授权服务器。 $authorizationServer = new AuthorizationServer([ 'accessTokenRepository' => new AccessTokenRepository(), // AccessTokenRepositoryInterface 实例。 'authorizationCodeRepository' => new AuthorizationCodeRepository(), // AuthorizationCodeRepositoryInterface 实例。 'clientRepository' => new ClientRepository(), // ClientRepositoryInterface 实例。 'scopeRepository' => new ScopeRepository(), // ScopeRepositoryInterface 实例。 'defaultScopes' => ['basic', 'basic2'], // 默认权限。 'accessTokenDuration' => 3600, // 访问令牌持续 1 小时。 'accessTokenCryptKey' => [ 'privateKey' => '/path/to/privateKey', // 访问令牌的私钥路径。 'passphrase' => null, // 访问令牌的私钥密码。没有密码可以为 `null`。 //'signKey' => 'sign key', // 字符串签名密钥。 ], 'authorizationCodeDuration' => 600, // 授权码持续 10 分钟。 'authorizationCodeCryptKey' => [ 'ascii' => 'def0000086937b.....', // 使用 `vendor/bin/generate-defuse-key` 生成的字符串。 //'path' => '/path/to/asciiFile', // 保存了 `vendor/bin/generate-defuse-key` 生成的字符串的文件路径。 //'password' => 'string key', // 字符串密钥。 ], ]); // 添加授权类型。 $authorizationServer->addAuthorizeType(new CodeAuthorize()); $authorizationServer->addAuthorizeType(new ImplicitAuthorize()); try { // 获取并验证授权请求。 // $request 不强制要求实现 ServerRequestInterface 接口,只需要实例中包函接口中的方法。 $authorizeRequest = $authorizationServer->getAuthorizeRequest($request); // 设置授权的用户。 // 用户未登录时,需要重定向到登录页面。 $authorizeRequest->setUserEntity(new UserEntity()); // UserEntityInterface 实例。 // 设置是否同意授权,同意授权设置为 `true`,拒绝授权设置为 `false`。 // 如果用户未确认授权,需要引导用户到授权页面。 $authorizeRequest->setIsApproved(true); // 运行并返回授权成功的回调地址。 $redirectUrl = $authorizationServer->runAuthorizeTypes($authorizeRequest); } catch (OAuthServerException $e) { $e->getHttpStatusCode(); $e->getMessage(); $e->getCode(); // 处理异常。 throw $e; } // 重定向到回调地址。 header("Location: {$redirectUrl}"); exit();
/token?grant_type=xxx
use devzyj\oauth2\server\AuthorizationServer; use devzyj\oauth2\server\grants\AuthorizationCodeGrant; use devzyj\oauth2\server\grants\PasswordGrant; use devzyj\oauth2\server\grants\ClientCredentialsGrant; use devzyj\oauth2\server\grants\RefreshTokenGrant; use devzyj\oauth2\server\exceptions\OAuthServerException; // 实例化授权服务器。 $authorizationServer = new AuthorizationServer([ 'accessTokenRepository' => new AccessTokenRepository(), // AccessTokenRepositoryInterface 实例。 'authorizationCodeRepository' => new AuthorizationCodeRepository(), // AuthorizationCodeRepositoryInterface 实例。 'clientRepository' => new ClientRepository(), // ClientRepositoryInterface 实例。 'refreshTokenRepository' => new RefreshTokenRepository(), // RefreshTokenRepositoryInterface 实例。 'scopeRepository' => new ScopeRepository(), // ScopeRepositoryInterface 实例。 'userRepository' => new UserRepository(), // UserRepositoryInterface 实例。 'accessTokenDuration' => 3600, // 访问令牌持续 1 小时。 'accessTokenCryptKey' => [ 'privateKey' => '/path/to/privateKey', // 访问令牌的私钥路径。 'passphrase' => null, // 访问令牌的私钥密码。没有密码可以为 `null`。 //'signKey' => 'sign key', // 字符串签名密钥。 ], 'authorizationCodeCryptKey' => [ 'ascii' => 'def0000086937b.....', // 使用 `vendor/bin/generate-defuse-key` 生成的字符串。 //'path' => '/path/to/asciiFile', // 保存了 `vendor/bin/generate-defuse-key` 生成的字符串的文件路径。 //'password' => 'string key', // 字符串密钥。 ], 'refreshTokenDuration' => 2592000, // 访问令牌持续 30 天。 'refreshTokenCryptKey' => [ 'ascii' => 'def0000086937b.....', // 使用 `vendor/bin/generate-defuse-key` 生成的字符串。 //'path' => '/path/to/asciiFile', // 保存了 `vendor/bin/generate-defuse-key` 生成的字符串的文件路径。 //'password' => 'string key', // 字符串密钥。 ], ]); // 添加授予类型。 $authorizationServer->addGrantType(new AuthorizationCodeGrant()); $authorizationServer->addGrantType(new PasswordGrant()); $authorizationServer->addGrantType(new ClientCredentialsGrant()); $authorizationServer->addGrantType(new RefreshTokenGrant()); try { // 运行并返回授予的认证信息。 // $request 不强制要求实现 ServerRequestInterface 接口,只需要实例中包函接口中的方法。 $credentials = $authorizationServer->runGrantTypes($request); } catch (OAuthServerException $e) { $e->getHttpStatusCode(); $e->getMessage(); $e->getCode(); // 处理异常。 throw $e; } // 显示认证信息。 echo json_encode($credentials);
Interfaces
需要实现的接口。
- devzyj\oauth2\server\interfaces\AccessTokenEntityInterface
- devzyj\oauth2\server\interfaces\AccessTokenRepositoryInterface
- devzyj\oauth2\server\interfaces\AuthorizationCodeEntityInterface
- devzyj\oauth2\server\interfaces\AuthorizationCodeRepositoryInterface
- devzyj\oauth2\server\interfaces\ClientEntityInterface
- devzyj\oauth2\server\interfaces\ClientRepositoryInterface
- devzyj\oauth2\server\interfaces\RefreshTokenEntityInterface
- devzyj\oauth2\server\interfaces\RefreshTokenRepositoryInterface
- devzyj\oauth2\server\interfaces\ScopeEntityInterface
- devzyj\oauth2\server\interfaces\ScopeRepositoryInterface
- devzyj\oauth2\server\interfaces\UserEntityInterface
- devzyj\oauth2\server\interfaces\UserRepositoryInterface
- devzyj\oauth2\server\interfaces\ServerRequestInterface 不强制要求实现该接口,只需要实例中包函接口中的方法。
Traits
实现了接口中的一些方法。
- devzyj\oauth2\server\traits\AccessTokenEntityTrait
- devzyj\oauth2\server\traits\AccessTokenRepositoryTrait
- devzyj\oauth2\server\traits\AuthorizationCodeEntityTrait
- devzyj\oauth2\server\traits\AuthorizationCodeRepositoryTrait
- devzyj\oauth2\server\traits\RefreshTokenEntityTrait
- devzyj\oauth2\server\traits\RefreshTokenRepositoryTrait
Generating public and private keys
openssl genrsa -out private.key 2048 openssl rsa -in private.key -pubout -out public.key
openssl genrsa -passout pass:_passphrase_ -out private.key 2048 openssl rsa -in private.key -passin pass:_passphrase_ -pubout -out public.key
Usaging Code Challenge
// 配置授权服务器。 $authorizationServer = new AuthorizationServer(); $authorizationServer->addAuthorizeType(new CodeAuthorize([ 'enableCodeChallenge' => true, 'defaultCodeChallengeMethod' => 'S256', ])); $authorizationServer->addGrantType(new AuthorizationCodeGrant([ 'enableCodeChallenge' => true, ])); // 生成 Code Verifier $codeVerifier = rtrim(strtr(base64_encode(md5(microtime())), '+/', '-_'), '='); // PHP < 7 $codeVerifier = rtrim(strtr(base64_encode(random_bytes(32)), '+/', '-_'), '='); // PHP >= 7 // 生成 Code Challenge $codeChallenge = rtrim(strtr(base64_encode(hash('sha256', $codeVerifier, true)), '+/', '-_'), '=');