我正在尝试使用PyCrypto来加密/解密某些字符串,而且我遇到了汉字问题。
当我尝试加密“ ni-hao ”( hello )时......
pemFile = open("/home/borrajax/keys/myKey.pem", "r")
encryptor = RSA.importKey(pemFile, passphrase="f00")
return encryptor.encrypt("你好", 0)[0]
......我一直在收到错误:
Module Crypto.PublicKey.pubkey:64 in encrypt
>> ciphertext=self._encrypt(plaintext, K)
Module Crypto.PublicKey.RSA:92 in _encrypt
>> return (self.key._encrypt(c),)
ValueError: Plaintext too large
我尝试了很多种组合,
encryptor.encrypt(u"你好"...
encryptor.encrypt(u"你好".encode("utf-8")...
没有任何运气。
我想在编码之前我总是可以尝试使用base64,但是我想把它留作“最后的资源”......我希望有一种更“优雅”的方式来做这件事。
有没有人遇到过同样的问题?任何提示将不胜感激。提前谢谢。
答案 0 :(得分:2)
首先,您应该只加密二进制数据,而不是Unicode文本。这意味着str
类型(在Python 2.x中)或bytes
(在Python 3.x和最近的Python 2.x中)。您必须在加密前对文本进行编码,并且必须在解密后对其进行解码。
其次,您要加密的字节字符串必须小于RSA模数(例如,RSA2048小于256字节)。如果您的数据较长,请考虑使用中间AES会话密钥。
第三,如果你使用PyCrypto 2.5,没有充分的理由使用RSA密钥对象的.encrypt/.decrypt
方法。使用PKCS#1方法之一更好,更安全:OAEP或v1.5。有了它们,明文必须更短。
答案 1 :(得分:1)
我在yakuake终端的交互式解释器中使用python 2.6.5上的pb在Ubuntu Linux 10.04上安装的PyCrypto v2.5进行了测试。
我无法重现您所看到的错误,尤其是“明文太大”位。我看到的一些错误:
encryptor.encrypt(u"你好",0)[0]
TypeError: argument 1 must be long, not unicode
似乎它不喜欢unicode对象 - 只想要str。
这两个都在我的设置上工作,并且都产生相同的输出,但第一个解决方案更正确:
encryptor.encrypt(u"你好".encode("utf-8"), 0)[0]
encryptor.encrypt("你好", 0)[0]
您是从交互式解释器还是从文件中尝试此操作?如果是档案,我是s the file UTF-8 encoded?如果是控制台,它是否有正确的UTF-8支持?
答案 2 :(得分:1)
我检查了PyCrypto的相关代码,只有当纯文本(转换为long)大于其中一个关键参数时才会抛出此错误。假设正确设置了脚本编码,可能是因为您的RSA密钥无效或太短。我试过这个片段,它没有问题:
rsa = RSA.generate(1024)
print(rsa.encrypt("你好", 0))