数据库加密基础:概念、分类与常见算法

聊数据库加密之前,得先搞清楚一个根本问题——加密到底在防谁?

金融行业的数据,说白了就是钱和人的信息。客户姓名、身份证号、银行卡号、交易流水,随便一个字段泄漏都是大事故。加密的作用就是把「明文」变成「密文」,即使硬盘被人搬走了、备份被人拷了,对方看到也是一堆乱码。我参与过的审计日志项目里,光是字段级加密这一项,就能挡住90%以上的配置失误泄漏。

好,直接上干货。先看加密的三要素:算法、密钥、模式。算法决定转换规则,密钥决定唯一性,模式决定怎么处理大数据块。这三者搭配起来,才构成一个完整加密方案。

加密分类:从两个维度切

分类方法有很多,我习惯从两个最关键的维度去看:密钥体系和加密粒度。

维度 分类 代表算法/方案 适用场景
密钥体系 对称加密 AES, 3DES, SM4 大数据量、数据库内部字段加密
密钥体系 非对称加密 RSA, ECC, SM2 密钥分发、数字签名、少量数据
加密粒度 全库加密 TDE(透明数据加密) 备份文件、静态数据保护
加密粒度 表级加密 Oracle TDE 表空间 指定业务表防护
加密粒度 字段级加密 AES-256 + 应用层密钥 身份证、手机号等高敏感属性
个人习惯:金融审计日志场景,我几乎只推荐字段级加密配合对称算法。全库加密太粗暴,查询性能下降明显;表级加密又不够灵活。字段级加密让审计只对敏感列解密,性能影响可控,合规也容易过。

常见算法速览

算法不是越多越好,关键是选对并理解它的弱点。下面这几个是我实际项目中接触最多的。

  • AES(高级加密标准):当前对称加密的王者。密钥长度128/192/256,我更推荐AES-256。为什么呢?128位抗撞库够用,但金融审计日志通常是超长期保留(5~10年),我建议直接上256位,不留隐患。
  • SM4(国密标准):国内金融必须对齐。本质上和AES对标,128位分组,32轮迭代。我在央行的一个审计项目里就硬性要求使用SM4代替AES,代码实现不难,但密钥管理库要换一套。
  • RSA(非对称):常用于加密密钥本身或数字签名。2048位起步,一次最多加密明文长度不能超过密钥位数减11字节(比如2048位只能加密256-11=245字节)。做个证书、交换个会话密钥还行,直接加密大字段就是自讨苦吃。
  • ECC(椭圆曲线):比RSA同安全强度下密钥短很多,256位ECC ≈ 3072位RSA。我在移动端审计APP数据回传时用过ECC做签名,效率确实漂亮。
我曾经踩过的坑:有一回用AES-128做字段级加密,测试环境一切正常。上线后业务方说某个查询慢了10倍。排查发现他们用「AES加密列」做了LIKE模糊匹配,导致每次查询都要全表解密再过滤。这就是典型的「只加密不考虑查询需求」——后来我们改用部分明文保留+加密+哈希索引的三层方案才解决。

核心流程:加密/解密怎么跑

无论你选哪种算法,操作流程都差不多。以最常见的字段级加密为例:

  1. 密钥生成:用安全的随机数生成器(比如/dev/urandom)产生一个256位密钥。
  2. 密钥存储:密钥不能和密文放一起。我习惯用专门的密钥管理服务(KMS),或者至少存到HSM硬件安全模块里。
  3. 加密:取明文数据 + 密钥 + IV(初始化向量),跑AES-256-CBC模式,输出密文(Base64编码方便存储)。
  4. 解密:从存储中取出密文,用同样的密钥和IV还原明文。
  5. 审计钩子:在加密/解密操作前后,自动记录日志:谁、何时、操作了什么数据的什么字段。这就是审计日志的来源。
# Python 示例:字段级 AES-256-CBC 加密/解密(仅演示)
from Crypto.Cipher import AES
from Crypto.Util.Padding import pad, unpad
import base64, os

key = os.urandom(32)          # 256位密钥
iv = os.urandom(16)           # IV,每次加密随机生成

def encrypt_field(plaintext: str) -> str:
    cipher = AES.new(key, AES.MODE_CBC, iv=iv)
    ct_bytes = cipher.encrypt(pad(plaintext.encode(), AES.block_size))
    return base64.b64encode(iv + ct_bytes).decode()

def decrypt_field(ciphertext: str) -> str:
    raw = base64.b64decode(ciphertext)
    iv = raw[:16]
    ct = raw[16:]
    cipher = AES.new(key, AES.MODE_CBC, iv=iv)
    pt = unpad(cipher.decrypt(ct), AES.block_size)
    return pt.decode()
细节注意:上面的IV拼接方式只适合演示。生产环境一定要对密钥进行访问控制,IV必须存但不能泄漏,每次加密使用新IV(随机化至关重要)。另外,Base64编码会让密文长度膨胀约1/3,数据库字段类型推荐用 VARBINARY 或 BLOB 减少空间浪费。

一张图看懂数据库加密体系

数据库加密基础知识体系 数据库加密 按密钥体系 对称加密(AES等) 非对称加密(RSA等) 按加密粒度 全库加密(TDE) 表级加密 字段级加密 常见算法 AES-256 SM4 RSA/ECC ⚠️ 选择加密方案时必须考虑 合规要求(国密)、性能、密钥管理成本

这张图基本涵盖了数据库加密的三个主要维度:按密钥体系分、按加密粒度分、按常见算法分。三者交叉选择就构成了实际的加密方案。金融审计日志项目里,我个人偏好「对称+字段级+定制密钥管理」的组合,既能满足合规审计要求,又不会把性能搞崩。

记住一点:算法是骨架,密钥管理才是灵魂。密钥丢了,再强的算法也是白搭。