MySQL 8.0+ 的 AES_ENCRYPT()/AES_DECRYPT() 不适合直接用于手机号、身份证等敏感字段加密,因其返回二进制值无法索引或模糊查询,ECB 模式导致相同明文密文一致,且无认证防篡改;推荐应用层使用 AES-GCM 等带认证加密,密钥由 KMS 托管,密文 base64 后存 VARCHAR。

MySQL 8.0+ 原生加密函数是否适合敏感字段?
MySQL 提供了 AES_ENCRYPT() 和 AES_DECRYPT(),但它们不适合直接用于手机号/身份证列加密——不是功能不行,而是用错场景。这些函数返回的是二进制(BLOB),无法索引、无法比较、无法做 LIKE 查询,且密钥硬编码在 SQL 里极易泄露。
更关键的是:AES_ENCRYPT() 不带认证,无法防篡改;若用 ECB 模式(默认),相同号码加密后结果完全一致,攻击者可直接通过密文频率反推真实值(比如“138****1234”反复出现)。
所以结论很明确:不要在 MySQL 层做应用级敏感字段加解密。
推荐方案:应用层加密 + MySQL 存储密文字符串
把加密逻辑移出数据库,在应用代码中完成,MySQL 只负责安全存储和传输。这是目前最可控、审计友好、也符合等保/个保法要求的做法。
- 使用带认证的加密模式,如 AES-GCM 或 AES-CBC + HMAC-SHA256(推荐
crypto/aes+crypto/cipher在 Go,或cryptography.hazmat.primitives.ciphers在 Python) - 密钥由 KMS(如阿里云 KMS、AWS KMS)托管,应用启动时动态获取,绝不写死
- 加密后 base64 编码为字符串,存入
VARCHAR(255)字段(AES-256-GCM 密文 + IV + tag 总长通常 ≤ 192 字节) - 解密只在必要业务环节(如实名核验)触发,避免全量解密扫描
示例(Python 简化逻辑):
面向 CRM 系统的 MySQL 8 数据库模式设计。当用户需要为客户关系管理(CRM)系统设计、评审、优化或生成数据库模式时,应使用此项技能。
from cryptography.hazmat.primitives.ciphers import Cipher, algorithms, modes from cryptography.hazmat.primitives import padding import os <p>def encrypt_phone(phone: str, key: bytes) -> str: iv = os.urandom(16) cipher = Cipher(algorithms.AES(key), modes.CBC(iv)) encryptor = cipher.encryptor() padder = padding.PKCS7(128).padder() padded_data = padder.update(phone.encode()) + padder.finalize() ciphertext = encryptor.update(padded_data) + encryptor.finalize() return base64.b64encode(iv + ciphertext).decode() # IV 显式拼接,便于解密</p>
如果必须用 MySQL 函数,至少要绕过哪些坑?
极少数遗留系统不允许改应用层,只能妥协使用 MySQL 内置函数。此时务必规避以下问题:
-
AES_ENCRYPT()必须显式指定模式,禁用默认 ECB:AES_ENCRYPT(data, key, 'AES-256-CBC')(MySQL 8.0.30+ 支持) - IV 必须随机生成并和密文一起存储(例如拼成
CONCAT(HEX(iv), ':', HEX(AES_ENCRYPT(...)))),否则 CBC 失效 - 密钥不能是明文字符串,应从会话变量注入:
SET @key = UNHEX(SHA2('your-salt-and-app-secret', 256));,再传给AES_ENCRYPT() - 字段类型必须为
VARBINARY(不是VARCHAR),长度至少 256,否则截断导致解密失败 - 解密时若返回
NULL,大概率是密钥/IV/模式不匹配,不是数据损坏——MySQL 不报具体错误
为什么不要用 MD5/SHA2 对手机号“脱敏”?
有人用 SHA2(phone, 256) 存哈希值,美其名曰“不可逆脱敏”。这是危险误区:
- 手机号只有 11 位数字,身份证虽长但结构固定、校验码可穷举,攻击者用 GPU 一小时就能建完全量彩虹表
- 哈希无法支持模糊查询(如查“同一人名下多个号码”)、无法满足“可逆解密用于公安接口对接”等真实需求
- 审计时会被认定为未履行《个人信息保护法》第 51 条“采取必要技术措施确保信息安全”的义务
真正需要的是加密(encryption),不是哈希(hashing)或掩码(masking)。
实际落地中最容易被忽略的点是密钥轮换机制——上线后没人记得半年换一次 KMS 密钥,结果某天密钥泄露,所有历史密文等于裸奔。加密不是加一道锁就完事,是整条链路的持续管控。










