Skip to content

Commit 38b4cda

Browse files
committed
add create token by user object
1 parent e513f84 commit 38b4cda

File tree

5 files changed

+177
-1
lines changed

5 files changed

+177
-1
lines changed

src/AuthorizationServerFactory.php

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
namespace OAuthServer;
44

55
use OAuthServer\Grant\OtpGrant;
6+
use OAuthServer\Grant\UserGrant;
67
use Hyperf\Contract\ConfigInterface;
78
use Psr\Container\ContainerInterface;
89
use OAuthServer\OneTimePasswordInterface;
@@ -62,6 +63,11 @@ public function __invoke()
6263
$tokenExpiresIn
6364
);
6465

66+
$server->enableGrantType(
67+
$this->makeUserGrant(),
68+
$tokenExpiresIn
69+
);
70+
6571
return $server;
6672
});
6773
}
@@ -120,4 +126,14 @@ public function makeOtpGrant()
120126
$grant->setRefreshTokenTTL(new \DateInterval('P1M'));
121127
});
122128
}
129+
130+
public function makeUserGrant()
131+
{
132+
$userRepository = make(UserRepository::class);
133+
$refreshTokenRepository = make(RefreshTokenRepository::class);
134+
135+
return tap(new UserGrant($userRepository, $refreshTokenRepository), function ($grant) {
136+
$grant->setRefreshTokenTTL(new \DateInterval('P1M'));
137+
});
138+
}
123139
}

src/ConfigProvider.php

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,9 @@ public function __invoke(): array
2626
ScopeRepository::class => ScopeRepository::class,
2727
UserRepository::class => UserRepository::class,
2828
TokenRepository::class => TokenRepository::class,
29+
30+
// Token By User
31+
Token::class => Token::class
2932
],
3033
'listeners' => [
3134
//

src/Grant/UserGrant.php

Lines changed: 103 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,103 @@
1+
<?php
2+
3+
namespace OAuthServer\Grant;
4+
5+
use DateInterval;
6+
use OAuthServer\Entities\UserEntity;
7+
use League\OAuth2\Server\RequestEvent;
8+
use OAuthServer\OneTimePasswordInterface;
9+
use Psr\Http\Message\ServerRequestInterface;
10+
use League\OAuth2\Server\Grant\AbstractGrant;
11+
use League\OAuth2\Server\Entities\UserEntityInterface;
12+
use League\OAuth2\Server\Entities\ClientEntityInterface;
13+
use League\OAuth2\Server\Exception\OAuthServerException;
14+
use League\OAuth2\Server\ResponseTypes\ResponseTypeInterface;
15+
use League\OAuth2\Server\Repositories\UserRepositoryInterface;
16+
use League\OAuth2\Server\Repositories\RefreshTokenRepositoryInterface;
17+
18+
/**
19+
* User grant class.
20+
*/
21+
class UserGrant extends AbstractGrant
22+
{
23+
/**
24+
* @param UserRepositoryInterface $userRepository
25+
* @param RefreshTokenRepositoryInterface $refreshTokenRepository
26+
* @param OneTimePasswordInterface $otp
27+
*/
28+
public function __construct(
29+
UserRepositoryInterface $userRepository,
30+
RefreshTokenRepositoryInterface $refreshTokenRepository
31+
) {
32+
$this->setUserRepository($userRepository);
33+
$this->setRefreshTokenRepository($refreshTokenRepository);
34+
35+
$this->refreshTokenTTL = new DateInterval('P1M');
36+
}
37+
38+
/**
39+
* {@inheritdoc}
40+
*/
41+
public function respondToAccessTokenRequest(
42+
ServerRequestInterface $request,
43+
ResponseTypeInterface $responseType,
44+
DateInterval $accessTokenTTL
45+
) {
46+
// Validate request
47+
$client = $this->validateClient($request);
48+
$scopes = $this->validateScopes($this->getRequestParameter('scope', $request, $this->defaultScope));
49+
$user = $this->validateUser($request, $client);
50+
51+
// Finalize the requested scopes
52+
$finalizedScopes = $this->scopeRepository->finalizeScopes($scopes, $this->getIdentifier(), $client, $user->getIdentifier());
53+
54+
// Issue and persist new access token
55+
$accessToken = $this->issueAccessToken($accessTokenTTL, $client, $user->getIdentifier(), $finalizedScopes);
56+
$this->getEmitter()->emit(new RequestEvent(RequestEvent::ACCESS_TOKEN_ISSUED, $request));
57+
$responseType->setAccessToken($accessToken);
58+
59+
// Issue and persist new refresh token if given
60+
$refreshToken = $this->issueRefreshToken($accessToken);
61+
62+
if ($refreshToken !== null) {
63+
$this->getEmitter()->emit(new RequestEvent(RequestEvent::REFRESH_TOKEN_ISSUED, $request));
64+
$responseType->setRefreshToken($refreshToken);
65+
}
66+
67+
return $responseType;
68+
}
69+
70+
/**
71+
* Undocumented function
72+
*
73+
* @param ServerRequestInterface $request
74+
* @param ClientEntityInterface $client
75+
* @return void
76+
*/
77+
protected function validateUser(ServerRequestInterface $request, ClientEntityInterface $client)
78+
{
79+
$user = $request->getAttribute('user');
80+
81+
if(\is_null($user)) {
82+
throw OAuthServerException::invalidRequest('user not register');
83+
}
84+
85+
$user = new UserEntity($user->id);
86+
87+
if ($user instanceof UserEntityInterface === false) {
88+
$this->getEmitter()->emit(new RequestEvent(RequestEvent::USER_AUTHENTICATION_FAILED, $request));
89+
90+
throw OAuthServerException::invalidGrant();
91+
}
92+
93+
return $user;
94+
}
95+
96+
/**
97+
* {@inheritdoc}
98+
*/
99+
public function getIdentifier()
100+
{
101+
return 'user';
102+
}
103+
}

src/Repositories/UserRepository.php

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -90,7 +90,9 @@ public function getUserByProviderUserId($id, $client)
9090

9191
$query = Db::connection($provider);
9292
$user = $query->table('users')->find($id);
93+
9394
unset($user->password);
94-
return $user;
95+
96+
return new UserEntity($user->id);
9597
}
9698
}

