aes从django加密和解密

2nc8po8w  于 2021-06-21  发布在  Mysql
关注(0)|答案(1)|浏览(837)

在我的django应用程序中,我想使用 AES_ENCRYPT 以及 AES_DECRYPT 从mysql数据库加密和解密的东西。
我知道python的crypto包支持aes,但是crypto-aes不会产生与mysql-aes相同的结果,尽管我确保两者都使用ecb模式。
所以,现在我要做的是:

sql = "select 1 as id, AES_ENCRYPT(my_field, '16-bytes encryption key') as field_enc from appname_table"
encrypted_fields = MyModel.objects.raw(sql)

这让我得到加密后的字段值,它的工作正常。问题是aes算法加密最终结果有许多无法打印的字符,如下所示:

encrypted_fields[3].field_enc
'\x88\xc5\xe4\xa0c?\xf8\x16|^1JB\x83{\xdf'
print(encrypted_fields[3].field_enc)
���c?�|^1JB�{�

所以,现在当我尝试使用相同的值来解密它时,mysql会返回一个错误
操作错误:(1300,“无效的utf8字符串:'\x88\xc5\xe4\xa0c'”
我想这是因为我试图向mysql查询发送不可打印的字符。
那么,我该怎么做呢?
请注意,我必须使用mysql函数,因为我使用这些函数加密了一些数据库字段,所以我需要使用相同的函数对它们进行解密,因为crypto的aes不能得到相同的结果。crypto一直要求要加密的文本必须像密钥一样有16字节长,而mysql则不要求这样。
我还试着看看mysql在加密之前是否对文本使用了某种填充,但没有说明他们在网页上填充了什么字符:
str和crypt\u str参数可以是任意长度,填充会自动添加到str中,因此它是基于块的算法(如aes)所需的块的倍数。此填充由aes_decrypt()函数自动删除

6uxekuva

6uxekuva1#

在google搜索了很多次之后,我发现了这篇关于在php中复制mysql-aes加密的博客文章。
它们的关键在于,用于填充的字符是一个ascii码等于aes块大小和文本长度之差的字符。

c = chr(16 - len(text_to_be_encrypted))
def align_str(s, n, char):
    if len(s) < n:
        diff = n - len(s)
        for i in range(diff):
            s += char
    return s
s = align_str(text_to_be_encrypted, 16, c)
e = encryption_suite.encrypt(s)

而且成功了。它产生了与mysql加密相同的输出。

相关问题