053. 编写一个函数,实现简单的文件加密和解密功能
以下是一个简单的Python函数,用于实现文件的加密和解密功能。这里使用了对称加密算法(如AES),因为它是实现文件加密的常用方法之一。我们将使用cryptography
库来完成这个任务。
安装依赖
首先,确保安装了cryptography
库。如果尚未安装,可以通过以下命令安装:
pip install cryptography
文件加密和解密代码
以下代码提供了一个简单的文件加密和解密功能:
from cryptography.hazmat.primitives.ciphers import Cipher, algorithms, modes
from cryptography.hazmat.primitives.kdf.pbkdf2 import PBKDF2HMAC
from cryptography.hazmat.primitives import hashes
from cryptography.hazmat.backends import default_backend
from cryptography.hazmat.primitives import padding
import os
def generate_key(password: str, salt: bytes) -> bytes:
"""
使用密码和盐值生成密钥
:param password: 用户提供的密码
:param salt: 盐值
:return: 生成的密钥
"""
kdf = PBKDF2HMAC(
algorithm=hashes.SHA256(),
length=32, # AES-256需要32字节的密钥
salt=salt,
iterations=100000,
backend=default_backend()
)
return kdf.derive(password.encode())
def encrypt_file(input_file: str, output_file: str, password: str):
"""
加密文件
:param input_file: 输入文件路径
:param output_file: 输出文件路径
:param password: 加密密码
"""
# 生成随机盐值
salt = os.urandom(16)
# 生成密钥
key = generate_key(password, salt)
# 生成随机IV(初始化向量)
iv = os.urandom(16)
# 创建AES加密器
cipher = Cipher(algorithms.AES(key), modes.CBC(iv), backend=default_backend())
encryptor = cipher.encryptor()
# 读取输入文件
with open(input_file, "rb") as f:
data = f.read()
# 对数据进行填充
padder = padding.PKCS7(algorithms.AES.block_size).padder()
padded_data = padder.update(data) + padder.finalize()
# 加密数据
encrypted_data = encryptor.update(padded_data) + encryptor.finalize()
# 将盐值、IV和加密数据写入输出文件
with open(output_file, "wb") as f:
f.write(salt)
f.write(iv)
f.write(encrypted_data)
print(f"文件已加密并保存到 {output_file}")
def decrypt_file(input_file: str, output_file: str, password: str):
"""
解密文件
:param input_file: 输入文件路径
:param output_file: 输出文件路径
:param password: 解密密码
"""
# 读取输入文件
with open(input_file, "rb") as f:
salt = f.read(16) # 读取盐值
iv = f.read(16) # 读取IV
encrypted_data = f.read() # 读取加密数据
# 生成密钥
key = generate_key(password, salt)
# 创建AES解密器
cipher = Cipher(algorithms.AES(key), modes.CBC(iv), backend=default_backend())
decryptor = cipher.decryptor()
# 解密数据
decrypted_padded_data = decryptor.update(encrypted_data) + decryptor.finalize()
# 移除填充
unpadder = padding.PKCS7(algorithms.AES.block_size).unpadder()
data = unpadder.update(decrypted_padded_data) + unpadder.finalize()
# 将解密数据写入输出文件
with open(output_file, "wb") as f:
f.write(data)
print(f"文件已解密并保存到 {output_file}")
# 示例用法
if __name__ == "__main__":
password = "my_secure_password"
encrypt_file("example.txt", "example.encrypted", password)
decrypt_file("example.encrypted", "example_decrypted.txt", password)
代码说明:
密钥生成:
-
使用
PBKDF2HMAC
算法从用户提供的密码和随机生成的盐值中派生出密钥。 -
盐值用于增加密码的安全性,防止彩虹表攻击。
加密过程:
-
使用AES算法(CBC模式)进行加密。
-
数据在加密前需要进行填充(使用PKCS7填充),以确保数据长度符合AES块大小的要求。
-
加密后的文件包含盐值、IV和加密数据。
解密过程:
-
从加密文件中读取盐值和IV,重新生成密钥。
-
解密数据后,移除填充,恢复原始数据。
文件操作:
-
输入文件被加密后保存为一个新的文件。
-
加密文件可以被解密并保存为另一个文件。
示例运行:
假设有一个文件example.txt
,内容为Hello, World!
。运行代码后:
-
example.encrypted
将包含加密后的数据。 -
example_decrypted.txt
将包含解密后的原始数据。
注意事项:
-
请确保密码足够复杂,以保证加密的安全性。
-
由于加密文件中包含盐值和IV,因此加密文件的大小会比原始文件稍大。
-
如果密码错误,解密过程可能会失败或产生错误的数据。
视频讲解
BiliBili: 视睿网络-哔哩哔哩视频 (bilibili.com)