IDX10501:签名验证失败。尝试的密钥:'System.IdentityModel.Tokens.X509AsymmetricSecurityKey'



我正在尝试验证来自Azure的令牌。我使用 Adal.js 来获取令牌。 当我尝试验证令牌时,每次总是收到相同的错误消息:

IDX10501:签名验证失败。密钥尝试:"System.IdentityModel.Tokens.X509AsymmetricSecurityKey"。 token: '{"typ":"JWT",...

消息中省略的令牌看起来像我在客户端上看到的,并且来自以下 3 个 url 的信息似乎已正确添加到数据结构中,即我可以看到填充字段的位置是我期望查看下面的链接和我在客户端上的令牌。

https://login.windows.net/{id}.onmicrosoft.com/federationmetadata/2007-06/federationmetadata.xml

https://login.microsoftonline.com/{id}.onmicrosoft.com/.well-known/openid-configuration

https://login.microsoftonline.com/common/discovery/keys

但是每当我到达最后一行ClaimsPrincipal claimsPrincipal = tokenHandler.ValidateToken(...我总是得到同样的错误。

任何想法如何使令牌验证?

// Get the jwt bearer token from the authorization header
string jwtToken = null;
AuthenticationHeaderValue authHeader = request.Headers.Authorization;
if (authHeader != null)
{
jwtToken = authHeader.Parameter;
}
string issuer;
List<SecurityToken> signingTokens;
// The issuer and signingTokens are cached for 24 hours. They are updated if any of the conditions in the if condition is true.            
if (DateTime.UtcNow.Subtract(_stsMetadataRetrievalTime).TotalHours > 24 || string.IsNullOrEmpty(_issuer) || _signingTokens == null)
{
// Get tenant information that's used to validate incoming jwt tokens
string stsDiscoveryEndpoint = string.Format("{0}/.well-known/openid-configuration", authority);
ConfigurationManager<OpenIdConnectConfiguration> configManager = new ConfigurationManager<OpenIdConnectConfiguration>(stsDiscoveryEndpoint);
OpenIdConnectConfiguration config = await configManager.GetConfigurationAsync();
_issuer = config.Issuer;
_signingTokens = config.SigningTokens.ToList();
_stsMetadataRetrievalTime = DateTime.UtcNow;
}
issuer = _issuer;
signingTokens = _signingTokens;
JwtSecurityTokenHandler tokenHandler = new JwtSecurityTokenHandler();
TokenValidationParameters validationParameters = new TokenValidationParameters
{
ValidAudience = audience,
ValidIssuer = issuer,
IssuerSigningTokens = signingTokens,
CertificateValidator = X509CertificateValidator.None
};
try {
// Validate token.
SecurityToken validatedToken = new JwtSecurityToken();
ClaimsPrincipal claimsPrincipal = tokenHandler.ValidateToken(jwtToken, validationParameters, out validatedToken);
}   

更新
以防万一我在初始化客户端和服务器时缺少某些内容。

Adal.js初始化选项是:

var endpoints = {
"https://graph.windows.net": "https://graph.windows.net"
};
var configOptions = {
tenant: "<ad>.onmicrosoft.com", // Optional by default, it sends common
clientId: "<app ID from azure portal>",
postLogoutRedirectUri: window.location.origin,
endpoints: endpoints,
}
window.authContext = new AuthenticationContext(configOptions);

服务器初始化选项包括:

static string aadInstance = "https://login.microsoftonline.com/{0}";
static string tenant = "<ad>.onmicrosoft.com";
static string audience = "<app ID from azure portal>";
string authority = String.Format(CultureInfo.InvariantCulture, aadInstance, tenant);
static string scopeClaimType = "http://schemas.microsoft.com/identity/claims/scope";

您要实现什么方案?你拥有的令牌适用于 AAD 图形 API,无需对其进行验证。使用该令牌执行 API 调用时,Microsoft 图形服务器端将验证访问令牌。

此外,在服务器端 init 选项中,将受众设置为来自 Azure 门户的应用 ID,这意味着在验证访问令牌时,访问令牌的受众应与 Azure 门户中的应用 ID 匹配,但访问令牌的受众https://graph.windows.net,因为你正在获取 Azure AD 图形 API 的令牌。

如果访问令牌是针对您自己的 API,则需要验证 API 中的访问令牌,可以使用 OWIN 中间件来处理令牌:

app.UseWindowsAzureActiveDirectoryBearerAuthentication(
new WindowsAzureActiveDirectoryBearerAuthenticationOptions
{
Audience = ConfigurationManager.AppSettings["ida:Audience"],
Tenant = ConfigurationManager.AppSettings["ida:Tenant"],
});

或手动验证 JWT 令牌,如以下代码示例。

相关内容

最新更新