You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Python Fernet部分加密文件后解密损坏问题求助

问题根源分析

你的文件解密后损坏,核心问题出在二进制数据的处理方式错误,具体有两个关键点:

  • 错误地将二进制数据转为字符串处理
    解密时把encrypted(bytes类型)直接转成str再用split("@@")拆分,二进制文件(比如JPG)包含大量非UTF-8兼容字节,转字符串时会被自动替换为占位符,导致原始数据不可逆损坏,后续再编码回bytes也无法恢复原样。

  • 使用文本分隔符拆分二进制数据不可靠
    即使转字符串不出问题,@@作为分隔符也可能出现在加密内容或原始文件的二进制数据中,导致拆分位置错误,拼接后的文件结构完全混乱。你加密时已经记录了加密内容的长度,却没在解密时利用这个长度来精准拆分数据。


修正后的代码

加密脚本(encrypt.py)

保留原逻辑并优化变量命名,核心逻辑无需修改:

from cryptography.fernet import Fernet

# 生成密钥并保存
cipher_key = Fernet.generate_key()
with open('myCode.txt', 'wb') as filekey:
    filekey.write(cipher_key)

# 加载密钥
with open("myCode.txt", "rb") as key_file:
    key = key_file.read()
fernet = Fernet(key)

# 读取原始文件
with open("sikish.jpg", "rb") as file:
    original_data = file.read()

# 仅加密前100字节
encrypted_part = fernet.encrypt(original_data[:100])
unencrypted_part = original_data[100:]

# 拼接数据:加密长度(UTF-8编码) + 分隔符 + 加密内容 + 分隔符 + 未加密内容
length_bytes = str(len(encrypted_part)).encode("utf-8")
full_data = length_bytes + b"@@" + encrypted_part + b"@@" + unencrypted_part

with open("encryptedSikish.jpg", "wb") as file:
    file.write(full_data)

解密脚本(decrypt.py)

重点修改数据拆分逻辑,用长度精准拆分,避免字符串转换:

from cryptography.fernet import Fernet

# 读取加密后的文件数据
with open("encryptedSikish.jpg", "rb") as file:
    encrypted_data = file.read()

# 加载密钥
with open("myCode.txt", "rb") as code:
    mykey = code.read()
fernet = Fernet(mykey)

# 拆分数据:先找到第一个b"@@"的位置,提取加密内容的长度
sep = b"@@"
first_sep_idx = encrypted_data.index(sep)
length = int(encrypted_data[:first_sep_idx].decode("utf-8"))

# 根据长度提取加密部分和未加密部分
encrypted_part = encrypted_data[first_sep_idx + len(sep) : first_sep_idx + len(sep) + length]
unencrypted_part = encrypted_data[first_sep_idx + len(sep) + length + len(sep):]

# 解密并拼接
decrypted_part = fernet.decrypt(encrypted_part)
final_data = decrypted_part + unencrypted_part

with open("DecryptedSikish.jpg", "wb") as finalfile:
    finalfile.write(final_data)

关键修改说明
  • 完全避免二进制转字符串:所有数据处理都保持bytes类型,只在读取加密长度时做一次安全的UTF-8解码(因为长度是数字转的字符串,肯定是合法UTF-8)。
  • 用长度精准拆分:利用加密时记录的加密内容长度,直接通过索引截取字节,彻底避免分隔符冲突的问题。
  • 明确变量命名:让代码逻辑更清晰,减少误解。

内容的提问来源于stack exchange,提问作者FinishHim

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.23 10:20:02