src/Token.php

Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
<?php
2+
3+
namespace OAuthServer;
4+
5+
use Psr\Http\Message\ServerRequestInterface;
6+
use League\OAuth2\Server\AuthorizationServer;
7+
use Hyperf\HttpServer\Contract\ResponseInterface;
8+
use OAuthServer\Exception\AuthenticationException;
9+
use League\OAuth2\Server\Exception\OAuthServerException;
10+
11+
12+
class Token
13+
{
14+
protected $request;
15+
protected $response;
16+
protected $server;
17+
18+
public function __construct(
19+
ServerRequestInterface $request,
20+
ResponseInterface $response,
21+
AuthorizationServer $server
22+
) {
23+
$this->request = $request;
24+
$this->response = $response;
25+
$this->server = $server;
26+
}
27+
28+
public function byUser($user, $client, array $scopes = [])
29+
{
30+
$request = $this->request->withParsedBody([
31+
'grant_type' => 'user',
32+
'client_id' => $client->id,
33+
'client_secret' => $client->secret,
34+
'scope' => implode(' ', $scopes)
35+
]);
36+
37+
$request = $request->withAttribute('user', $user);
38+
39+
return $this->issueToken($request, $this->response);
40+
}
41+
42+
public function issueToken(ServerRequestInterface $request, ResponseInterface $response)
43+
{
44+
try {
45+
return $this->server->respondToAccessTokenRequest($request, $response);
46+
} catch (OAuthServerException $e) {
47+
return $e->generateHttpResponse($response);
48+
} catch (\Exception $e) {
49+
throw new AuthenticationException("Unauthorize: {$e->getMessage()}");
50+
}
51+
}
52+
}

0 commit comments

Comments
 (0)