将 IdentityServer4 升级到 Core 3.1 - 令牌突然没有正确签名? [英] Upgrading IdentityServer4 to Core 3.1 - tokens are suddenly not signed correctly?

查看:27
本文介绍了将 IdentityServer4 升级到 Core 3.1 - 令牌突然没有正确签名?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我们在将 IdentityServer4 (2.5.3 - 3.1.0) 升级到 Core 3.1(从 2.2)时遇到错误.突然发出的令牌没有正确的签名.我们没有改变签名算法;在不同版本之间仍然使用相同的 .PFX 证书.

var idSrvBuilder = services.AddIdentityServer(opts =>{opts.Events.RaiseErrorEvents = true;opts.Events.RaiseFailureEvents = true;opts.Events.RaiseInformationEvents = true;opts.Events.RaiseSuccessEvents = true;如果 (_env.IsProduction()){opts.PublicOrigin = Configuration["Globals:IdentityURL"];}}).AddSigningCredential(new X509Certificate2(Configuration["Cert:Path"], Configuration["Cert:Password"]));

当对旧 API 使用 OWIN 中间件UseIdentityServerBearerTokenAuthentication"时,如果 ValidationModeLocal,它会失败,但如果它直接针对 IdentityServer(使用 ValidationMode)进行验证,则不会 ValidationEndpoint).API 只会返回未授权",但可以使用旧令牌(对它们进行签名的相同证书!)

app.UseIdentityServerBearerTokenAuthentication(new IdentityServer3.AccessTokenValidation.IdentityServerBearerTokenAuthenticationOptions{权限 = AppSettings.Authority,ClientId = AppSettings.ApiName,ClientSecret = AppSettings.ApiSecret,EnableValidationResultCache = false,ValidationMode = IdentityServer3.AccessTokenValidation.ValidationMode.Local});

查看版本之间发布的令牌有明显的不同:

旧的(移除的有效载荷):

<预> <代码> eyJhbGciOiJSUzI1NiIsImtpZCI6IjZCMTM4RUIzMUE4OUExQTdEQTdCNkRGNzMwOTRGMzIzREJFNzhCNjYiLCJ0eXAiOiJKV1QiLCJ4NXQiOiJheE9Pc3hxSm9hZmFlMjMzTUpUekk5dm5pMlkifQ.U3unxhW6act8fQLCLAYBJAZ-lIMiKaghVEUdA3b7iM0mI0UqGmYgYw05SvVXTAT8ZNQPuq0D-97d0Z6VVBC2wH7VAl0daF6sYJyuSUEtDiBPttNQ9MsGBNjcN1HABZ0nv-z_lgG2Z9sgp4blCvc7N8xOsja-kuk6m06I7iOfS7O_YKPtTAXA10OCzdtiJbhYijeTFsBJaWf5-J3XJCtqpp-MGXCboE0gQIlvysKz5_CRaaKYptczw-cTX3sgRIhfWn2VxVujhH7JKeSJan52X-fQ4T47PWuVcWNOrcWheeLAbVDQU1U9DiLVVua3BasnIku5Rx4XcLnqCaokCiWZhg

具有以下令牌标头:

<代码>{"alg": "RS256",孩子":6B138EB31A89A1A7DA7B6DF73094F323DBE78B66","typ": "JWT","x5t": "axOOsxqJoafae233MJTzI9vni2Y"}

新:

<预> <代码> eyJhbGciOiJSUzI1NiIsImtpZCI6IjZCMTM4RUIzMUE4OUExQTdEQTdCNkRGNzMwOTRGMzIzREJFNzhCNjYiLCJ0eXAiOiJhdCtqd3QiLCJ4NXQiOiJheE9Pc3hxSm9hZmFlMjMzTUpUekk5dm5pMlkifQ.RmKHRk44c6Ele-VbB8lhNsmmcvKFludaWypuBzQzYqR7AEIuLXAuZ-N4I9ooVvQLHisBJT4qA4epEK9xdtf0ELpcvfEe3Yc2dkJnKp_rjJSRuhqyNHD0hPAoxqVSWHhfaLxLiL7_17mklqLDEqwdXANnA2YCO-Q-9wqGALZorywHYucr0X9m2hYm1oVgXPitG_TAqysYVNnLCHVGZRNE7Xmug0XhkJXzQ8RpZuSHlDHFlT2cgb7psEb4NUfA8v5-Q-LyqfPDk4xJZX2ia53SoPpiJbByFgscYF4xk54SkkcB9EOxCCsR-IYHJAmyYkhGRpBVWY5xU_9qb2ioIwkzZg

