如何在Mongoose中配置Client-Side Field Level Encryption
基于Mongoose实现客户端字段级加密(CSFLE)的配置方案
前置依赖
- MongoDB版本为4.2+企业版/Atlas集群,Mongoose版本为6.0+
- 安装所需依赖:
npm install mongodb mongodb-client-encryption mongoose - 提前准备主密钥:测试环境可本地生成96字节随机密钥,生产环境建议托管到云KMS服务
步骤1:生成测试用本地主密钥
const crypto = require('crypto'); // 96字节随机主密钥,生产环境禁止硬编码,需存储在安全的KMS服务中 const masterKey = crypto.randomBytes(96);
步骤2:配置带加密能力的Mongoose连接
const mongoose = require('mongoose'); const { ClientEncryption } = require('mongodb-client-encryption'); const encryptionConfig = { keyVaultNamespace: 'encryption.__keyVault', // 存储数据加密密钥的专属集合 kmsProviders: { local: { key: masterKey } } }; // 建立带自动加密能力的数据库连接 const connectWithCSFLE = async () => { await mongoose.connect('mongodb://localhost:27017/your_business_db', { autoEncryption: encryptionConfig }); };
步骤3:生成数据加密密钥(DEK)
const createDataKey = async () => { const encryptionClient = new ClientEncryption(mongoose.connection.getClient(), { keyVaultNamespace: encryptionConfig.keyVaultNamespace, kmsProviders: encryptionConfig.kmsProviders }); // 返回生成的数据加密密钥ID,后续配置Schema时使用 return await encryptionClient.createDataKey('local'); };
步骤4:定义带加密字段的Mongoose Schema
支持两种加密算法:
AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic:确定性加密,相同明文加密结果一致,支持等值查询AEAD_AES_256_CBC_HMAC_SHA_512-Random:随机加密,相同明文加密结果不同,安全性更高,不支持查询
const userSchema = new mongoose.Schema({ username: String, // 加密字段:身份证号,支持等值查询 idCard: { type: String, encrypt: { key: dataKeyId, // 替换为步骤3生成的dataKeyId algorithm: "AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic" } }, // 加密字段:银行卡号,不支持查询,安全性更高 bankCard: { type: String, encrypt: { key: dataKeyId, algorithm: "AEAD_AES_256_CBC_HMAC_SHA_512-Random" } } }); const User = mongoose.model('User', userSchema);
步骤5:验证加密效果
加密解密全流程在客户端自动完成,业务侧无需额外处理逻辑
// 插入数据时敏感字段自动加密 await User.create({ username: '张三', idCard: '110101199001011234', bankCard: '6222021234567890123' }); // 查询数据时敏感字段自动解密 const user = await User.findOne({ username: '张三' }); console.log(user.idCard); // 输出明文:110101199001011234
注意事项:
- 不要对
_id、索引字段、关联字段进行加密,会导致索引失效、关联查询异常- 数据加密密钥和主密钥不要与业务数据存储在同一数据库实例,避免密钥泄露
- 确定性加密会暴露明文重复特征,仅在需要等值查询的场景下使用
内容的提问来源于stack exchange,提问作者Yehuda_Fievel
相关产品推荐
相关产品推荐

