Example #1
0
        public async Task <bool> Execute(RevokeTokenParameter revokeTokenParameter, AuthenticationHeaderValue authenticationHeaderValue, X509Certificate2 certificate, string issuerName)
        {
            if (revokeTokenParameter == null)
            {
                throw new ArgumentNullException(nameof(revokeTokenParameter));
            }

            if (string.IsNullOrWhiteSpace(revokeTokenParameter.Token))
            {
                throw new ArgumentNullException(nameof(revokeTokenParameter.Token));
            }

            // 1. Check the client credentials
            var errorMessage = string.Empty;
            var instruction  = CreateAuthenticateInstruction(revokeTokenParameter, authenticationHeaderValue, certificate);
            var authResult   = await _authenticateClient.AuthenticateAsync(instruction, issuerName);

            var client = authResult.Client;

            if (client == null)
            {
                throw new IdentityServerException(ErrorCodes.InvalidClient, authResult.ErrorMessage);
            }

            // 2. Retrieve the granted token & check if it exists
            GrantedToken grantedToken = await _tokenStore.GetAccessToken(revokeTokenParameter.Token);

            bool isAccessToken = true;

            if (grantedToken == null)
            {
                grantedToken = await _tokenStore.GetRefreshToken(revokeTokenParameter.Token);

                isAccessToken = false;
            }

            if (grantedToken == null)
            {
                throw new IdentityServerException(ErrorCodes.InvalidToken, ErrorDescriptions.TheTokenDoesntExist);
            }

            // 3. Verifies whether the token was issued to the client making the revocation request
            if (grantedToken.ClientId != client.ClientId)
            {
                throw new IdentityServerException(ErrorCodes.InvalidToken, string.Format(ErrorDescriptions.TheTokenHasNotBeenIssuedForTheGivenClientId, client.ClientId));
            }

            // 4. Invalid the granted token
            if (isAccessToken)
            {
                return(await _tokenStore.RemoveAccessToken(grantedToken.AccessToken));
            }

            return(await _tokenStore.RemoveRefreshToken(grantedToken.RefreshToken));
        }
Example #2
0
        public async Task <GrantedTokenValidationResult> CheckRefreshTokenAsync(string refreshToken)
        {
            if (string.IsNullOrWhiteSpace(refreshToken))
            {
                throw new ArgumentNullException(nameof(refreshToken));
            }

            var grantedToken = await _tokenStore.GetRefreshToken(refreshToken);

            return(CheckGrantedToken(grantedToken));
        }
        private async Task <GrantedToken> ValidateParameter(RefreshTokenGrantTypeParameter refreshTokenGrantTypeParameter)
        {
            var grantedToken = await _tokenStore.GetRefreshToken(refreshTokenGrantTypeParameter.RefreshToken);

            if (grantedToken == null)
            {
                throw new IdentityServerException(
                          ErrorCodes.InvalidGrant,
                          ErrorDescriptions.TheRefreshTokenIsNotValid);
            }

            return(grantedToken);
        }
