- android - 多次调用 OnPrimaryClipChangedListener
- android - 无法更新 RecyclerView 中的 TextView 字段
- android.database.CursorIndexOutOfBoundsException : Index 0 requested, 光标大小为 0
- android - 使用 AppCompat 时,我们是否需要明确指定其 UI 组件(Spinner、EditText)颜色
我正在使用 jose
进行 python jwe 加密。
这是我的示例代码
import jose
from time import time
from Crypto.PublicKey import RSA
key = RSA.generate(2048)
claims = {'name': 'Jack'}
pub_jwk = {'k': key.publickey().exportKey('PEM')}
jwe = jose.encrypt(claims, pub_jwk)
jwt = jose.serialize_compact(jwe)
这里jwt的值为二进制字符串
b'eyJlbmMiOiAiQTEyOENCQy1IUzI1NiIsICJhbGciOiAiUlNBLU9BRVAiLCAiX192IjogMn0.N1RFIEaRIGxCgSkT8HhQI4bO66XOL2RVfn4tMu8BBfGBO79AFKzHUYIRuVqpBX9YcUrsn66n3ccH5O2HO-CuCEPZ6EBM47IBUW1NAdFnm4uc3_X3EAngGTe2hnkLp0RzByYUcaLp2bMn7TWptRmvDGrADaI3uliZCV_ahLeWWFySFjIm_LaLBUzH1okZ-uPqvKQRXDEsdmBSTH5KlsQZHOdRa6uZz_iILmZY6Pp-9XtOSldTLiGasIA_9DNfljP5UtImOhAax_piA7hHeacGAtBNZJVZCWZZajLI6HKz5hVs4aZy7I2EIK6ogL0ubBNMeCQ0dZ70SWjvBTcTbtV2jw.65XaQ1rCSIn25Gc73CJe0g.oo81kAasMwPTISH5XEnnY5Mym3PPXMVs-FtYwgboHUE.5TR5Au7A7JYU7x0iYoPhGQ'
当我用相同的 jwt
值解密时,它会给出准确的结果。
enc = jose.decrypt(jose.deserialize_compact(jwt), priv_jwk)
这里当我尝试制作加密值的json
data = {'jwt': jwt}
json.dumps(data)
它给我错误 Object of type 'bytes' is not JSON serializable
我可以像这样解码加密:
jwt = jose.serialize_compact(jwe)
但是用这个加密值解密会报错。我不想在解密过程中对 jwt
进行编码。
无论如何我可以在加密时得到 string
而不是 byte
以便我可以将它转储到 JSON。
最佳答案
首先,Demonware/JOSE 项目最初是为 Python 2 编写的,您可能正在使用 Python 3 branch .有unresolved issues with the implementation ,对我来说,这说明包作者实际上并没有很好地理解这个问题。 JWT token 在其紧凑的序列化中只是一系列与 .
字符连接的 URL 安全 Base64 字符串。
无论何时加密或签署新 token ,都必须将字节解码为字符串(只需将字节值解码为 ASCII)。验证或解密时,需要将字符串重新编码为字节。
例如要在 JSON 对象中编码 jwt
值,您需要解码:
data = {'jwt': jwt.decode('ascii')}
Javascript Web Token (JWT) 的全部意义在于以文本形式与另一方进行交换。该库通过声明该方法返回一个字符串来复合问题。
您可以使用默认的 utf-8
编解码器来缩短它,因为 ASCII 是 UTF-8 的子集:
data = {'jwt': jwt.decode()}
在相反的方向上,您必须再次将紧凑字符串编码为字节:
data = json.loads(json_document)
jose.decrypt(jose.deserialize_compact(data['jwt'].encode()), priv_jwk)
但你基本上使用的是过时的软件; Demonware/jose project 3年没更新了。它还依赖于过时的、无人维护的 pycrypto 包。您不想使用。
相反,看看 Authlib或 JWCrypto ,两个 积极维护 的模块,并使用 cryptography
project处理棘手的密码学原语(还有 pyjwt
和 python-jose
,但这些项目(尚)不支持 JWE 加密,仅支持 JWS 签名 token )。
其中,Authlib 提供了迄今为止最干净、最清晰的 API。例如。要使用 Demonware/JOSE 选择的默认加密和签名算法,使用 Authlib 生成公钥/私钥对并创建加密 token ,您需要执行以下操作:
from authlib.jose import jwt
from cryptography.hazmat.backends import default_backend
from cryptography.hazmat.primitives import serialization
from cryptography.hazmat.primitives.asymmetric import rsa
# generate a private key with corresponding public key, then
# export the keys as a PEM serializations.
private_key = rsa.generate_private_key(
public_exponent=65537,
key_size=2048,
backend=default_backend()
)
private_key_pem = private_key.private_bytes(
serialization.Encoding.PEM,
serialization.PrivateFormat.PKCS8,
serialization.NoEncryption()
)
public_key = private_key.public_key()
public_key_pem = public_key.public_bytes(
serialization.Encoding.PEM,
serialization.PublicFormat.SubjectPublicKeyInfo
)
# create an encrypted token (JWT using JWE)
claims = {'name': 'Jack'}
header = {'enc': 'A128CBC-HS256', 'alg': 'RSA-OAEP'}
token = jwt.encode(header, claims, public_key_pem).decode()
# decrypt the token again
claims_from_token = jwt.decode(token.encode(), private_key_pem)
请注意,Authlib 也会在此处返回一个 bytes
值,因此如果您想进一步将其嵌入 JSON 并将 token 数据从 JSON 有效负载传回,您也必须对其进行解码和编码到 jwt.decode()
方法。
在 JWCrypto 中使用相同的公钥和私钥序列化:
import json
from jwcrypto import jwt, jwk
# Create a JWK key object from the private key
jwk_key = jwk.JWK.from_pem(private_key_pem)
# create a JWT() instance to handle ecryption and serialization
header = {'enc': 'A128CBC-HS256', 'alg': 'RSA-OAEP'}
jwt_token = jwt.JWT(claims, header)
jwt_token.make_encrypted_token(jwk_key)
token = jwt_token.serialize()
# deserialize again, using a new JWT instance but with different arguments;
# Yes, this is a confusing API.
# it's always a good idea to limit what algorithms you'll accept
# note that this is a list of both *signing* and *encryption* algorithms, not
# the possible values of the "alg" key in a JOSE header.
jwt_token = jwt.JWT(key=jwk_key, jwt=token, algs=['A128CBC-HS256', 'RSA-OAEP'])
claims_from_token = json.loads(jwt_token.claims)
请注意,此库在序列化时会返回一个字符串,但您必须手动对声明进行 JSON 解码。 API 还将序列化和反序列化混合到一个类中,创建了一个非常困惑的参数、方法和属性组合。
关于python - jose 加密返回二进制字符串,但用解码后的字符串解密会在 python 中出错,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/58545757/
按照目前的情况,这个问题不适合我们的问答形式。我们希望答案得到事实、引用或专业知识的支持,但这个问题可能会引发辩论、争论、投票或扩展讨论。如果您觉得这个问题可以改进并可能重新打开,visit the
在编码时,我问了自己这个问题: 这样更快吗: if(false) return true; else return false; 比这个? if(false) return true; return
如何在逻辑条件下进行“返回”? 在这样的情况下这会很有用 checkConfig() || return false; var iNeedThis=doSomething() || return fa
这是我的正则表达式 demo 如问题所述: 如果第一个数字是 1 则返回 1 但如果是 145 则返回 145 但如果是 133 则返回 133 样本数据a: K'8134567 K'81345678
在代码高尔夫问答部分查看谜题和答案时,我遇到了 this solution返回 1 的最长和最晦涩的方法 引用答案, int foo(void) { return! 0; } int bar(
我想在下面返回 JSON。 { "name": "jackie" } postman 给我错误。说明 Unexpected 'n' 这里是 Spring Boot 的新手。 1日龄。有没有正确的方法来
只要“is”返回 True,“==”不应该返回 True 吗? In [101]: np.NAN is np.nan is np.NaN Out[101]: True In [102]: np.NAN
我需要获取所有在 6 号或 7 号房间或根本不在任何房间的学生的详细信息。如果他们在其他房间,简单地说,我不希望有那个记录。 我的架构是: students(roll_no, name,class,.
我有一个表单,我将它发送到 php 以通过 ajax 插入到 mysql 数据库中。一切顺利,php 返回 "true" 值,但在 ajax 中它显示 false 消息。 在这里你可以查看php代码:
我在 Kotlin 中遇到了一个非常奇怪的无法解释的值比较问题,以下代码打印 假 data class Foo ( val a: Byte ) fun main() { val NUM
请注意,这并非特定于 Protractor。问题在于 Angular 2 的内置 Testability service Protractor 碰巧使用。 Protractor 调用 Testabil
在调试窗口中,以下表达式均返回 1。 Application.WorksheetFunction.CountA(Cells(4 + (i - 1) * rows_per_record, 28) & "
我在本地使用 jsonplaceholder ( http://jsonplaceholder.typicode.com/)。我正在通过 extjs rest 代理测试我的 GET 和 POST 调用
这是 Postman 为成功调用我的页面而提供的(修改后的)代码段。 var client = new RestClient("http://sub.example.com/wp-json/wp/v2
这个问题在这里已经有了答案: What to do with mysqli problems? Errors like mysqli_fetch_array(): Argument #1 must
我想我对 C 命令行参数有点生疏。我查看了我的一些旧代码,但无论这个版本是什么,都会出现段错误。 运行方式是 ./foo -n num(其中 num 是用户在命令行中输入的数字) 但不知何故它不起作用
我已经编写了一个类来处理命名管道连接,如果我创建了一个实例,关闭它,然后尝试创建另一个实例,调用 CreateFile() 返回 INVALID_HANDLE_VALUE,并且 GetLastErro
即使 is_writable() 返回 true,我也无法写入文件。当然,该文件存在并且显然是可读的。这是代码: $file = "data"; echo file_get_contents($fil
下面代码中的变量 $response 为 NULL,尽管它应该是 SOAP 请求的值。 (潮汐列表)。当我调用 $client->__getLastResponse() 时,我从 SOAP 服务获得了
我一直在网上的不同论坛上搜索答案,但似乎没有与我的情况相符的... 我正在使用 Windows 7,VS2010。 我有一个使用定时器来调用任务栏刷新功能的应用程序。在该任务栏函数中包含对 LoadI
我是一名优秀的程序员,十分优秀!