第3章 加密技术基础:对称加密、非对称加密、哈希、AEAD
做审计日志系统,逃不开一个话题:加密。
你想想看,日志里可能记录着用户操作、敏感数据变更、甚至密钥轮换记录。如果这些内容以明文存储,那审计系统本身就变成了最大的安全隐患。
所以,搞明白四种核心加密技术,是咱们后续做索引和查询优化的地基。这一章,我把它们掰开了讲,结合我在审计项目里踩过的坑,给你说透。
3.1 对称加密:又快又简单,但密钥怎么管?
对称加密,说白了就是加密和解密用同一把钥匙。常见的算法有 AES、DES、SM4。
它的优点就一个字:快。硬件加速后,AES-256 在普通服务器上能达到 GB 级吞吐。所以,审计日志里的大块内容——比如完整的请求/响应体——我习惯用对称加密来搞定。
但对称加密有个硬伤——密钥分发。你用同一把钥匙加密所有日志,那这把钥匙一旦泄露,全部日志就被看光了。
我在项目里遇到过一件事:某个团队把 AES 密钥硬编码在配置中心,结果配置中心被扫出来一个弱密码。嗯,从那以后我定了一条规矩——对称密钥必须定期轮换,并且用非对称加密来传输。
- 优点:计算开销小,适合海量日志加密
- 缺点:密钥管理复杂,需要配套的密钥生命周期系统
- 审计场景:加密日志正文、敏感字段(如 IP、用户 ID)
3.2 非对称加密:公钥私钥,各司其职
非对称加密,密钥成对出现:公钥加密,私钥解密;或者私钥签名,公钥验签。常用算法有 RSA、ECC(SM2 是国密版本)。
速度上,它比对称加密慢两到三个数量级。所以没人用它来加密大段日志。那它在审计系统里干嘛用?两件事:数字签名 和 密钥交换。
审计日志的不可否认性,靠的就是非对称签名。
每条日志落盘前,用私钥算一个签名。后续审计时,只要公钥能验过签名,就能证明这条日志没被篡改过,而且确实是那个节点产生的。这招在合规审计里几乎是必选项。
我曾经遇到过一个坑:有个系统用 RSA-1024 做签名,部署了三年才发现密钥强度已经不满足监管要求。换到 RSA-2048 或者 ECC P-256,花了整整两周的迁移时间。所以,我建议一开始就用 ECC,密钥短、性能好、未来十年都扛得住。
- 签名:每条日志追加一个签名,用于防篡改和溯源
- 密钥交换:用非对称加密传输对称密钥,解决密钥分发问题
- 性能注意:签名验签频率高的话,建议用 ECC 或 SM2,降低 CPU 开销
3.3 哈希函数:不可逆的指纹
哈希函数把任意长度的数据压缩成固定长度的摘要。常见的算法有 SHA-256、SHA-3、SM3。哈希的特点是单向且抗碰撞——你没法从摘要反推出原文,也很难找到两个不同的输入产生相同的摘要。
在审计日志里,哈希有两个经典用途:
- 日志指纹链:每条日志的哈希包含上一条的哈希,形成链式结构。任何人想篡改中间某条日志,都得把后面的哈希全改一遍,成本极高。
- 完整性校验:定期对日志文件计算哈希,跟存档值比对,确认文件没有被静默损坏或篡改。
我曾经踩过一个坑:用 MD5 做日志指纹。当时觉得日志只是内部用,结果被安全审计扫出来,说 MD5 已经能被碰撞攻击。全量重新哈希一遍,几百万条日志跑了半天。从那以后,我不管什么场景,哈希一律用 SHA-256 起步。
3.4 AEAD:一步到位,省心省力
AEAD(Authenticated Encryption with Associated Data)是「认证加密」的缩写。它把机密性和完整性合在一个算法里,一步搞定。
常见的 AEAD 方案有 AES-256-GCM、ChaCha20-Poly1305。你想想看,以前我们要先加密再用 HMAC 做认证,两个步骤容易出错——比如有人忘了做 HMAC,或者 nonce 重复使用。AEAD 直接消灭了这类问题。
我个人强烈建议:所有审计日志的加密,优先用 AEAD。理由很简单——它同时保证「别人看不懂」和「别人改不了」。而且,大部分现代 CPU 都对 GCM 模式做了硬件加速,性能几乎不输纯对称加密。
下面是一个用 Python 实现 AES-256-GCM 加密日志的示例,也是我项目中一直在用的模板:
from cryptography.hazmat.primitives.ciphers.aead import AESGCM
import os
def encrypt_log_entry(key: bytes, log_data: bytes, associated_data: bytes = b"") -> bytes:
# 生成随机 nonce,每次加密必须不同
nonce = os.urandom(12)
aead = AESGCM(key)
# 加密并认证,associated_data 参与认证但不加密
ciphertext = aead.encrypt(nonce, log_data, associated_data)
# 存储格式:nonce + 密文,方便解密时提取
return nonce + ciphertext
def decrypt_log_entry(key: bytes, encrypted: bytes, associated_data: bytes = b"") -> bytes:
nonce = encrypted[:12]
ciphertext = encrypted[12:]
aead = AESGCM(key)
return aead.decrypt(nonce, ciphertext, associated_data)
# 使用示例
key = AESGCM.generate_key(bit_length=256)
log = b"user=admin action=delete_file target=config.yaml ts=2025-01-15T10:00:00Z"
encrypted = encrypt_log_entry(key, log, b"audit_log_v1")
decrypted = decrypt_log_entry(key, encrypted, b"audit_log_v1")
print(decrypted.decode())
3.5 四种技术对比
到这里,四种技术的定位应该清楚了。我整理了一个对比表格,方便你快速参考:
| 技术 | 核心能力 | 审计日志用途 | 性能特点 | 常见算法 |
|---|---|---|---|---|
| 对称加密 | 机密性 | 加密日志正文 | 极快,硬件加速 | AES-256, SM4 |
| 非对称加密 | 签名 / 密钥交换 | 数字签名、传输对称密钥 | 慢,适合小数据量 | ECC P-256, RSA-2048, SM2 |
| 哈希函数 | 完整性 / 指纹 | 日志链式校验、文件完整性 | 快,可并行 | SHA-256, SHA-3, SM3 |
| AEAD | 机密性 + 完整性 | 加密+认证一步完成(推荐) | 较快,GCM 有硬件加速 | AES-256-GCM, ChaCha20-Poly1305 |
我给你的选型建议:
- 日志正文加密 → AEAD(AES-256-GCM 或 ChaCha20-Poly1305)
- 日志签名验签 → 非对称加密(ECC P-256 优先)
- 日志指纹链 → 哈希(SHA-256,配合间隔锚点)
- 密钥传输 → 非对称加密保护对称密钥
四种技术各有所长,但实际项目中往往是组合使用。比如一条审计日志:用 AEAD 加密正文保证机密性和完整性,再对整条日志(含元数据)做一次 ECC 签名,最后把哈希锚点写入区块链或持久化存储。你看,一环扣一环,每种技术都在合适的位置发挥作用。