diff --git a/Event/RefreshEvent.php b/Event/RefreshEvent.php new file mode 100644 index 00000000..6cf61f0f --- /dev/null +++ b/Event/RefreshEvent.php @@ -0,0 +1,39 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Gesdinet\JWTRefreshTokenBundle\Event; + +use Gesdinet\JWTRefreshTokenBundle\Model\RefreshTokenInterface; +use Symfony\Component\EventDispatcher\Event; +use Symfony\Component\Security\Core\Authentication\Token\PreAuthenticatedToken; + +class RefreshEvent extends Event +{ + private $refreshToken; + + private $preAuthenticatedToken; + + public function __construct(RefreshTokenInterface $refreshToken, PreAuthenticatedToken $preAuthenticatedToken) + { + $this->refreshToken = $refreshToken; + $this->preAuthenticatedToken = $preAuthenticatedToken; + } + + public function getRefreshToken() + { + return $this->refreshToken; + } + + public function getPreAuthenticatedToken() + { + return $this->preAuthenticatedToken; + } +} diff --git a/README.md b/README.md index 324834b7..0ee5b88c 100644 --- a/README.md +++ b/README.md @@ -245,3 +245,44 @@ If you want to revoke a single token you can use this: ```bash php app/console gesdinet:jwt:revoke TOKEN ``` + +### Events + +If you want to do something when token is refreshed you can listen for `gesdinet.refresh_token` event. + +For example: + +```php +logger = $logger; + } + + public function log(RefreshEvent $event) + { + $refreshToken = $event->getRefreshToken()->getRefreshToken(); + $user = $event->getPreAuthenticatedToken()->getUser()->getUsername(); + + $this->logger->debug(sprintf('User "%s" has refreshed it\'s JWT token with refresh token "%s".', $user, $refreshToken)); + } + + public static function getSubscribedEvents() + { + return array( + 'gesdinet.refresh_token' => 'log', + ); + } +} +``` diff --git a/Resources/config/services.yml b/Resources/config/services.yml index 4665fe8b..73cb0079 100644 --- a/Resources/config/services.yml +++ b/Resources/config/services.yml @@ -16,7 +16,7 @@ services: gesdinet.jwtrefreshtoken: class: Gesdinet\JWTRefreshTokenBundle\Service\RefreshToken public: true - arguments: [ "@gesdinet.jwtrefreshtoken.authenticator", "@gesdinet.jwtrefreshtoken.user_provider", "@lexik_jwt_authentication.handler.authentication_success", "@lexik_jwt_authentication.handler.authentication_failure", "@gesdinet.jwtrefreshtoken.refresh_token_manager", "%gesdinet_jwt_refresh_token.ttl%", "%gesdinet_jwt_refresh_token.security.firewall%", "%gesdinet_jwt_refresh_token.ttl_update%" ] + arguments: [ "@gesdinet.jwtrefreshtoken.authenticator", "@gesdinet.jwtrefreshtoken.user_provider", "@lexik_jwt_authentication.handler.authentication_success", "@lexik_jwt_authentication.handler.authentication_failure", "@gesdinet.jwtrefreshtoken.refresh_token_manager", "%gesdinet_jwt_refresh_token.ttl%", "%gesdinet_jwt_refresh_token.security.firewall%", "%gesdinet_jwt_refresh_token.ttl_update%", "@event_dispatcher" ] gesdinet.jwtrefreshtoken.user_provider: class: Gesdinet\JWTRefreshTokenBundle\Security\Provider\RefreshTokenProvider diff --git a/Service/RefreshToken.php b/Service/RefreshToken.php index 5110f254..0a0eea1e 100644 --- a/Service/RefreshToken.php +++ b/Service/RefreshToken.php @@ -11,6 +11,8 @@ namespace Gesdinet\JWTRefreshTokenBundle\Service; +use Gesdinet\JWTRefreshTokenBundle\Event\RefreshEvent; +use Symfony\Component\EventDispatcher\EventDispatcherInterface; use Symfony\Component\HttpFoundation\Request; use Lexik\Bundle\JWTAuthenticationBundle\Security\Http\Authentication\AuthenticationSuccessHandler; use Lexik\Bundle\JWTAuthenticationBundle\Security\Http\Authentication\AuthenticationFailureHandler; @@ -38,7 +40,9 @@ class RefreshToken private $ttlUpdate; - public function __construct(RefreshTokenAuthenticator $authenticator, RefreshTokenProvider $provider, AuthenticationSuccessHandler $successHandler, AuthenticationFailureHandler $failureHandler, RefreshTokenManagerInterface $refreshTokenManager, $ttl, $providerKey, $ttlUpdate) + private $eventDispatcher; + + public function __construct(RefreshTokenAuthenticator $authenticator, RefreshTokenProvider $provider, AuthenticationSuccessHandler $successHandler, AuthenticationFailureHandler $failureHandler, RefreshTokenManagerInterface $refreshTokenManager, $ttl, $providerKey, $ttlUpdate, EventDispatcherInterface $eventDispatcher) { $this->authenticator = $authenticator; $this->provider = $provider; @@ -48,6 +52,7 @@ public function __construct(RefreshTokenAuthenticator $authenticator, RefreshTok $this->ttl = $ttl; $this->providerKey = $providerKey; $this->ttlUpdate = $ttlUpdate; + $this->eventDispatcher = $eventDispatcher; } /** @@ -86,6 +91,8 @@ public function refresh(Request $request) $this->refreshTokenManager->save($refreshToken); } + $this->eventDispatcher->dispatch('gesdinet.refresh_token', new RefreshEvent($refreshToken, $preAuthenticatedToken)); + return $this->successHandler->onAuthenticationSuccess($request, $preAuthenticatedToken); } } diff --git a/spec/Service/RefreshTokenSpec.php b/spec/Service/RefreshTokenSpec.php index 478c67d1..e6c941d6 100644 --- a/spec/Service/RefreshTokenSpec.php +++ b/spec/Service/RefreshTokenSpec.php @@ -10,6 +10,7 @@ use Lexik\Bundle\JWTAuthenticationBundle\Security\Http\Authentication\AuthenticationSuccessHandler; use PhpSpec\ObjectBehavior; use Prophecy\Argument; +use Symfony\Component\EventDispatcher\EventDispatcherInterface; use Symfony\Component\HttpFoundation\Request; use Symfony\Component\Security\Core\Authentication\Token\PreAuthenticatedToken; use Symfony\Component\Security\Core\Authentication\Token\TokenInterface; @@ -17,13 +18,13 @@ class RefreshTokenSpec extends ObjectBehavior { - public function let(RefreshTokenAuthenticator $authenticator, RefreshTokenProvider $provider, AuthenticationSuccessHandler $successHandler, AuthenticationFailureHandler $failureHandler, RefreshTokenManagerInterface $refreshTokenManager, TokenInterface $token, UserProviderInterface $userProvider, $ttl, $providerKey, $ttlUpdate) + public function let(RefreshTokenAuthenticator $authenticator, RefreshTokenProvider $provider, AuthenticationSuccessHandler $successHandler, AuthenticationFailureHandler $failureHandler, RefreshTokenManagerInterface $refreshTokenManager, TokenInterface $token, UserProviderInterface $userProvider, $ttl, $providerKey, $ttlUpdate, EventDispatcherInterface $eventDispatcher) { $ttl = 2592000; $ttlUpdate = false; $providerKey = 'testkey'; - $this->beConstructedWith($authenticator, $provider, $successHandler, $failureHandler, $refreshTokenManager, $ttl, $providerKey, $ttlUpdate); + $this->beConstructedWith($authenticator, $provider, $successHandler, $failureHandler, $refreshTokenManager, $ttl, $providerKey, $ttlUpdate, $eventDispatcher); } public function it_is_initializable() @@ -42,9 +43,9 @@ public function it_refresh_token(Request $request, $refreshTokenManager, $authen $this->refresh($request); } - public function it_refresh_token_with_ttl_update(RefreshTokenProvider $provider, AuthenticationSuccessHandler $successHandler, AuthenticationFailureHandler $failureHandler, Request $request, $refreshTokenManager, $authenticator, $token, PreAuthenticatedToken $preAuthenticatedToken, RefreshTokenInterface $refreshToken) + public function it_refresh_token_with_ttl_update(RefreshTokenProvider $provider, AuthenticationSuccessHandler $successHandler, AuthenticationFailureHandler $failureHandler, Request $request, $refreshTokenManager, $authenticator, $token, PreAuthenticatedToken $preAuthenticatedToken, RefreshTokenInterface $refreshToken, EventDispatcherInterface $eventDispatcher) { - $this->beConstructedWith($authenticator, $provider, $successHandler, $failureHandler, $refreshTokenManager, 2592000, 'testkey', true); + $this->beConstructedWith($authenticator, $provider, $successHandler, $failureHandler, $refreshTokenManager, 2592000, 'testkey', true, $eventDispatcher); $authenticator->createToken(Argument::any(), Argument::any())->willReturn($token); $authenticator->authenticateToken(Argument::any(), Argument::any(), Argument::any())->willReturn($preAuthenticatedToken);