Example #4
0
        public async Task <Option <UmaIntrospectionResponse> > Execute(
            IntrospectionParameter introspectionParameter,
            CancellationToken cancellationToken)
        {
            var introspectionParameterToken = introspectionParameter.Token;

            if (string.IsNullOrWhiteSpace(introspectionParameterToken))
            {
                return(new ErrorDetails
                {
                    Status = HttpStatusCode.BadRequest,
                    Title = ErrorCodes.InvalidToken,
                    Detail = Strings.TheTokenDoesntExist
                });
            }
            // Read this RFC for more information - https://docs.kantarainitiative.org/uma/wg/rec-oauth-uma-federated-authz-2.0.html#introspection-endpoint

            // 3. Retrieve the token type hint
            var tokenTypeHint = CoreConstants.StandardTokenTypeHintNames.AccessToken;

            if (CoreConstants.AllStandardTokenTypeHintNames.Contains(introspectionParameter.TokenTypeHint))
            {
                tokenTypeHint = introspectionParameter.TokenTypeHint;
            }

            // 4. Trying to fetch the information about the access_token  || refresh_token
            var grantedToken = tokenTypeHint switch
            {
                CoreConstants.StandardTokenTypeHintNames.AccessToken => await _tokenStore
                .GetAccessToken(introspectionParameterToken, cancellationToken)
                .ConfigureAwait(false),
                CoreConstants.StandardTokenTypeHintNames.RefreshToken => await _tokenStore
                .GetRefreshToken(introspectionParameterToken, cancellationToken)
                .ConfigureAwait(false),
                _ => null
            };

            // 5. Return an error if there's no granted token
            if (grantedToken == null)
            {
                return(new ErrorDetails {
                    Title = ErrorCodes.InvalidGrant, Detail = Strings.TheTokenIsNotValid
                });
            }

            // 6. Fill-in parameters
            //// default : Specify the other parameters : NBF & JTI
            var result = new UmaIntrospectionResponse
            {
                //Scope = grantedToken.Scope.Split(' ', StringSplitOptions.RemoveEmptyEntries),
                ClientId   = grantedToken.ClientId,
                Expiration = grantedToken.ExpiresIn,
                TokenType  = grantedToken.TokenType
            };

            if (grantedToken.UserInfoPayLoad != null)
            {
                var subject =
                    grantedToken.IdTokenPayLoad?.GetClaimValue(OpenIdClaimTypes.Subject);
                if (!string.IsNullOrWhiteSpace(subject))
                {
                    result = result with {
                        Subject = subject
                    };
                }
            }

            // 7. Fill-in the other parameters
            if (grantedToken.IdTokenPayLoad != null)
            {
                var audiencesArr = grantedToken.IdTokenPayLoad.GetArrayValue(StandardClaimNames.Audiences);
                var subject      =
                    grantedToken.IdTokenPayLoad.GetClaimValue(OpenIdClaimTypes.Subject);
                var userName =
                    grantedToken.IdTokenPayLoad.GetClaimValue(OpenIdClaimTypes.Name);

                result = result with
                {
                    Audience = string.Join(" ", audiencesArr),
                    IssuedAt = grantedToken.IdTokenPayLoad.Iat ?? 0,
                    Issuer   = grantedToken.IdTokenPayLoad.Iss
                };
                if (!string.IsNullOrWhiteSpace(subject))
                {
                    result = result with {
                        Subject = subject
                    };
                }

                if (!string.IsNullOrWhiteSpace(userName))
                {
                    result = result with {
                        UserName = userName
                    };
                }
            }

            // 8. Based on the expiration date disable OR enable the introspection resultKind
            var expirationDateTime = grantedToken.CreateDateTime.AddSeconds(grantedToken.ExpiresIn);

            result = result with {
                Active = DateTimeOffset.UtcNow < expirationDateTime
            };

            return(result);
        }
    }
}
        public async Task <IntrospectionResult> Execute(
            IntrospectionParameter introspectionParameter,
            AuthenticationHeaderValue authenticationHeaderValue, string issuerName)
        {
            // 1. Validate the parameters
            if (introspectionParameter == null)
            {
                throw new ArgumentNullException(nameof(introspectionParameter));
            }

            if (string.IsNullOrWhiteSpace(introspectionParameter.Token))
            {
                throw new ArgumentNullException(nameof(introspectionParameter.Token));
            }

            _introspectionParameterValidator.Validate(introspectionParameter);

            // 2. Authenticate the client
            var instruction = CreateAuthenticateInstruction(introspectionParameter, authenticationHeaderValue);
            var authResult  = await _authenticateClient.AuthenticateAsync(instruction, issuerName);

            if (authResult.Client == null)
            {
                throw new IdentityServerException(ErrorCodes.InvalidClient, authResult.ErrorMessage);
            }

            // 3. Retrieve the token type hint
            var tokenTypeHint = Constants.StandardTokenTypeHintNames.AccessToken;

            if (Constants.AllStandardTokenTypeHintNames.Contains(introspectionParameter.TokenTypeHint))
            {
                tokenTypeHint = introspectionParameter.TokenTypeHint;
            }

            // 4. Trying to fetch the information about the access_token  || refresh_token
            GrantedToken grantedToken = null;

            if (tokenTypeHint == Constants.StandardTokenTypeHintNames.AccessToken)
            {
                grantedToken = await _tokenStore.GetAccessToken(introspectionParameter.Token);

                if (grantedToken == null)
                {
                    grantedToken = await _tokenStore.GetRefreshToken(introspectionParameter.Token);
                }
            }
            else
            {
                grantedToken = await _tokenStore.GetRefreshToken(introspectionParameter.Token);

                if (grantedToken == null)
                {
                    grantedToken = await _tokenStore.GetAccessToken(introspectionParameter.Token);
                }
            }

            // 5. Throw an exception if there's no granted token
            if (grantedToken == null)
            {
                throw new IdentityServerException(
                          ErrorCodes.InvalidToken,
                          ErrorDescriptions.TheTokenIsNotValid);
            }

            // 6. Fill-in parameters
            //// TODO : Specifiy the other parameters : NBF & JTI
            var result = new IntrospectionResult
            {
                Scope      = grantedToken.Scope,
                ClientId   = grantedToken.ClientId,
                Expiration = grantedToken.ExpiresIn,
                TokenType  = grantedToken.TokenType
            };

            // 7. Fill-in the other parameters
            if (grantedToken.IdTokenPayLoad != null)
            {
                var audiences    = string.Empty;
                var audiencesArr = grantedToken.IdTokenPayLoad.GetArrayClaim(StandardClaimNames.Audiences);
                var issuedAt     = grantedToken.IdTokenPayLoad.Iat;
                var issuer       = grantedToken.IdTokenPayLoad.Issuer;
                var subject      = grantedToken.IdTokenPayLoad.GetClaimValue(Jwt.Constants.StandardResourceOwnerClaimNames.Subject);
                var userName     = grantedToken.IdTokenPayLoad.GetClaimValue(Jwt.Constants.StandardResourceOwnerClaimNames.Name);
                if (audiencesArr.Any())
                {
                    audiences = string.Join(" ", audiencesArr);
                }

                result.Audience = audiences;
                result.IssuedAt = issuedAt;
                result.Issuer   = issuer;
                result.Subject  = subject;
                result.UserName = userName;
            }

            // 8. Based on the expiration date disable OR enable the introspection result
            var expirationDateTime = grantedToken.CreateDateTime.AddSeconds(grantedToken.ExpiresIn);
            var tokenIsExpired     = DateTime.UtcNow > expirationDateTime;

            if (tokenIsExpired)
            {
                result.Active = false;
            }
            else
            {
                result.Active = true;
            }

            return(result);
        }
        public async Task <Option <OauthIntrospectionResponse> > Execute(
            IntrospectionParameter introspectionParameter,
            CancellationToken cancellationToken)
        {
            // Read this RFC for more information - https://www.rfc-editor.org/rfc/rfc7662.txt

            // 3. Retrieve the token type hint
            var tokenTypeHint = CoreConstants.StandardTokenTypeHintNames.AccessToken;

            if (CoreConstants.AllStandardTokenTypeHintNames.Contains(introspectionParameter.TokenTypeHint))
            {
                tokenTypeHint = introspectionParameter.TokenTypeHint;
            }

            // 4. Trying to fetch the information about the access_token  || refresh_token
            var introspectionParameterToken = introspectionParameter.Token;
            var grantedToken = tokenTypeHint switch
            {
                _ when introspectionParameterToken == null => null,
                CoreConstants.StandardTokenTypeHintNames.AccessToken => await _tokenStore
                .GetAccessToken(introspectionParameterToken, cancellationToken)
                .ConfigureAwait(false),
                CoreConstants.StandardTokenTypeHintNames.RefreshToken => await _tokenStore
                .GetRefreshToken(introspectionParameterToken, cancellationToken)
                .ConfigureAwait(false),
                _ => null
            };

            // 5. Return an error if there's no granted token
            if (grantedToken == null)
            {
                return(new OauthIntrospectionResponse());
            }

            // 6. Fill-in parameters
            //// default : Specify the other parameters : NBF & JTI
            var result = new OauthIntrospectionResponse
            {
                Scope      = grantedToken.Scope.Split(' ', StringSplitOptions.RemoveEmptyEntries),
                ClientId   = grantedToken.ClientId,
                Expiration = grantedToken.ExpiresIn,
                TokenType  = grantedToken.TokenType
            };

            if (grantedToken.UserInfoPayLoad != null)
            {
                var subject =
                    grantedToken.IdTokenPayLoad?.GetClaimValue(OpenIdClaimTypes.Subject);
                if (!string.IsNullOrWhiteSpace(subject))
                {
                    result = result with {
                        Subject = subject
                    };
                }
            }

            // 7. Fill-in the other parameters
            if (grantedToken.IdTokenPayLoad != null)
            {
                var audiencesArr = grantedToken.IdTokenPayLoad.GetArrayValue(StandardClaimNames.Audiences);
                var subject      =
                    grantedToken.IdTokenPayLoad.GetClaimValue(OpenIdClaimTypes.Subject);
                var userName =
                    grantedToken.IdTokenPayLoad.GetClaimValue(OpenIdClaimTypes.Name);

                result = result with
                {
                    Audience = string.Join(" ", audiencesArr),
                    IssuedAt = grantedToken.IdTokenPayLoad.Iat ?? 0,
                    Issuer   = grantedToken.IdTokenPayLoad.Iss
                };
                if (!string.IsNullOrWhiteSpace(subject))
                {
                    result = result with {
                        Subject = subject
                    };
                }

                if (!string.IsNullOrWhiteSpace(userName))
                {
                    result = result with {
                        UserName = userName
                    };
                }
            }

            // 8. Based on the expiration date disable OR enable the introspection resultKind
            var expirationDateTime = grantedToken.CreateDateTime.AddSeconds(grantedToken.ExpiresIn);

            result = result with {
                Active = DateTimeOffset.UtcNow < expirationDateTime
            };

            return(result);
        }
    }
}