带有以下标题:

<代码>{"alg": "RS256",孩子":6B138EB31A89A1A7DA7B6DF73094F323DBE78B66","typ": "at+jwt","x5t": "axOOsxqJoafae233MJTzI9vni2Y"}

我猜问题是新令牌中的 "typ""at+jwt"?这意味着什么?我查看了 IdentityServers 版本、Github 问题、谷歌搜索、搜索 stackoverflow,但似乎没有人注意到神秘的新 "at+jwt" "typ".

这可能是导致问题的原因吗?如何指示我的新版本发布标准 JWT?这个奇怪的at+jwt是什么?

解决方案

感谢@Ruard van Elburg 在评论中链接到显式类型标记.

将默认的at+jwt"改为jwt"解决了这个问题:

var idSrvBuilder = services.AddIdentityServer(opts =>{opts.Events.RaiseErrorEvents = true;opts.Events.RaiseFailureEvents = true;opts.Events.RaiseInformationEvents = true;opts.Events.RaiseSuccessEvents = true;opts.AccessTokenJwtType = "jwt";如果 (_env.IsProduction()){opts.PublicOrigin = Configuration["Globals:IdentityURL"];}});

我猜测根本问题在于我们在该 API 中使用的包 IdentityServer3.AccessTokenValidation 无法识别 at+jwt.我们正在使用它,以便我们可以潜在地支持引用标记.

我们也无法将此 API 升级到 ASP Core 并使用来自 Microsoft 的较新的 IdentityServerAuthenticationExtensions,因为我们需要支持来自第三方的某些依赖项.该软件包似乎能够很好地处理 at+jwt.

还是不行.查看了 Ruard 链接到的 Github 问题.

原来我还必须打开 EmitLegacyResourceAudienceClaim 所以它看起来不像这样:

var idSrvBuilder = services.AddIdentityServer(opts =>{opts.Events.RaiseErrorEvents = true;opts.Events.RaiseFailureEvents = true;opts.Events.RaiseInformationEvents = true;opts.Events.RaiseSuccessEvents = true;opts.AccessTokenJwtType = "JWT";opts.EmitLegacyResourceAudienceClaim = true;如果 (_env.IsProduction()){opts.PublicOrigin = Configuration["Globals:IdentityURL"];}})

We encountered an error while upgrading IdentityServer4 (2.5.3 - 3.1.0) to Core 3.1 (from 2.2). Suddenly tokens that are issued doesn't have the correct signature. We haven't changed the signing algorithm; still using the same .PFX-certificate between versions.

var idSrvBuilder = services.AddIdentityServer(opts =>
            {
                opts.Events.RaiseErrorEvents = true;
                opts.Events.RaiseFailureEvents = true;
                opts.Events.RaiseInformationEvents = true;
                opts.Events.RaiseSuccessEvents = true;
                if (_env.IsProduction())
                {
                    opts.PublicOrigin = Configuration["Globals:IdentityURL"];
                }
            }).AddSigningCredential(new X509Certificate2(Configuration["Cert:Path"], Configuration["Cert:Password"]));

When using the OWIN middleware "UseIdentityServerBearerTokenAuthentication" for an older API it fails if ValidationMode is Local but not if it's validating directly against the IdentityServer (with ValidationMode ValidationEndpoint). The API will only return "Unauthorized" but works with the older token (same certificate signing them!)

app.UseIdentityServerBearerTokenAuthentication(new IdentityServer3.AccessTokenValidation.IdentityServerBearerTokenAuthenticationOptions
            {
                Authority = AppSettings.Authority,
                ClientId = AppSettings.ApiName,
                ClientSecret = AppSettings.ApiSecret,
                EnableValidationResultCache = false,
                ValidationMode = IdentityServer3.AccessTokenValidation.ValidationMode.Local
            });

Looking at the token issued between versions there's a glaring difference:

Old (removed payload):

