private void ValidateNonce(JwtSecurityToken jwt, PublicOpenIdConnectProtocolValidator protocolValidator, OpenIdConnectProtocolValidationContext validationContext, ExpectedException ee) { try { protocolValidator.PublicValidateNonce(jwt, validationContext); ee.ProcessNoException(); } catch (Exception ex) { ee.ProcessException(ex); } }
public void OpenIdConnectProtocolValidator_ValidateNonce() { PublicOpenIdConnectProtocolValidator protocolValidatorRequiresTimeStamp = new PublicOpenIdConnectProtocolValidator(); string nonceWithTimeStamp = protocolValidatorRequiresTimeStamp.GenerateNonce(); PublicOpenIdConnectProtocolValidator protocolValidatorDoesNotRequireTimeStamp = new PublicOpenIdConnectProtocolValidator { RequireTimeStampInNonce = false, }; PublicOpenIdConnectProtocolValidator protocolValidatorDoesNotRequireNonce = new PublicOpenIdConnectProtocolValidator { RequireNonce = false, }; string nonceWithoutTimeStamp = protocolValidatorDoesNotRequireTimeStamp.GenerateNonce(); string nonceBadTimeStamp = "abc.abc"; string nonceTicksTooLarge = Int64.MaxValue.ToString() + "." + nonceWithoutTimeStamp; string nonceTicksTooSmall = Int64.MinValue.ToString() + "." + nonceWithoutTimeStamp; string nonceTicksNegative = ((Int64)(-1)).ToString() + "." + nonceWithoutTimeStamp; string nonceTicksZero = ((Int64)(0)).ToString() + "." + nonceWithoutTimeStamp; JwtSecurityToken jwtWithNonceWithTimeStamp = new JwtSecurityToken(claims: new List <Claim> { new Claim(JwtRegisteredClaimNames.Nonce, nonceWithTimeStamp) }); JwtSecurityToken jwtWithNonceWithoutTimeStamp = new JwtSecurityToken(claims: new List <Claim> { new Claim(JwtRegisteredClaimNames.Nonce, nonceWithoutTimeStamp) }); JwtSecurityToken jwtWithNonceWithBadTimeStamp = new JwtSecurityToken(claims: new List <Claim> { new Claim(JwtRegisteredClaimNames.Nonce, nonceBadTimeStamp) }); JwtSecurityToken jwtWithNonceTicksTooLarge = new JwtSecurityToken(claims: new List <Claim> { new Claim(JwtRegisteredClaimNames.Nonce, nonceTicksTooLarge) }); JwtSecurityToken jwtWithNonceTicksTooSmall = new JwtSecurityToken(claims: new List <Claim> { new Claim(JwtRegisteredClaimNames.Nonce, nonceTicksTooSmall) }); JwtSecurityToken jwtWithNonceTicksNegative = new JwtSecurityToken(claims: new List <Claim> { new Claim(JwtRegisteredClaimNames.Nonce, nonceTicksNegative) }); JwtSecurityToken jwtWithNonceZero = new JwtSecurityToken(claims: new List <Claim> { new Claim(JwtRegisteredClaimNames.Nonce, nonceTicksZero) }); JwtSecurityToken jwtWithoutNonce = new JwtSecurityToken(claims: new List <Claim> { new Claim(JwtRegisteredClaimNames.NameId, nonceWithTimeStamp) }); JwtSecurityToken jwtWithNonceWhitespace = new JwtSecurityToken(claims: new List <Claim> { new Claim(JwtRegisteredClaimNames.Nonce, "") }); OpenIdConnectProtocolValidationContext validationContext = new OpenIdConnectProtocolValidationContext(); validationContext.Nonce = null; ValidateNonce(jwt: null, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: ExpectedException.ArgumentNullException()); ValidateNonce(jwt: jwtWithNonceWithTimeStamp, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: null, ee: ExpectedException.ArgumentNullException()); // nonce is null, RequireNonce is true. ValidateNonce(jwt: jwtWithNonceWithTimeStamp, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: new ExpectedException(typeof(OpenIdConnectProtocolInvalidNonceException), substringExpected: "IDX10311:")); validationContext.Nonce = nonceWithoutTimeStamp; ValidateNonce(jwt: jwtWithoutNonce, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: new ExpectedException(typeof(OpenIdConnectProtocolInvalidNonceException), substringExpected: "IDX10322:")); ValidateNonce(jwt: jwtWithNonceWhitespace, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: new ExpectedException(typeof(OpenIdConnectProtocolInvalidNonceException), substringExpected: "IDX10301:")); ValidateNonce(jwt: jwtWithNonceWithTimeStamp, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: new ExpectedException(typeof(OpenIdConnectProtocolInvalidNonceException), substringExpected: "IDX10301:")); validationContext.Nonce = nonceWithTimeStamp; ValidateNonce(jwt: jwtWithNonceWithTimeStamp, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: ExpectedException.NoExceptionExpected); // nonce expired validationContext.Nonce = nonceWithTimeStamp; protocolValidatorRequiresTimeStamp.NonceLifetime = TimeSpan.FromMilliseconds(10); Thread.Sleep(100); ValidateNonce(jwt: jwtWithNonceWithTimeStamp, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: new ExpectedException(typeof(OpenIdConnectProtocolInvalidNonceException))); // nonce missing timestamp, validator requires time stamp // 1. not well formed, no '.' validationContext.Nonce = nonceWithoutTimeStamp; protocolValidatorRequiresTimeStamp.NonceLifetime = TimeSpan.FromMinutes(10); ValidateNonce(jwt: jwtWithNonceWithoutTimeStamp, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: new ExpectedException(typeof(OpenIdConnectProtocolInvalidNonceException), substringExpected: "IDX10317:")); // 2. timestamp not well formed validationContext.Nonce = nonceBadTimeStamp; ValidateNonce(jwt: jwtWithNonceWithBadTimeStamp, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: new ExpectedException(typeExpected: typeof(OpenIdConnectProtocolInvalidNonceException), innerTypeExpected: typeof(FormatException), substringExpected: "IDX10318:")); // 3. timestamp not required validationContext.Nonce = nonceBadTimeStamp; ValidateNonce(jwt: jwtWithNonceWithBadTimeStamp, protocolValidator: protocolValidatorDoesNotRequireTimeStamp, validationContext: validationContext, ee: ExpectedException.NoExceptionExpected); // 4. ticks max value validationContext.Nonce = nonceTicksTooLarge; ValidateNonce(jwt: jwtWithNonceTicksTooLarge, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: new ExpectedException(typeExpected: typeof(OpenIdConnectProtocolInvalidNonceException), innerTypeExpected: typeof(ArgumentException), substringExpected: "IDX10320:")); // 5. ticks min value small validationContext.Nonce = nonceTicksTooSmall; ValidateNonce(jwt: jwtWithNonceTicksTooSmall, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: new ExpectedException(typeExpected: typeof(OpenIdConnectProtocolInvalidNonceException), substringExpected: "IDX10318:")); // 6. ticks negative validationContext.Nonce = nonceTicksNegative; ValidateNonce(jwt: jwtWithNonceTicksNegative, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: new ExpectedException(typeExpected: typeof(OpenIdConnectProtocolInvalidNonceException), substringExpected: "IDX10318:")); // 7. ticks zero validationContext.Nonce = nonceTicksZero; ValidateNonce(jwt: jwtWithNonceZero, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: new ExpectedException(typeExpected: typeof(OpenIdConnectProtocolInvalidNonceException), substringExpected: "IDX10318:")); // require nonce false validationContext.Nonce = null; ValidateNonce(jwt: jwtWithNonceWithoutTimeStamp, protocolValidator: protocolValidatorDoesNotRequireNonce, validationContext: validationContext, ee: ExpectedException.NoExceptionExpected); // validationContext has nonce validationContext.Nonce = nonceWithTimeStamp; ValidateNonce(jwt: jwtWithoutNonce, protocolValidator: protocolValidatorDoesNotRequireNonce, validationContext: validationContext, ee: new ExpectedException(typeExpected: typeof(OpenIdConnectProtocolInvalidNonceException), substringExpected: "IDX10323:")); }
public void OpenIdConnectProtocolValidator_CHash() { PublicOpenIdConnectProtocolValidator protocolValidator = new PublicOpenIdConnectProtocolValidator(); string authorizationCode1 = protocolValidator.GenerateNonce(); string authorizationCode2 = protocolValidator.GenerateNonce(); string chash1 = IdentityUtilities.CreateCHash(authorizationCode1, "SHA256"); string chash2 = IdentityUtilities.CreateCHash(authorizationCode2, "SHA256"); Dictionary <string, string> emptyDictionary = new Dictionary <string, string>(); Dictionary <string, string> mappedDictionary = new Dictionary <string, string>(protocolValidator.HashAlgorithmMap); JwtSecurityToken jwtWithCHash1 = new JwtSecurityToken ( audience: IdentityUtilities.DefaultAudience, claims: new List <Claim> { new Claim(JwtRegisteredClaimNames.CHash, chash1) }, issuer: IdentityUtilities.DefaultIssuer ); JwtSecurityToken jwtWithEmptyCHash = new JwtSecurityToken ( audience: IdentityUtilities.DefaultAudience, claims: new List <Claim> { new Claim(JwtRegisteredClaimNames.CHash, string.Empty) }, issuer: IdentityUtilities.DefaultIssuer, signingCredentials: IdentityUtilities.DefaultAsymmetricSigningCredentials ); JwtSecurityToken jwtWithoutCHash = new JwtSecurityToken ( audience: IdentityUtilities.DefaultAudience, claims: new List <Claim> { new Claim(JwtRegisteredClaimNames.Nonce, chash2) }, issuer: IdentityUtilities.DefaultIssuer ); JwtSecurityToken jwtWithSignatureChash1 = new JwtSecurityToken ( audience: IdentityUtilities.DefaultAudience, claims: new List <Claim> { new Claim(JwtRegisteredClaimNames.CHash, chash1) }, issuer: IdentityUtilities.DefaultIssuer, signingCredentials: IdentityUtilities.DefaultAsymmetricSigningCredentials ); JwtSecurityToken jwtWithSignatureMultipleChashes = new JwtSecurityToken ( audience: IdentityUtilities.DefaultAudience, claims: new List <Claim> { new Claim(JwtRegisteredClaimNames.CHash, chash1), new Claim(JwtRegisteredClaimNames.CHash, chash2) }, issuer: IdentityUtilities.DefaultIssuer, signingCredentials: IdentityUtilities.DefaultAsymmetricSigningCredentials ); OpenIdConnectProtocolValidationContext validationContext = new OpenIdConnectProtocolValidationContext(); validationContext.AuthorizationCode = authorizationCode2; // chash is not a string, but array ValidateCHash(jwt: jwtWithSignatureMultipleChashes, protocolValidator: protocolValidator, validationContext: validationContext, ee: new ExpectedException(typeExpected: typeof(OpenIdConnectProtocolInvalidCHashException), substringExpected: "IDX10304:")); // chash doesn't match ValidateCHash(jwt: jwtWithSignatureChash1, protocolValidator: protocolValidator, validationContext: validationContext, ee: new ExpectedException(typeExpected: typeof(OpenIdConnectProtocolInvalidCHashException), substringExpected: "IDX10304:")); // use algorithm map validationContext.AuthorizationCode = authorizationCode1; ValidateCHash(jwt: jwtWithSignatureChash1, protocolValidator: protocolValidator, validationContext: validationContext, ee: ExpectedException.NoExceptionExpected); // Creation of algorithm failed, need to map. protocolValidator.SetHashAlgorithmMap(emptyDictionary); ValidateCHash(jwt: jwtWithSignatureChash1, protocolValidator: protocolValidator, validationContext: validationContext, ee: new ExpectedException(typeExpected: typeof(OpenIdConnectProtocolInvalidCHashException), substringExpected: "IDX10307:")); protocolValidator.SetHashAlgorithmMap(mappedDictionary); ValidateCHash(jwt: null, protocolValidator: protocolValidator, validationContext: validationContext, ee: ExpectedException.ArgumentNullException()); ValidateCHash(jwt: jwtWithoutCHash, protocolValidator: protocolValidator, validationContext: validationContext, ee: new ExpectedException(typeExpected: typeof(OpenIdConnectProtocolInvalidCHashException), substringExpected: "IDX10308:")); ValidateCHash(jwt: jwtWithEmptyCHash, protocolValidator: protocolValidator, validationContext: validationContext, ee: new ExpectedException(typeExpected: typeof(OpenIdConnectProtocolInvalidCHashException), substringExpected: "IDX10304:")); ValidateCHash(jwt: jwtWithCHash1, protocolValidator: protocolValidator, validationContext: validationContext, ee: new ExpectedException(typeExpected: typeof(OpenIdConnectProtocolInvalidCHashException), substringExpected: "IDX10307:")); ValidateCHash(jwt: jwtWithoutCHash, protocolValidator: protocolValidator, validationContext: null, ee: ExpectedException.ArgumentNullException()); // make sure default alg works. validationContext.AuthorizationCode = authorizationCode1; jwtWithCHash1.Header.Remove("alg"); ValidateCHash(jwt: jwtWithCHash1, protocolValidator: protocolValidator, validationContext: validationContext, ee: ExpectedException.NoExceptionExpected); }
private void ValidateNonce(JwtSecurityToken jwt, PublicOpenIdConnectProtocolValidator protocolValidator, OpenIdConnectProtocolValidationContext validationContext, ExpectedException ee) { try { protocolValidator.PublicValidateNonce(jwt, validationContext); ee.ProcessNoException(); } catch(Exception ex) { ee.ProcessException(ex); } }
public void OpenIdConnectProtocolValidator_ValidateNonce() { PublicOpenIdConnectProtocolValidator protocolValidatorRequiresTimeStamp = new PublicOpenIdConnectProtocolValidator(); string nonceWithTimeStamp = protocolValidatorRequiresTimeStamp.GenerateNonce(); PublicOpenIdConnectProtocolValidator protocolValidatorDoesNotRequireTimeStamp = new PublicOpenIdConnectProtocolValidator { RequireTimeStampInNonce = false, }; PublicOpenIdConnectProtocolValidator protocolValidatorDoesNotRequireNonce = new PublicOpenIdConnectProtocolValidator { RequireNonce = false, }; string nonceWithoutTimeStamp = protocolValidatorDoesNotRequireTimeStamp.GenerateNonce(); string nonceBadTimeStamp = "abc.abc"; string nonceTicksTooLarge = Int64.MaxValue.ToString() + "." + nonceWithoutTimeStamp; string nonceTicksTooSmall = Int64.MinValue.ToString() + "." + nonceWithoutTimeStamp; string nonceTicksNegative = ((Int64)(-1)).ToString() + "." + nonceWithoutTimeStamp; string nonceTicksZero = ((Int64)(0)).ToString() + "." + nonceWithoutTimeStamp; JwtSecurityToken jwtWithNonceWithTimeStamp = new JwtSecurityToken ( claims: new List<Claim> { new Claim(JwtRegisteredClaimNames.Nonce, nonceWithTimeStamp) }); JwtSecurityToken jwtWithNonceWithoutTimeStamp = new JwtSecurityToken(claims: new List<Claim> { new Claim(JwtRegisteredClaimNames.Nonce, nonceWithoutTimeStamp) }); JwtSecurityToken jwtWithNonceWithBadTimeStamp = new JwtSecurityToken(claims: new List<Claim> { new Claim(JwtRegisteredClaimNames.Nonce, nonceBadTimeStamp) }); JwtSecurityToken jwtWithNonceTicksTooLarge = new JwtSecurityToken(claims: new List<Claim> { new Claim(JwtRegisteredClaimNames.Nonce, nonceTicksTooLarge) }); JwtSecurityToken jwtWithNonceTicksTooSmall = new JwtSecurityToken(claims: new List<Claim> { new Claim(JwtRegisteredClaimNames.Nonce, nonceTicksTooSmall) }); JwtSecurityToken jwtWithNonceTicksNegative = new JwtSecurityToken(claims: new List<Claim> { new Claim(JwtRegisteredClaimNames.Nonce, nonceTicksNegative) }); JwtSecurityToken jwtWithNonceZero = new JwtSecurityToken(claims: new List<Claim> { new Claim(JwtRegisteredClaimNames.Nonce, nonceTicksZero) }); JwtSecurityToken jwtWithoutNonce = new JwtSecurityToken(claims: new List<Claim> { new Claim(JwtRegisteredClaimNames.NameId, nonceWithTimeStamp) }); JwtSecurityToken jwtWithNonceWhitespace = new JwtSecurityToken(claims: new List<Claim> { new Claim(JwtRegisteredClaimNames.Nonce, "") }); OpenIdConnectProtocolValidationContext validationContext = new OpenIdConnectProtocolValidationContext(); validationContext.Nonce = null; ValidateNonce(jwt: null, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: ExpectedException.ArgumentNullException()); ValidateNonce(jwt: jwtWithNonceWithTimeStamp, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: null, ee: ExpectedException.ArgumentNullException()); // nonce is null, RequireNonce is true. ValidateNonce(jwt: jwtWithNonceWithTimeStamp, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: new ExpectedException(typeof(OpenIdConnectProtocolInvalidNonceException), substringExpected: "IDX10311:")); validationContext.Nonce = nonceWithoutTimeStamp; ValidateNonce(jwt: jwtWithoutNonce, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: new ExpectedException(typeof(OpenIdConnectProtocolInvalidNonceException), substringExpected: "IDX10322:")); ValidateNonce(jwt: jwtWithNonceWhitespace, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: new ExpectedException(typeof(OpenIdConnectProtocolInvalidNonceException), substringExpected: "IDX10301:")); ValidateNonce(jwt: jwtWithNonceWithTimeStamp, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: new ExpectedException(typeof(OpenIdConnectProtocolInvalidNonceException), substringExpected: "IDX10301:")); validationContext.Nonce = nonceWithTimeStamp; ValidateNonce(jwt: jwtWithNonceWithTimeStamp, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: ExpectedException.NoExceptionExpected); // nonce expired validationContext.Nonce = nonceWithTimeStamp; protocolValidatorRequiresTimeStamp.NonceLifetime = TimeSpan.FromMilliseconds(10); Thread.Sleep(100); ValidateNonce(jwt: jwtWithNonceWithTimeStamp, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: new ExpectedException(typeof(OpenIdConnectProtocolInvalidNonceException))); // nonce missing timestamp, validator requires time stamp // 1. not well formed, no '.' validationContext.Nonce = nonceWithoutTimeStamp; protocolValidatorRequiresTimeStamp.NonceLifetime = TimeSpan.FromMinutes(10); ValidateNonce(jwt: jwtWithNonceWithoutTimeStamp, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: new ExpectedException(typeof(OpenIdConnectProtocolInvalidNonceException), substringExpected: "IDX10317:")); // 2. timestamp not well formed validationContext.Nonce = nonceBadTimeStamp; ValidateNonce(jwt: jwtWithNonceWithBadTimeStamp, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: new ExpectedException( typeExpected: typeof(OpenIdConnectProtocolInvalidNonceException), innerTypeExpected: typeof(FormatException), substringExpected: "IDX10318:")); // 3. timestamp not required validationContext.Nonce = nonceBadTimeStamp; ValidateNonce(jwt: jwtWithNonceWithBadTimeStamp, protocolValidator: protocolValidatorDoesNotRequireTimeStamp, validationContext: validationContext, ee: ExpectedException.NoExceptionExpected); // 4. ticks max value validationContext.Nonce = nonceTicksTooLarge; ValidateNonce(jwt: jwtWithNonceTicksTooLarge, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: new ExpectedException(typeExpected: typeof(OpenIdConnectProtocolInvalidNonceException), innerTypeExpected: typeof(ArgumentException), substringExpected: "IDX10320:")); // 5. ticks min value small validationContext.Nonce = nonceTicksTooSmall; ValidateNonce(jwt: jwtWithNonceTicksTooSmall, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: new ExpectedException(typeExpected: typeof(OpenIdConnectProtocolInvalidNonceException), substringExpected: "IDX10318:")); // 6. ticks negative validationContext.Nonce = nonceTicksNegative; ValidateNonce(jwt: jwtWithNonceTicksNegative, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: new ExpectedException(typeExpected: typeof(OpenIdConnectProtocolInvalidNonceException), substringExpected: "IDX10318:")); // 7. ticks zero validationContext.Nonce = nonceTicksZero; ValidateNonce(jwt: jwtWithNonceZero, protocolValidator: protocolValidatorRequiresTimeStamp, validationContext: validationContext, ee: new ExpectedException(typeExpected: typeof(OpenIdConnectProtocolInvalidNonceException), substringExpected: "IDX10318:")); // require nonce false validationContext.Nonce = null; ValidateNonce(jwt: jwtWithNonceWithoutTimeStamp, protocolValidator: protocolValidatorDoesNotRequireNonce, validationContext: validationContext, ee: ExpectedException.NoExceptionExpected); // validationContext has nonce validationContext.Nonce = nonceWithTimeStamp; ValidateNonce(jwt: jwtWithoutNonce, protocolValidator: protocolValidatorDoesNotRequireNonce, validationContext: validationContext, ee: new ExpectedException(typeExpected: typeof(OpenIdConnectProtocolInvalidNonceException), substringExpected: "IDX10323:")); }
public void OpenIdConnectProtocolValidator_CHash() { PublicOpenIdConnectProtocolValidator protocolValidator = new PublicOpenIdConnectProtocolValidator(); string authorizationCode1 = protocolValidator.GenerateNonce(); string authorizationCode2 = protocolValidator.GenerateNonce(); string chash1 = IdentityUtilities.CreateCHash(authorizationCode1, "SHA256"); string chash2 = IdentityUtilities.CreateCHash(authorizationCode2, "SHA256"); Dictionary<string, string> emptyDictionary = new Dictionary<string, string>(); Dictionary<string, string> mappedDictionary = new Dictionary<string, string>(protocolValidator.HashAlgorithmMap); JwtSecurityToken jwtWithCHash1 = new JwtSecurityToken ( audience: IdentityUtilities.DefaultAudience, claims: new List<Claim> { new Claim(JwtRegisteredClaimNames.CHash, chash1) }, issuer: IdentityUtilities.DefaultIssuer ); JwtSecurityToken jwtWithEmptyCHash = new JwtSecurityToken ( audience: IdentityUtilities.DefaultAudience, claims: new List<Claim> { new Claim(JwtRegisteredClaimNames.CHash, string.Empty) }, issuer: IdentityUtilities.DefaultIssuer, signingCredentials: IdentityUtilities.DefaultAsymmetricSigningCredentials ); JwtSecurityToken jwtWithoutCHash = new JwtSecurityToken ( audience: IdentityUtilities.DefaultAudience, claims: new List<Claim> { new Claim(JwtRegisteredClaimNames.Nonce, chash2) }, issuer: IdentityUtilities.DefaultIssuer ); JwtSecurityToken jwtWithSignatureChash1 = new JwtSecurityToken ( audience : IdentityUtilities.DefaultAudience, claims: new List<Claim> { new Claim(JwtRegisteredClaimNames.CHash, chash1) }, issuer: IdentityUtilities.DefaultIssuer, signingCredentials : IdentityUtilities.DefaultAsymmetricSigningCredentials ); JwtSecurityToken jwtWithSignatureMultipleChashes = new JwtSecurityToken ( audience: IdentityUtilities.DefaultAudience, claims: new List<Claim> { new Claim(JwtRegisteredClaimNames.CHash, chash1), new Claim(JwtRegisteredClaimNames.CHash, chash2) }, issuer: IdentityUtilities.DefaultIssuer, signingCredentials: IdentityUtilities.DefaultAsymmetricSigningCredentials ); OpenIdConnectProtocolValidationContext validationContext = new OpenIdConnectProtocolValidationContext(); validationContext.AuthorizationCode = authorizationCode2; // chash is not a string, but array ValidateCHash(jwt: jwtWithSignatureMultipleChashes, protocolValidator: protocolValidator, validationContext: validationContext, ee: new ExpectedException(typeExpected: typeof(OpenIdConnectProtocolInvalidCHashException), substringExpected: "IDX10304:")); // chash doesn't match ValidateCHash(jwt: jwtWithSignatureChash1, protocolValidator: protocolValidator, validationContext: validationContext, ee: new ExpectedException(typeExpected: typeof(OpenIdConnectProtocolInvalidCHashException), substringExpected: "IDX10304:")); // use algorithm map validationContext.AuthorizationCode = authorizationCode1; ValidateCHash(jwt: jwtWithSignatureChash1, protocolValidator: protocolValidator, validationContext: validationContext, ee: ExpectedException.NoExceptionExpected); // Creation of algorithm failed, need to map. protocolValidator.SetHashAlgorithmMap(emptyDictionary); ValidateCHash(jwt: jwtWithSignatureChash1, protocolValidator: protocolValidator, validationContext: validationContext, ee: new ExpectedException(typeExpected: typeof(OpenIdConnectProtocolInvalidCHashException), substringExpected: "IDX10307:")); protocolValidator.SetHashAlgorithmMap(mappedDictionary); ValidateCHash(jwt: null, protocolValidator: protocolValidator, validationContext: validationContext, ee: ExpectedException.ArgumentNullException()); ValidateCHash(jwt: jwtWithoutCHash, protocolValidator: protocolValidator, validationContext: validationContext, ee: new ExpectedException(typeExpected: typeof(OpenIdConnectProtocolInvalidCHashException), substringExpected: "IDX10308:")); ValidateCHash(jwt: jwtWithEmptyCHash, protocolValidator: protocolValidator, validationContext: validationContext, ee: new ExpectedException(typeExpected: typeof(OpenIdConnectProtocolInvalidCHashException), substringExpected: "IDX10304:")); ValidateCHash(jwt: jwtWithCHash1, protocolValidator: protocolValidator, validationContext: validationContext, ee: new ExpectedException(typeExpected: typeof(OpenIdConnectProtocolInvalidCHashException), substringExpected: "IDX10307:")); ValidateCHash(jwt: jwtWithoutCHash, protocolValidator: protocolValidator, validationContext: null, ee: ExpectedException.ArgumentNullException()); // make sure default alg works. validationContext.AuthorizationCode = authorizationCode1; jwtWithCHash1.Header.Remove("alg"); ValidateCHash(jwt: jwtWithCHash1, protocolValidator: protocolValidator, validationContext: validationContext, ee: ExpectedException.NoExceptionExpected); }