本文目录导读:

Python脚本中加密存储配置信息有多种方法,我来介绍几种常用的安全方案:
使用 cryptography 库(推荐)
from cryptography.fernet import Fernet
import base64
import json
from pathlib import Path
class ConfigEncryptor:
def __init__(self, key_file="config_key.key"):
self.key_file = key_file
self.cipher = None
def generate_key(self):
"""生成加密密钥并保存"""
key = Fernet.generate_key()
with open(self.key_file, 'wb') as f:
f.write(key)
return key
def load_key(self):
"""加载加密密钥"""
with open(self.key_file, 'rb') as f:
key = f.read()
self.cipher = Fernet(key)
return key
def encrypt_config(self, config_dict):
"""加密配置字典"""
if not self.cipher:
self.load_key()
config_json = json.dumps(config_dict).encode()
encrypted = self.cipher.encrypt(config_json)
return encrypted
def decrypt_config(self, encrypted_data):
"""解密配置数据"""
if not self.cipher:
self.load_key()
decrypted = self.cipher.decrypt(encrypted_data)
return json.loads(decrypted.decode())
# 使用示例
def main():
# 1. 首次使用:生成密钥并加密配置
encryptor = ConfigEncryptor()
# 生成密钥(仅执行一次)
if not Path("config_key.key").exists():
encryptor.generate_key()
print("密钥文件已生成,请妥善保管!")
# 2. 加密配置
config = {
"database": {
"host": "localhost",
"port": 3306,
"username": "admin",
"password": "SecretPassword123!"
},
"api": {
"key": "api-key-123456",
"secret": "api-secret-789012"
}
}
encrypted_data = encryptor.encrypt_config(config)
# 保存加密后的配置
with open("config.encrypted", "wb") as f:
f.write(encrypted_data)
# 3. 解密配置使用
with open("config.encrypted", "rb") as f:
encrypted_data = f.read()
decrypted_config = encryptor.decrypt_config(encrypted_data)
# 使用配置
db_password = decrypted_config["database"]["password"]
api_key = decrypted_config["api"]["key"]
print(f"数据库密码: {db_password}")
print(f"API密钥: {api_key}")
if __name__ == "__main__":
main()
使用环境变量 + 配置加密(更安全)
import os
from cryptography.fernet import Fernet
import base64
import json
class SecureConfigManager:
def __init__(self):
# 从环境变量获取主密钥
self.master_key = os.environ.get('CONFIG_MASTER_KEY')
if not self.master_key:
raise ValueError("请设置 CONFIG_MASTER_KEY 环境变量")
# 将主密钥转换为Fernet密钥
self.fernet_key = base64.urlsafe_b64encode(
self.master_key.encode()[:32].ljust(32, b'\0')
)
self.cipher = Fernet(self.fernet_key)
def encrypt_value(self, value):
"""加密单个配置值"""
return self.cipher.encrypt(value.encode()).decode()
def decrypt_value(self, encrypted_value):
"""解密单个配置值"""
return self.cipher.decrypt(encrypted_value.encode()).decode()
def save_config(self, config_dict, filename="config.json"):
"""保存加密的配置文件"""
encrypted_config = {}
for key, value in config_dict.items():
encrypted_config[key] = self.encrypt_value(str(value))
with open(filename, 'w') as f:
json.dump(encrypted_config, f, indent=2)
def load_config(self, filename="config.json"):
"""加载并解密配置文件"""
with open(filename, 'r') as f:
encrypted_config = json.load(f)
decrypted_config = {}
for key, value in encrypted_config.items():
decrypted_config[key] = self.decrypt_value(value)
return decrypted_config
# 使用示例
def main():
# 设置环境变量(实际使用时应设置为系统环境变量)
os.environ['CONFIG_MASTER_KEY'] = 'your-very-secure-master-key-32chars'
manager = SecureConfigManager()
# 加密保存配置
config = {
"DB_PASSWORD": "super_secret_password",
"API_KEY": "sk-test-123456",
"EMAIL_PASSWORD": "email_pass_2024"
}
manager.save_config(config)
print("配置已加密保存")
# 读取并使用配置
loaded_config = manager.load_config()
print(f"数据库密码: {loaded_config['DB_PASSWORD']}")
if __name__ == "__main__":
main()
使用 keyring 系统密钥环(最安全)
import keyring
import json
class KeyringConfigManager:
def __init__(self, service_name="MyPythonApp"):
self.service_name = service_name
def save_to_keyring(self, key, value):
"""保存到系统密钥环"""
keyring.set_password(self.service_name, key, value)
def get_from_keyring(self, key):
"""从系统密钥环获取"""
return keyring.get_password(self.service_name, key)
def delete_from_keyring(self, key):
"""从系统密钥环删除"""
keyring.delete_password(self.service_name, key)
def save_config_dict(self, config_dict):
"""保存配置字典到密钥环"""
for key, value in config_dict.items():
self.save_to_keyring(key, value)
def get_config_dict(self, keys):
"""从密钥环获取配置字典"""
config = {}
for key in keys:
value = self.get_from_keyring(key)
if value:
config[key] = value
return config
# 使用示例
def main():
manager = KeyringConfigManager()
# 保存配置到系统密钥环
config = {
"database_host": "localhost",
"database_user": "myuser",
"database_password": "secret123"
}
manager.save_config_dict(config)
print("配置已保存到系统密钥环")
# 读取配置
keys_to_load = ["database_host", "database_user", "database_password"]
loaded_config = manager.get_config_dict(keys_to_load)
print(f"数据库密码: {loaded_config['database_password']}")
if __name__ == "__main__":
main()
推荐的安全实践
"""
最佳实践配置文件结构:
project/
├── config/
│ ├── config.json # 非敏感配置
│ └── config.encrypted # 加密的敏感配置
├── keys/
│ └── master.key # 主密钥文件(从不提交到Git)
├── .env # 环境变量(不提交到Git)
├── .gitignore
└── your_script.py
"""
# .env 文件示例
CONFIG_MASTER_KEY=your_master_key_here
DB_HOST=localhost
DB_PORT=3306
# .gitignore 添加
keys/
.env
*.encrypted
config_key.key
"""
安全建议:
1. 永远不要将密钥硬编码在代码中
2. 使用环境变量传递密钥
3. 将密钥文件添加到 .gitignore
4. 使用不同的密钥用于开发和生产环境
5. 考虑使用专业的密钥管理服务(如 AWS KMS, Azure Key Vault)
6. 定期轮换密钥
7. 限制密钥访问权限
"""
# 综合使用示例
import os
from pathlib import Path
from cryptography.fernet import Fernet
class ProductionConfigManager:
"""生产环境配置管理器"""
def __init__(self):
# 优先使用环境变量,其次是密钥文件
self.master_key = os.environ.get('CONFIG_MASTER_KEY')
if not self.master_key:
key_file = Path('keys/master.key')
if key_file.exists():
self.master_key = key_file.read_text().strip()
else:
# 生成新的密钥
self.master_key = Fernet.generate_key().decode()
key_file.parent.mkdir(exist_ok=True)
key_file.write_text(self.master_key)
key_file.chmod(0o600) # 仅所有者可读写
self.cipher = Fernet(self.master_key.encode() if isinstance(self.master_key, str) else self.master_key)
def encrypt(self, data):
if isinstance(data, str):
data = data.encode()
return self.cipher.encrypt(data)
def decrypt(self, encrypted_data):
return self.cipher.decrypt(encrypted_data)
# 使用示例
config_manager = ProductionConfigManager()
encrypted = config_manager.encrypt("sensitive_data")
decrypted = config_manager.decrypt(encrypted)
安装依赖
# 安装所需库 pip install cryptography keyring # keyring 可能需要额外系统依赖 # Ubuntu/Debian: sudo apt-get install libsecret-1-dev # macOS: brew install libsecret
选择建议
- 个人项目:使用 cryptography 库 + 密钥文件
- 团队项目:使用环境变量 + cryptography
- 企业应用:使用系统密钥环或专业密钥管理服务
- 云原生应用:使用云服务商提供的密钥管理服务
没有任何加密方法是绝对安全的,关键是找到安全性和便利性的平衡点。
版权声明:NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播