eyJhbGciOiJSUzI1NiIsImtpZCI6IjZCMTM4RUIzMUE4OUExQTdEQTdCNkRGNzMwOTRGMzIzREJFNzhCNjYiLCJ0eXAiOiJKV1QiLCJ4NXQiOiJheE9Pc3hxSm9hZmFlMjMzTUpUekk5dm5pMlkifQ.U3unxhW6act8fQLCLAYBJAZ-lIMiKaghVEUdA3b7iM0mI0UqGmYgYw05SvVXTAT8ZNQPuq0D-97d0Z6VVBC2wH7VAl0daF6sYJyuSUEtDiBPttNQ9MsGBNjcN1HABZ0nv-z_lgG2Z9sgp4blCvc7N8xOsja-kuk6m06I7iOfS7O_YKPtTAXA10OCzdtiJbhYijeTFsBJaWf5-J3XJCtqpp-MGXCboE0gQIlvysKz5_CRaaKYptczw-cTX3sgRIhfWn2VxVujhH7JKeSJan52X-fQ4T47PWuVcWNOrcWheeLAbVDQU1U9DiLVVua3BasnIku5Rx4XcLnqCaokCiWZhg

With the following token header:

{
  "alg": "RS256",
  "kid": "6B138EB31A89A1A7DA7B6DF73094F323DBE78B66",
  "typ": "JWT",
  "x5t": "axOOsxqJoafae233MJTzI9vni2Y"
}

New:

eyJhbGciOiJSUzI1NiIsImtpZCI6IjZCMTM4RUIzMUE4OUExQTdEQTdCNkRGNzMwOTRGMzIzREJFNzhCNjYiLCJ0eXAiOiJhdCtqd3QiLCJ4NXQiOiJheE9Pc3hxSm9hZmFlMjMzTUpUekk5dm5pMlkifQ.RmKHRk44c6Ele-VbB8lhNsmmcvKFludaWypuBzQzYqR7AEIuLXAuZ-N4I9ooVvQLHisBJT4qA4epEK9xdtf0ELpcvfEe3Yc2dkJnKp_rjJSRuhqyNHD0hPAoxqVSWHhfaLxLiL7_17mklqLDEqwdXANnA2YCO-Q-9wqGALZorywHYucr0X9m2hYm1oVgXPitG_TAqysYVNnLCHVGZRNE7Xmug0XhkJXzQ8RpZuSHlDHFlT2cgb7psEb4NUfA8v5-q-LyqfPDk4xJZX2ia53SoPpiJbByFgscYF4xk54SkkcB9EOxCCsR-IYHJAmyYkhGRpBVWY5xU_9qb2ioIwkzZg

With the following header:

{
  "alg": "RS256",
  "kid": "6B138EB31A89A1A7DA7B6DF73094F323DBE78B66",
  "typ": "at+jwt",
  "x5t": "axOOsxqJoafae233MJTzI9vni2Y"
}

I'm guessing the issue is that "typ" from the new token is "at+jwt"? What does that mean? I've looked at IdentityServers releases, Github issues, googled, searched stackoverflow but no one seems to have noticed the mysterious new "at+jwt" "typ".

Could that be causing the issue? How can I instruct my new version to issue a standard JWT? And what is this strange at+jwt?

解决方案

Thanks to @Ruard van Elburg in the comments for linking to explicit typed tokens.

Changing the default "at+jwt" to just "jwt" solved the issue:

var idSrvBuilder = services.AddIdentityServer(opts =>
            {
                opts.Events.RaiseErrorEvents = true;
                opts.Events.RaiseFailureEvents = true;
                opts.Events.RaiseInformationEvents = true;
                opts.Events.RaiseSuccessEvents = true;
                opts.AccessTokenJwtType = "jwt";
                if (_env.IsProduction())
                {
                    opts.PublicOrigin = Configuration["Globals:IdentityURL"];
                }
            });

I'm guessing the underlying issue is with the package IdentityServer3.AccessTokenValidation we're using in that API not being able to recognize at+jwt. We're using that so that we can potentielly support reference tokens.

We also can't upgrade this API to ASP Core and use the newer IdentityServerAuthenticationExtensions from Microsoft due to some depedencies from third parties we need to support. That package does seem to be able to handle at+jwt just fine.

EDIT:

Still didn't work. Had a look at the Github issue that Ruard linked to.

Turns out I also had to turn on EmitLegacyResourceAudienceClaim so not it looks like this:

var idSrvBuilder = services.AddIdentityServer(opts =>
            {
                opts.Events.RaiseErrorEvents = true;
                opts.Events.RaiseFailureEvents = true;
                opts.Events.RaiseInformationEvents = true;
                opts.Events.RaiseSuccessEvents = true;
                opts.AccessTokenJwtType = "JWT";
                opts.EmitLegacyResourceAudienceClaim = true;
                if (_env.IsProduction())
                {
                    opts.PublicOrigin = Configuration["Globals:IdentityURL"];
                }
            })

这篇关于将 IdentityServer4 升级到 Core 3.1 - 令牌突然没有正确签名?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