我遇到了以下情况。我有一个公开密钥集的 JWKS。但是,我想确保密钥不会在传输过程中被中间人修改。 我没有看到任何对此的支持。
当然,我可以随意向
keys
元素旁边的 JSON 元素添加签名。通过使用证书的私钥完成此操作,外部方可以使用 PKI 来验证证书,从而验证签名,从而验证我的 JWKS 中的公钥。我可以使用 JWS(如果我不介意密钥不能直接被人类读取)或类似 JSF 的东西(但这看起来不太受支持/使用)。
但我想知道是否有什么我错过了。
我最好使用现有解决方案/可以/仍然使用该消息并自行决定是否要验证签名的东西。
有按规范提供的解决方案吗?
执行此操作的方法(在野外使用)描述于 https://www.nimbusds.com/products/server/docs/api/jwk-set#signed-keys 它使用 jwt。 因此,我可以公开一个
/jwks
端点,而不是公开类似 /jwks.jwk
的内容。
在其中,它可能看起来像这样:
{
"iss" : "https://c2id.com",
"sub" : "https://c2id.com",
"iat" : 1594030600,
"keys" : [
{
"kty" : "RSA",
"use" : "sig",
"kid" : "P9Zd",
"e" : "AQAB",
"n" : "kWp2zRA23Z3vTL4uoe8kTFptxBVFunIoP4t_8TDYJrOb7D1iZNDXVeEsYKp6ppmrTZDAgd-cNOTKLd4M39WJc5FN0maTAVKJc7NxklDeKc4dMe1BGvTZNG4MpWBo-taKULlYUu0ltYJuLzOjIrTHfarucrGoRWqM0sl3z2-fv9k"
}
]
}
这将允许客户端验证 jwt 的真实性,如果是真实的,他们就可以接受提供的密钥。
然后,
/jwks.jwk
可能需要使用 PKI 进行验证,并提供 JWKS 规范中所述的证书链:
https://www.rfc-editor.org/rfc/rfc7515#section-4.1.6
这将具有以下示例标题:
kid: '-1614245140',
x5t: 'lDdNIsb3FxulMcYdAXxYJ_Z5950', <-- the thumbprint of the certificate used for this signing (should be the last in the x5c)
x5c: [ <-- the certificate chain, starting with the root
'MIIDqjCCApKgAwIBAgIESLNEvDA ...', <-- the root certificate
'MIICwzCCAasCCQCKVy9eKjvi+jA ...', <-- the intermediary certificate
'MIIDTDCCAjSgAwIBAgIJAPlnQYH...' <-- the subject certificate (i.e. the one in the application, e.g. 'oam-jwks'
],
alg: 'RS256' <-- the algorithm used
}
然后,客户端可以使用证书链来验证用于签名的证书的真实性,使用该证书来验证 jwk 的真实性,然后愉快地使用提供的密钥集。