Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix over-reporting of IDX14100 stating "there are no dots" #2618

Merged
merged 1 commit into from
May 30, 2024

Conversation

halter73
Copy link
Contributor

IDX14100 makes sense when it is thrown from JsonWebToken constructor or Read method when there is really one dot, but not as a generic error message any time there is a token validation failure for any reason.

IDX14100: JWT is not well formed, there are no dots (.).\nThe token needs to be in JWS or JWE Compact Serialization Format. (JWS): 'EncodedHeader.EncodedPayload.EncodedSignature'. (JWE): 'EncodedProtectedHeader.EncodedEncryptedKey.EncodedInitializationVector.EncodedCiphertext.EncodedAuthenticationTag'.

Dot1 = encodedTokenSpan.IndexOf('.');
if (Dot1 == -1 || Dot1 == encodedTokenSpan.Length - 1)
throw LogHelper.LogExceptionMessage(new SecurityTokenMalformedException(LogMessages.IDX14100));

The above line seems to be the only correct usage of the IDX14100, and it remains after this PR. IDX14120 gives a more precise error message when a "JWT is not well formed, there is only one dot", but that winds up getting wrapped in another exception with the incorrect IDX14100 message and relogged by JsonWebTokenHandler.ReadToken. Other validation errors like a non-numeric "iat" claim also result get the incorrect IDX14100 message.

info: Microsoft.AspNetCore.Authentication.JwtBearer.JwtBearerHandler[1]
      Failed to validate the token.
      Microsoft.IdentityModel.Tokens.SecurityTokenMalformedException: IDX14100: JWT is not well formed, there are no dots (.).
The token needs to be in JWS or JWE Compact Serialization Format. (JWS): 'EncodedHeader.EndcodedPayload.EncodedSignature'. (JWE): 'EncodedProtectedHeader.EncodedEncryptedKey.EncodedInitializationVector.EncodedCiphertext.EncodedAuthenticationTag'.
       ---> System.ArgumentException: IDX14101: Unable to decode the payload '[PII of type 'Microsoft.IdentityModel.Logging.SecurityArtifact' is hidden. For more details, see https://aka.ms/IdentityModel/PII.]' as Base64Url encoded string.
       ---> System.Text.Json.JsonException: IDX11020: The JSON value of type: 'String', could not be converted to 'JsonTokenType.Number'. Reading: 'Microsoft.IdentityModel.JsonWebTokens.JsonWebToken.iat', Position: '52', CurrentDepth: '1', BytesConsumed: '75'.
         at Microsoft.IdentityModel.Tokens.Json.JsonSerializerPrimitives.ReadLong(Utf8JsonReader& reader, String propertyName, String className, Boolean read)
         at Microsoft.IdentityModel.JsonWebTokens.JsonWebToken.CreatePayloadClaimSet(Byte[] bytes, Int32 length)
         at Microsoft.IdentityModel.Tokens.Base64UrlEncoding.Decode[T](String input, Int32 offset, Int32 length, Func`3 action)
         at Microsoft.IdentityModel.JsonWebTokens.JsonWebToken.CreateClaimSet(String rawString, Int32 startIndex, Int32 length, Func`3 action)
         at Microsoft.IdentityModel.JsonWebTokens.JsonWebToken.ReadToken(String encodedJson)
         --- End of inner exception stack trace ---
         at Microsoft.IdentityModel.JsonWebTokens.JsonWebToken.ReadToken(String encodedJson)
         at Microsoft.IdentityModel.JsonWebTokens.JsonWebToken..ctor(String jwtEncodedString)
         at Microsoft.IdentityModel.JsonWebTokens.JsonWebTokenHandler.ReadToken(String token, TokenValidationParameters validationParameters)
         --- End of inner exception stack trace ---

This exception wrapping by JsonWebTokenHandler.ReadToken seems to serve no purpose other than make it appear that the token is invalid for the wrong reason. The original reporter pointed out that this was obscuring an exception caused by deleting System.Buffers.dll. While this isn't something a developer should do, it demonstrates why wrapping arbitrary exceptions is bad in this scenario. Even if the issue really was what is described by IDX14100, JsonWebTokenHandler.ReadToken still unnecessary wraps that with an identical outer exception and logs it a second time.

The change to use a custom ArgumentException rather than an IDX14100 SecurityTokenMalformedException when JsonWebTokenHandler.ValidateTokenAsync gets a non-JsonWebToken SecurityToken is less important, but it is another place IDX14100 is being used that has nothing to do with the number of dots in the token. I don't think we should be logging ArgumentExceptions at all, but I continue logging in order to stick to the conventions of the library. If we make a change to not log ArgumentExceptions, we should probably do that everywhwere.

Fixes #2058

@halter73 halter73 requested a review from a team as a code owner May 29, 2024 23:27
@jennyf19 jennyf19 merged commit 33c8c42 into AzureAD:dev May 30, 2024
5 checks passed
@jennyf19 jennyf19 added this to the 7.6.1 milestone May 30, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

[Bug] Unhelpful error message with missing dependency for System.Buffers
4 participants