private function checkRefreshToken(Request $request, $clientId)
{
// refresh_token must exists and in valid format.
$refreshToken = $request->request->get('refresh_token');
$errors = $this->validator->validate($refreshToken, [new NotBlank(), new RefreshToken()]);
if (count($errors) > 0) {
throw new InvalidRequestException(['error_description' => 'The request includes an invalid parameter value.']);
}
// scope may not exists, else must be in valid format.
$scope = $request->request->get('scope');
$errors = $this->validator->validate($scope, [new Scope()]);
if (count($errors) > 0) {
throw new InvalidRequestException(['error_description' => 'The request includes an invalid parameter value.']);
}
// Check refresh_token with database record.
$refreshTokenManager = $this->modelManagerFactory->getModelManager('refresh_token');
$result = $refreshTokenManager->readModelOneBy(['refreshToken' => $refreshToken]);
if ($result === null || $result->getClientId() !== $clientId) {
throw new InvalidGrantException(['error_description' => 'The provided refresh token was issued to another client.']);
} elseif ($result->getExpires() < new \DateTime()) {
throw new InvalidGrantException(['error_description' => 'The provided refresh token is expired.']);
}
// Fetch username from stored refresh_token.
$username = $result->getUsername();
// Fetch scope from pre-grnerated refresh_token.
$scopeGranted = null;
if ($result !== null && $result->getClientId() == $clientId && $result->getScope()) {
$scopeGranted = $result->getScope();
}
// Compare if given scope is subset of original refresh_token's scope.
if ($scope !== null && $scopeGranted !== null) {
// Compare if given scope within all available granted scopes.
$scope = preg_split('/\\s+/', $scope);
if (array_intersect($scope, $scopeGranted) !== $scope) {
throw new InvalidScopeException(['error_description' => 'The requested scope exceeds the scope granted by the resource owner.']);
}
} elseif ($scopeGranted !== null) {
$scope = $scopeGranted;
}
if ($scope !== null) {
// Compare if given scope within all supported scopes.
$scopeSupported = [];
$scopeManager = $this->modelManagerFactory->getModelManager('scope');
$result = $scopeManager->readModelAll();
if ($result !== null) {
foreach ($result as $row) {
$scopeSupported[] = $row->getScope();
}
}
if (array_intersect($scope, $scopeSupported) !== $scope) {
throw new InvalidScopeException(['error_description' => 'The requested scope is unknown.']);
}
// Compare if given scope within all authorized scopes.
$scopeAuthorized = [];
$authorizeManager = $this->modelManagerFactory->getModelManager('authorize');
$result = $authorizeManager->readModelOneBy(['clientId' => $clientId, 'username' => $username]);
if ($result !== null) {
$scopeAuthorized = $result->getScope();
}
if (array_intersect($scope, $scopeAuthorized) !== $scope) {
throw new InvalidScopeException(['error_description' => 'The requested scope exceeds the scope granted by the resource owner.']);
}
}
return [$username, $scope];
}