【问题标题】:Python cryptography Fernet.generate_key() key lengthPython 密码学 Fernet.generate_key() 密钥长度
【发布时间】:2021-02-04 01:54:16
【问题描述】:

我对密码学不太了解,但是当我在 python 中使用密码学库并尝试生成密钥时,密钥长度在 32 以上

from cryptography.fernet import Fernet
import base64

key = Fernet.generate_key()
>>>x2pXHXqCcUGjcq4HTcvdqH5xSEF_SLATO6p1Xk3tejM=

如果我使用这个密钥来解密 在线 或在 python 之外的消息,它会说密钥的最大长度是 32 我读到密码库使用 128 位密钥 CBC AES。

我不确定这是否与填充有关,我的问题是是否可以使用此密钥在 python 外部解密 Fernet 加密的消息,或者无论如何我可以获得原始的 16 字节密钥(因为它应该使用128键)

【问题讨论】:

    标签: python python-3.x cryptography python-cryptography


    【解决方案1】:

    Fernet.generate_key() 生成并由构造函数预期的密钥实际上由两个 128 位密钥组成:一个用于签名,另一个用于加密,按此顺序连接。

    来自source code

        key = base64.urlsafe_b64decode(key)
        if len(key) != 32:
            raise ValueError(
                "Fernet key must be 32 url-safe base64-encoded bytes."
            )
    
        self._signing_key = key[:16]
        self._encryption_key = key[16:]
    

    感谢@PaulKehrer 更新

    这在format specification 中有描述,引用如下:

    一个fernet key是以下字段的base64url编码:

    Signing-key ‖ Encryption-key
    
    • 签名密钥,128 位
    • 加密密钥,128 位

    使用低级库和服务解密 Fernet 消息需要手动解析 token format

    • Fernet 生成 url-safe base64
    • 除了数据,令牌还包含版本、时间戳、IV 和 HMAC

    【讨论】:

    • spec 实际上明确记录了这种密钥格式。
    • 嗨,我仍然面临输入长度的问题(解密的消息)它说“使用填充密码解密时输入长度必须是 16 的倍数”网站,如link 示例:fernet 密钥: b'pZoloqJuKowAd3JsAtecK5ZkGpx4vaxIwyFU3TWTWzE=' 加密: b'gAAAAABgHcCJe6tuM-a2aMY8eah35eY2GzhVcOl4zi0wgQ8EGcP-V4f7ItIBbs8JHpins1TzDO32DaUTDA-xms_1WEM5tR=d
    • @anewuser 使用第三方服务几乎没有问题。首先,fernet 产生一个url-safe base64,它可以被其他库拒绝。其次,您仍在传递整个 32 字节的 fernet 密钥,其中需要 16 字节的密钥。最后,Fernet 加密的输出除了密文外,还包含版本、时间戳、IV 和 HMAC(参见spec)。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2015-02-16
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多