如何在Python中解密C#生成的AES加密数据
问题排查结果
- 核心问题:密钥处理逻辑不匹配
C#侧直接将密钥字符串转为ASCII字节作为AES密钥,Python侧对原始密钥字符串做了SHA256哈希后再作为密钥,两边使用的密钥完全不一致,是加解密失败的最主要原因。 - 次要问题:密钥长度不符合AES规范
当前使用的原始密钥My private key共14个字符,转为ASCII后只有14字节,不符合AES要求的16/24/32字节(对应128/192/256位密钥)的标准,C#运行时会直接抛出密码学异常,需要先补齐密钥长度。 - IV参数匹配无误
C#侧new byte[16]生成的是16个0的字节数组,Python侧binascii.unhexlify(16 * "00")生成的也是16个0的字节数组,IV参数不存在问题。 - 填充逻辑兼容
你自定义的Pythonr_pad函数就是标准PKCS7填充,和C# AES类默认的PaddingMode.PKCS7填充规则完全兼容,不需要调整。
修复方案
推荐统一两边的密钥生成逻辑,使用SHA256哈希生成32字节的AES-256密钥,避免密钥长度不符合规范的问题:
C#代码调整
修改密钥生成逻辑,显式指定填充模式:
using System.Security.Cryptography; using System.Text; // Main方法内替换密钥赋值逻辑 var key = "My private key"; using (var sha256 = SHA256.Create()) { myAes.Key = sha256.ComputeHash(Encoding.UTF8.GetBytes(key)); } myAes.Mode = CipherMode.CBC; myAes.Padding = PaddingMode.PKCS7; // 显式指定填充模式,避免默认值差异 myAes.IV = new byte[16]; // EncryptStringToBytes_Aes方法内创建Aes对象后也补充填充配置 aesAlg.Padding = PaddingMode.PKCS7; // StreamWriter显式指定UTF-8编码,避免系统默认编码差异 using (var swEncrypt = new StreamWriter(csEncrypt, Encoding.UTF8))
Python代码调整
解密时改为自动去除PKCS7填充,不要硬切明文长度:
# 解密部分修改为: decrypted_data = AES.new(encoded_key, AES.MODE_CBC, iv).decrypt(bytes_to_decrypt) pad_len = decrypted_data[-1] decode_str = decrypted_data[:-pad_len].decode('utf-8')
如果不想修改C#原有逻辑,直接对齐C#的密钥生成规则即可,Python侧替换密钥生成代码:
# 注意需要保证原始密钥长度为16/24/32字节 encoded_key = key.encode('ascii')
修改完成后两边生成的密文完全一致,跨语言加解密可以正常运行。
内容的提问来源于stack exchange,提问作者Mohit Kumar
相关产品推荐
相关产品推荐

