好吧,我明白我问的问题可能很明显,但不幸的是我缺乏关于这个主题的知识,这个任务对我来说似乎很棘手.
我有一个OpenID Connect Provider返回的id令牌(JWT).这里是:
eyJraWQiOiIxZTlnZGs3IiwiYWxnIjoiUlMyNTYifQ.ewogImlzcyI6ICJodHRwOi8vc2VydmVyLmV4YW1wbGUuY29tIiwKICJzdWIiOiAiMjQ4Mjg5NzYxMDAxIiwKICJhdWQiOiAiczZCaGRSa3F0MyIsCiAibm9uY2UiOiAibi0wUzZfV3pBMk1qIiwKICJleHAiOiAxMzExMjgxOTcwLAogImlhdCI6IDEzMTEyODA5NzAsCiAiY19oYXNoIjogIkxEa3RLZG9RYWszUGswY25YeENsdEEiCn0.XW6uhdrkBgcGx6zVIrCiROpWURs-4goO1sKA4m9jhJIImiGg5muPUcNegx6sSv43c5DSn37sxCRrDZZm4ZPBKKgtYASMcE20SDgvYJdJS0cyuFw7Ijp_7WnIjcrl6B5cmoM6ylCvsLMwkoQAxVublMwH10oAxjzD6NEFsu9nipkszWhsPePf_rM4eMpkmCbTzume-fzZIi5VjdWGGEmzTg32h3jiex-r5WTHbj-u5HL7u_KP3rmbdYNzlzd1xWRYTUs4E8nOTgzAUwvwXkIQhOh5TPcSMBYy6X3E7-_gr9Ue6n4ND7hTFhtjYs3cjNKIA08qm5cpVYFMFMG6PkhzLQ
它的头和有效负载解码如下:
{
"kid":"1e9gdk7",
"alg":"RS256"
}.
{
"iss": "http://server.example.com",
"sub": "248289761001",
"aud": "s6BhdRkqt3",
"nonce": "n-0S6_WzA2Mj",
"exp": 1311281970,
"iat": 1311280970,
"c_hash": "LDktKdoQak3Pk0cnXxCltA"
}
Run Code Online (Sandbox Code Playgroud)
从IODC提供商的发现中,我得到了公钥(JWK):
{
"kty":"RSA",
"kid":"1e9gdk7",
"n":"w7Zdfmece8iaB0kiTY8pCtiBtzbptJmP28nSWwtdjRu0f2GFpajvWE4VhfJAjEsOcwYzay7XGN0b-X84BfC8hmCTOj2b2eHT7NsZegFPKRUQzJ9wW8ipn_aDJWMGDuB1XyqT1E7DYqjUCEOD1b4FLpy_xPn6oV_TYOfQ9fZdbE5HGxJUzekuGcOKqOQ8M7wfYHhHHLxGpQVgL0apWuP2gDDOdTtpuld4D2LK1MZK99s9gaSjRHE8JDb1Z4IGhEcEyzkxswVdPndUWzfvWBBWXWxtSUvQGBRkuy1BHOa4sP6FKjWEeeF7gm7UMs2Nm2QUgNZw6xvEDGaLk4KASdIxRQ",
"e":"AQAB"
}
Run Code Online (Sandbox Code Playgroud)
那么,问题是如何在C#中使用我所获得的RS256算法的公钥来验证这个JWT?如果有一个很好的教程明确描述这个过程,那将是很棒的.但是,如何使用它的一个例子System.IdentityModel.Tokens.Jwt
也可以正常工作.
更新:我明白,我需要做类似下面的代码,但我不知道在哪里获得用于计算SHA256哈希的" 密钥 ".
string tokenStr = "eyJraWQiOiIxZTlnZGs3IiwiYWxnIjoiUlMyNTYifQ.ewogImlzcyI6ICJodHRwOi8vc2VydmVyLmV4YW1wbGUuY29tIiwKICJzdWIiOiAiMjQ4Mjg5NzYxMDAxIiwKICJhdWQiOiAiczZCaGRSa3F0MyIsCiAibm9uY2UiOiAibi0wUzZfV3pBMk1qIiwKICJleHAiOiAxMzExMjgxOTcwLAogImlhdCI6IDEzMTEyODA5NzAsCiAiY19oYXNoIjogIkxEa3RLZG9RYWszUGswY25YeENsdEEiCn0.XW6uhdrkBgcGx6zVIrCiROpWURs-4goO1sKA4m9jhJIImiGg5muPUcNegx6sSv43c5DSn37sxCRrDZZm4ZPBKKgtYASMcE20SDgvYJdJS0cyuFw7Ijp_7WnIjcrl6B5cmoM6ylCvsLMwkoQAxVublMwH10oAxjzD6NEFsu9nipkszWhsPePf_rM4eMpkmCbTzume-fzZIi5VjdWGGEmzTg32h3jiex-r5WTHbj-u5HL7u_KP3rmbdYNzlzd1xWRYTUs4E8nOTgzAUwvwXkIQhOh5TPcSMBYy6X3E7-_gr9Ue6n4ND7hTFhtjYs3cjNKIA08qm5cpVYFMFMG6PkhzLQ";
string[] tokenParts = tokenStr.Split('.');
RSACryptoServiceProvider rsa = new RSACryptoServiceProvider();
rsa.ImportParameters(
new RSAParameters() {
Modulus = FromBase64Url("w7Zdfmece8iaB0kiTY8pCtiBtzbptJmP28nSWwtdjRu0f2GFpajvWE4VhfJAjEsOcwYzay7XGN0b-X84BfC8hmCTOj2b2eHT7NsZegFPKRUQzJ9wW8ipn_aDJWMGDuB1XyqT1E7DYqjUCEOD1b4FLpy_xPn6oV_TYOfQ9fZdbE5HGxJUzekuGcOKqOQ8M7wfYHhHHLxGpQVgL0apWuP2gDDOdTtpuld4D2LK1MZK99s9gaSjRHE8JDb1Z4IGhEcEyzkxswVdPndUWzfvWBBWXWxtSUvQGBRkuy1BHOa4sP6FKjWEeeF7gm7UMs2Nm2QUgNZw6xvEDGaLk4KASdIxRQ"),
Exponent = FromBase64Url("AQAB")
});
HMACSHA256 sha = new HMACSHA256(key);
byte[] hash = sha.ComputeHash(Encoding.UTF8.GetBytes(tokenParts[0] + '.' + tokenParts[1]));
byte[] signature = rsa.Encrypt(hash, …
Run Code Online (Sandbox Code Playgroud) JOSE、JWA、JWE、JWK、JWS 和 JWT 之间有什么区别?它们之间有何关系?
我正在阅读有关 JWKS 的信息,并找到有关密钥轮换概念的信息 - https://developer.okta.com/docs/concepts/key-rotation/
假设我在应用程序中使用 JWKS,但我不会定期获取它们,因此只是硬编码。单键 JSON 对象看起来像
{
"kty": "RSA",
"e": "xxx",
"use": "sig",
"kid": "xxx",
"x5t": "xx",
"x5c": [
"xxx"
],
"n": "xxx
}
Run Code Online (Sandbox Code Playgroud)
JWKS 为您提供公钥,以便您可以验证 JWT。现在提问。
请考虑上面的示例,因此我在应用程序中有密钥,并且想知道何时应该更换它们。
当然,我知道这是不好的做法(我应该直接从 JWKS 端点获取密钥并感到安全),但这只是一个示例(如果这是一个愚蠢的示例,请提出一个更好的示例来描述上下文)。
"e": "AQAB"
JWKS - Json Web 密钥集是什么意思
{
"keys": [
{
"kty": "RSA", #key type
"e": "AQAB", #Question - what does "e" mean or stand for. And what values can e take. What is AQAB here.
"use": "sig", #verify client assertion signature. This means what is the use of the key. Answer - to verify signature. Right?
"kid": "somebase64encodestring", #key id
"alg": "RS256", #key algoritham. Here it is RSA.
"n": "anotherbase64encodestring" #This is the actual public key base64 encoded.
} …
Run Code Online (Sandbox Code Playgroud) 我需要生成具有以下参数的 JWK:
\n\xe2\x80\x9ckty\xe2\x80\x9d:密钥类型
\n\xe2\x80\x9ckid\xe2\x80\x9d:密钥 ID
\n\xe2\x80\x9cuse\xe2\x80\x9d:\xe2\x80\x9csig\xe2\x80\x9d 公钥使用
\n\xe2\x80\x9cn\xe2\x80\x9d:模数
\n\xe2\x80\x9ce\xe2\x80\x9d: \xe2\x80\x9cAQAB\xe2\x80\x9d 公共指数
\n\xe2\x80\x9cx5c\xe2\x80\x9d:X.509 证书链
\n\xe2\x80\x9cx5t\xe2\x80\x9d:X.509 证书 SHA-1 指纹
\n笔记:
\nJWK 应包含使用 RSA 算法的公钥。RSA 提供用于密钥匹配目的的密钥 ID。
\n应包含使用 \xe2\x80\x9cx5t\xe2\x80\x9d (X.509 SHA-1 指纹)和 \xe2\x80\x9cx5c\xe2\x80\x9d (X.509\n证书链)的 X.509 证书参数
\n前 5 个参数(“kty”、“kid”、“use”、“n”、“e”)相当简单,不是问题。但是,对于“x5c”和“x5t”组件,我不确定如何生成它们。看来我可以使用https://www.samltool.com/self_signed_certs.php上找到的工具创建 x509 证书,我想生成的 x509 证书将包含 x5c 参数。这是正确的吗?我如何从中生成 x5t(证书指纹)?
\n感谢所有帮助。
\nRFC中有一个RSA密钥:
https://tools.ietf.org/html/rfc7516#appendix-A.1
{"kty":"RSA",
"n":"oahUIoWw0K0usKNuOR6H4wkf4oBUXHTxRvgb48E-BVvxkeDNjbC4he8rUW
cJoZmds2h7M70imEVhRU5djINXtqllXI4DFqcI1DgjT9LewND8MW2Krf3S
psk_ZkoFnilakGygTwpZ3uesH-PFABNIUYpOiN15dsQRkgr0vEhxN92i2a
sbOenSZeyaxziK72UwxrrKoExv6kc5twXTq4h-QChLOln0_mtUZwfsRaMS
tPs6mS6XrgxnxbWhojf663tuEQueGC-FCMfra36C9knDFGzKsNa7LZK2dj
YgyD3JR_MB_4NUJW_TqOQtwHYbxevoJArm-L5StowjzGy-_bq6Gw",
"e":"AQAB",
"d":"kLdtIj6GbDks_ApCSTYQtelcNttlKiOyPzMrXHeI-yk1F7-kpDxY4-WY5N
WV5KntaEeXS1j82E375xxhWMHXyvjYecPT9fpwR_M9gV8n9Hrh2anTpTD9
3Dt62ypW3yDsJzBnTnrYu1iwWRgBKrEYY46qAZIrA2xAwnm2X7uGR1hghk
qDp0Vqj3kbSCz1XyfCs6_LehBwtxHIyh8Ripy40p24moOAbgxVw3rxT_vl
t3UVe4WO3JkJOzlpUf-KTVI2Ptgm-dARxTEtE-id-4OJr0h-K-VFs3VSnd
VTIznSxfyrj8ILL6MG_Uv8YAu7VILSB3lOW085-4qE3DzgrTjgyQ",
"p":"1r52Xk46c-LsfB5P442p7atdPUrxQSy4mti_tZI3Mgf2EuFVbUoDBvaRQ-
SWxkbkmoEzL7JXroSBjSrK3YIQgYdMgyAEPTPjXv_hI2_1eTSPVZfzL0lf
fNn03IXqWF5MDFuoUYE0hzb2vhrlN_rKrbfDIwUbTrjjgieRbwC6Cl0",
"q":"wLb35x7hmQWZsWJmB_vle87ihgZ19S8lBEROLIsZG4ayZVe9Hi9gDVCOBm
UDdaDYVTSNx_8Fyw1YYa9XGrGnDew00J28cRUoeBB_jKI1oma0Orv1T9aX
IWxKwd4gvxFImOWr3QRL9KEBRzk2RatUBnmDZJTIAfwTs0g68UZHvtc",
"dp":"ZK-YwE7diUh0qR1tR7w8WHtolDx3MZ_OTowiFvgfeQ3SiresXjm9gZ5KL
hMXvo-uz-KUJWDxS5pFQ_M0evdo1dKiRTjVw_x4NyqyXPM5nULPkcpU827
rnpZzAJKpdhWAgqrXGKAECQH0Xt4taznjnd_zVpAmZZq60WPMBMfKcuE",
"dq":"Dq0gfgJ1DdFGXiLvQEZnuKEN0UUmsJBxkjydc3j4ZYdBiMRAy86x0vHCj
ywcMlYYg4yoC4YZa9hNVcsjqA3FeiL19rk8g6Qn29Tt0cj8qqyFpz9vNDB
UfCAiJVeESOjJDZPYHdHY8v1b-o-Z2X5tvLx-TCekf7oxyeKDUqKWjis",
"qi":"VIMpMYbPf47dT1w_zDUXfPimsSegnMOA1zTaX7aGk_8urY6R8-ZW1FxU7
AlWAyLWybqq6t16VFd7hQd0y6flUK4SlOydB61gwanOsXGOAOv82cHq0E3
eL4HrtZkUuKvnPrMnsUUFlfUdybVzxyjz9JF_XyaY14ardLSjf4L_FNY"
}
Run Code Online (Sandbox Code Playgroud)
我试过了jwk-to-pem
:
-----BEGIN RSA PUBLIC KEY-----
MIIBCgKCAQEAoahUIoWw0K0usKNuOR6H4wkf4oBUXHTxRvgb48E+BVvxkeDNjbC4
he8rUWcJoZmds2h7M70imEVhRU5djINXtqllXI4DFqcI1DgjT9LewND8MW2Krf3S
psk/ZkoFnilakGygTwpZ3uesH+PFABNIUYpOiN15dsQRkgr0vEhxN92i2asbOenS
ZeyaxziK72UwxrrKoExv6kc5twXTq4h+QChLOln0/mtUZwfsRaMStPs6mS6Xrgxn
xbWhojf663tuEQueGC+FCMfra36C9knDFGzKsNa7LZK2djYgyD3JR/MB/4NUJW/T
qOQtwHYbxevoJArm+L5StowjzGy+/bq6GwIDAQAB
-----END RSA PUBLIC KEY-----
Run Code Online (Sandbox Code Playgroud)
还必须用"PUBLIC KEY"替换"RSA PUBLIC KEY".
该命令openssl rsa -inform PEM -pubin
给出:
unable to load Public Key
139911798556312:error:0D0680A8:asn1 encoding routines:ASN1_CHECK_TLEN:wrong tag:tasn_dec.c:1197:
139911798556312:error:0D07803A:asn1 encoding routines:ASN1_ITEM_EX_D2I:nested asn1 error:tasn_dec.c:374:Type=X509_ALGOR
139911798556312:error:0D08303A:asn1 encoding routines:ASN1_TEMPLATE_NOEXP_D2I:nested asn1 error:tasn_dec.c:697:Field=algor, …
Run Code Online (Sandbox Code Playgroud) 每个OpenID Connect提供程序都会发布包含jwks_uri
属性的发现文档.从这里返回的数据jwks_uri
似乎有两种不同的形式.一个表单包含名为x5c
和的字段x5t
.这样的一个例子如下:
{
"keys": [
{
"kty": "RSA",
"use": "sig",
"kid": "C61F8F2524D080D0DB0A508747A94C2161DEDAC8",
"x5t": "xh-PJSTQgNDbClCHR6lMIWHe2sg", <------ HERE
"e": "AQAB",
"n": "lueb...",
"x5c": [
"MIIC/..." <------ HERE
],
"alg": "RS256"
}
]
}
Run Code Online (Sandbox Code Playgroud)
我看到的另一个版本省略了x5c和x5t属性但包含e
和n
.一个例子是:
{
"keys": [
{
"kty": "RSA",
"alg": "RS256",
"use": "sig",
"kid": "cb11e2f233aee0329a5344570349cddb6b8ff252",
"n": "sJ46h...", <------ HERE
"e": "AQAB" <------ HERE
}
]
}
Run Code Online (Sandbox Code Playgroud)
我不太明白区别是什么,为什么有时会使用x5c/x5t
组合,但有时候只是简单e/n
.我正在使用C#Microsoft.IdentityModel.Tokens.TokenValidationParameters
,我正在试图找出如何供应该物业IssuerSigningKey
.此类的示例用法是
new TokenValidationParameters
{
ValidateAudience …
Run Code Online (Sandbox Code Playgroud) 我需要使用 C# 生成 JSON Web Key (jwk),如图所示。我已经阅读了几篇文章,但也有其他语言(例如 Java)的实现,并且有第三方库(Nimbus JOSE+JWT 库等)。您能帮我用 C# 生成 JSON Web Key 吗?
{
"e": "AQAB",
"n": "nZD7QWmIwj-3N_RZ1qJjX6CdibU87y2l02yMay4KunambalP9g0fU9yZLwLX9WYJINcXZDUf6QeZ-SSbblET-h8Q4OvfSQ7iuu0WqcvBGy8M0qoZ7I-NiChw8dyybMJHgpiP_AyxpCQnp3bQ6829kb3fopbb4cAkOilwVRBYPhRLboXma0cwcllJHPLvMp1oGa7Ad8osmmJhXhM9qdFFASg_OCQdPnYVzp8gOFeOGwlXfSFEgt5vgeU25E-ycUOREcnP7BnMUk7wpwYqlE537LWGOV5z_1Dqcqc9LmN-z4HmNV7b23QZW4_mzKIOY4IqjmnUGgLU9ycFj5YGDCts7Q",
"alg": "RS256",
"kid": "8f796169-0ac4-48a3-a202-fa4f3d814fcd",
"kty": "RSA",
"use": "sig"
}
Run Code Online (Sandbox Code Playgroud) 我正在开发一个应用程序,其中所有 API 都受 OAuth 保护。我已从客户端收到访问令牌,但无法解码和验证令牌。
我有以下格式的 JWK
{
"keys": [
{
"kty": "RSA",
"x5t#S256": "Some value",
"e": "Some Value",
"x5t": "Some Value",
"kid": "SIGNING_KEY",
"x5c": [
"Some Value"
],
"key_ops": [
"verify",
"encrypt"
],
"alg": "RS256",
"n": "Some Value"
}
]
}
Run Code Online (Sandbox Code Playgroud)
如何在Python中使用上述JWK解码JWT令牌?
所以我在 .net Core angular 应用程序中使用 Cognito(使用 amazon-javascript-sdk),我试图验证我在 .net core 后端从亚马逊获得的 access_token,以便我可以保护我的 Web Api . 使用 Amazon cognito JWKS 我能够验证 access_token 并因此允许/拒绝访问我的 api。问题是我现在在我的 startup.cs 中硬编码了 JWK 密钥。我从 JWKS 了解到的是,这些密钥可以轮换(没有发现亚马逊是否这样做),所以我想以某种方式告诉我的中间件从端点获取密钥。我阅读了一些有关发现文档和其他内容的内容,但找不到有关如何配置中间件以自动执行此操作的任何内容。
对于 OpenId,您可以使用 MetadataAddress 指向https://cognito-idp .{awsregion}.amazonaws.com/{userPool}/.well-known/openid-configuration,这将获得所有必要的配置。如果您使用 JwtBearer 中间件,我觉得 IssuerSigningKey(JWK) 应该存在类似的东西。我希望指向 JWK url,而不是设置一个硬编码的密钥,中间件将在其中找到密钥并执行它的魔法。JWKS 还包含多个密钥,因此我希望中间件自行确定要使用哪个密钥。
相关代码:
services.AddAuthentication(options =>
{
options.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme;
options.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme;
})
.AddJwtBearer(jwt =>
{
jwt.TokenValidationParameters = new TokenValidationParameters
{
IssuerSigningKey = MagicFunction("hardcodedRSAModules","hardcodedRSA")
ValidIssuer = "https://cognito-idp.us-east-2.amazonaws.com/{userpool}",
ValidateIssuerSigningKey = true,
ValidateIssuer = true,
ValidateLifetime = true,
ValidateAudience = false,
ClockSkew = …
Run Code Online (Sandbox Code Playgroud)