private async Task ValidateRequestAsync(IRefreshTokenRequest request) { _request = request; if (_request.ClientId == Guid.Empty || _request.ClientSecret == null) { throw new InvalidClientException("Invalid client credentials."); } if (_request.RefreshToken == null) { throw new InvalidGrantException("Refresh token could not be found"); } _refreshToken = await _refreshTokenRepository.FindAsync(request.RefreshToken); if (_refreshToken == null || _refreshToken.IsExpired || _refreshToken.Application.ClientId != request.ClientId) { throw new InvalidGrantException("Refresh token could not be found."); } // If someone tries to use the same refresh token twice, disable the access token. if (_refreshToken.Used) { if (_refreshToken.AccessToken != null && !_refreshToken.AccessToken.IsExpired) { _refreshToken.AccessToken.Disabled = true; await _accessTokenRepository.SaveAsync(); } throw new InvalidGrantException("Refresh token could not be found."); } await _authenticateClientService.AuthenticateAsync(_request.ClientId, _request.ClientSecret); // Make sure all requested scopes were requested in the original refresh token. if (request.Scope != null) { var scopes = request.Scope.Split(" "); foreach (var scope in scopes) { // Only allow the refreshed token to use the scopes issued with the // original token as per https://tools.ietf.org/html/rfc6749#section-6 var originalScopes = _refreshToken.AuthorizationCode.Scope.Split(" "); if (originalScopes.All(scopeName => scopeName != scope)) { throw new InvalidScopeException("The provided scope is invalid."); } } } _scope = request.Scope ?? _refreshToken.Scope; }
public async Task <JwtToken> GenerateTokenAsync(IRefreshTokenRequest request) { await ValidateRequestAsync(request); var refreshToken = GenerateRefreshToken(); var jwtToken = await CreateJwtTokenAsync(); jwtToken.RefreshToken = refreshToken.RefreshTokenId; refreshToken.AccessTokenId = jwtToken.TokenId; refreshToken.Code = _refreshToken.Code; _refreshToken.Used = true; var accessToken = jwtToken.ToAccessToken(); _accessTokenRepository.Add(accessToken); await SaveAsync(); return(jwtToken); }