CSFLE 加密模式
概述
注意
企业功能
字段级加密的自动功能仅在 MongoDB Enterprise 4.2 或更高版本以及 MongoDB Atlas 4.2 或更高版本的集群中可用。
加密模式包含用户指定的规则,用于标识哪些字段必须加密以及如何加密这些字段。应用程序必须使用 JSON Schema Draft 4 标准语法的严格子集以及以下加密特定关键字指定自动加密规则:JSON Schema Draft 4 标准和以下加密特定关键字
Encrypt指定加密当前字段时使用的加密选项。
Encrypt Metadata指定可继承的加密选项。
对于 MongoDB shell,请使用Mongo()
构造函数用于创建数据库连接,并包括客户端字段级加密作为配置对象的一部分。有关示例,请参阅配置对象。更多信息请参考启用客户端端加密的集群连接。
对于官方MongoDB驱动程序,请使用特定于驱动的数据库连接构造函数(MongoClient
)创建数据库连接,并将客户端字段级加密配置对象中的自动加密规则包含在内。有关CSFLE特定的MongoClient
选项的更多信息,请参阅mongo客户端页面。
定义
encrypt
对象
"bsonType" : "object", "properties" : { "<fieldName>" : { "encrypt" : { "algorithm" : "<string>", "bsonType" : "<string>" | [ "<string>" ], "keyId" : [ <UUID> ] } } } 表示必须加密的
<fieldName>
。`encrypt`对象有以下要求encrypt
不能在<fieldName>
对象中拥有任何兄弟字段。encrypt
必须是<fieldName>
对象的唯一子元素。encrypt
不能在items
或additionalItems
关键字的任何子模式中指定。具体来说,自动客户端字段级加密不支持加密数组中的单个元素。
encrypt
对象可以包含 仅 以下字段如果将任何其他字段添加到
encrypt
对象中,则在执行自动加密读取或写入操作时会导致错误如果省略了
keyId
或algorithm
,则 自动加密共享库 会检查所有父字段,并尝试从最近的指定选项的encryptMetadata
对象中构建这些选项。bsonType
不能继承,并且根据algorithm
的值可能需要。如果自动加密共享库无法使用指定的字段和任何必需的
encryptMetadata
继承的键构建完整的encrypt
对象,则自动加密将失败并返回错误。
encrypt.algorithm
String
指示加密
<fieldName>
值时使用的加密算法。仅支持以下算法 仅AEAD_AES_256_CBC_HMAC_SHA_512-Random
AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic
有关加密算法的完整文档,请参阅 字段和加密类型。
如果省略,则自动加密共享库会检查所有父字段,寻找包含
encryptMetadata.algorithm
键的最接近祖先,并继承该值。如果不存在父级algorithm
,自动字段级加密将失败并返回错误。如果
encrypt.algorithm
或其继承的值是AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic
,则encrypt
对象需要包含encrypt.bsonType
字段。如果
encrypt.algorithm
或其继承的值是AEAD_AES_256_CBC_HMAC_SHA_512-Random
,则encrypt
对象可能包含encrypt.bsonType
字段。
encrypt.bsonType
字符串 | 字符串数组
正在加密字段的BSON类型。如果
encrypt.algorithm
是AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic
,则这是必需的。如果
encrypt.algorithm
或其继承的值是AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic
,则bsonType
必须指定一个单个类型。对于确定性加密算法,bsonType
不支持以下任何BSON类型:double
decimal128
bool
object
array
如果
encrypt.algorithm
或其继承的值是AED_AES_256_CBC_HMAC_SHA_512-Random
,则bsonType
是可选的,可以指定支持的BSON类型的数组。对于具有bsonType
为array
或object
的字段,客户端会加密整个数组或对象,而不是其单个元素。encrypt.bsonType
无论encrypt.algorithm
或其继承的值如何,都不支持以下类型:minKey
maxKey
null
undefined
encrypt.keyId
单一UUID数组
用于加密字段值的密钥数据的UUID。UUID是BSON 二进制数据元素,属于子类型
4
。在数组内指定一个字符串。
如果省略,则自动加密共享库会检查所有父字段,查找包含
encryptMetadata.keyId
键的最接近的祖先字段,并继承该值。如果父字段中不存在keyId
键,则自动字段级加密失败并返回错误。keyId
或其继承的值必须存在于自动加密配置选项中指定的密钥库集合中。如果指定的数据加密密钥不存在,则自动加密失败。官方MongoDB驱动程序对指定UUID有语言特定的要求。请参阅驱动程序文档以获取关于实现客户端字段级加密的完整文档。
encryptMetadata
对象
{ "bsonType" : "object", "encryptMetadata" : { "algorithm" : "<string>", "keyId" : [ <UUID> ] }, "properties" : { "encrypt" : {} } } 定义了加密选项,一个嵌套在兄弟
properties
中的encrypt
对象可以继承这些选项。如果encrypt
对象缺少支持加密所需的选项,自动加密共享库将搜索所有父对象以定位一个指定缺少选项的encryptMetadata
对象。encryptMetadata
必须在具有bsonType: "object"
的子模式中指定。encryptMetadata
不能指定给items
或additionalItems
关键字的任何子模式。具体来说,自动客户端字段级加密不支持加密数组中的单个元素。encryptMetadata
对象可以包含 仅 以下字段。向encrypt
对象添加任何其他字段会导致自动加密读取或写入操作时出错
encryptMetadata.algorithm
String
用于加密特定字段的加密算法。如果
encrypt
对象缺少algorithm
字段,自动加密共享库将在所有父对象中搜索,以定位指定encryptMetadata
对象。仅支持以下算法
AEAD_AES_256_CBC_HMAC_SHA_512-Random
AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic
关于加密算法的完整文档,请参阅字段和加密类型。
如果指定
AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic
,任何继承该值的encrypt
对象必须指定encrypt.bsonType
。
encryptMetadata.keyId
单一UUID数组
数据加密键的UUID。UUID是BSON子类型
4
的二进制数据元素。在数组内指定一个字符串。
如果
encrypt
对象缺少keyId
字段,自动加密共享库将在所有父对象中搜索,以定位指定encryptMetadata
对象。数据加密密钥必须在自动加密配置选项中指定的密钥库集合中存在。指定的配置选项还必须包括对密钥管理服务(KMS)和用于创建数据密钥的客户主密钥(CMK)的适当访问。如果数据加密密钥不存在或者客户端无法使用指定的KMS和CMK解密密钥,自动加密将失败。
官方MongoDB驱动程序对指定UUID有语言特定的要求。请参阅驱动程序文档以获取关于实现客户端字段级加密的完整文档。
示例
加密模式 - 多个字段
考虑一个集合 MedCo.patients
,其中每个文档具有以下结构
{ "fname" : "<String>", "lname" : "<String>", "passportId" : "<String>", "bloodType" : "<String>", "medicalRecords" : [ {<object>} ], "insurance" : { "policyNumber" : "<string>", "provider" : "<string>" } }
以下字段包含可能被查询的个人身份信息(PII)
passportId
bloodType
insurance.policyNumber
insurance.provider
确定性的加密算法保证值的加密输出保持静态。这允许对特定值的查询返回有意义的成果,但代价是增加了对频率分析恢复的敏感性。因此,确定性的加密算法满足数据的加密和可查询性要求。
以下字段包含可能永远不会被查询的法律保护的个人信息(PII)
medicalRecords
随机的加密算法保证值的加密输出始终是唯一的。这防止了对特定字段值的查询返回有意义的成果,同时支持对字段内容最高级别的保护。因此,随机的加密算法满足数据的加密和可查询性要求。
以下架构指定了满足上述要求的自动加密规则,用于MedCo.patients
集合
{ "MedCo.patients" : { "bsonType" : "object", "properties" : { "passportId" : { "encrypt" : { "keyId" : [UUID("bffb361b-30d3-42c0-b7a4-d24a272b72e3")], "algorithm" : "AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic", "bsonType" : "string" } }, "bloodType" : { "encrypt" : { "keyId" : [UUID("bffb361b-30d3-42c0-b7a4-d24a272b72e3")], "algorithm" : "AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic", "bsonType" : "string" } }, "medicalRecords" : { "encrypt" : { "keyId" : [UUID("f3821212-e697-4d65-b740-4a6791697c6d")], "algorithm" : "AEAD_AES_256_CBC_HMAC_SHA_512-Random", "bsonType" : "array" } }, "insurance" : { "bsonType" : "object", "properties" : { "policyNumber" : { "encrypt" : { "keyId" : [UUID("bffb361b-30d3-42c0-b7a4-d24a272b72e3")], "algorithm" : "AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic", "bsonType" : "string" } }, "provider" : { "encrypt" : { "keyId" : [UUID("bffb361b-30d3-42c0-b7a4-d24a272b72e3")], "algorithm" : "AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic", "bsonType" : "string" } } } } } } }
上述自动加密规则标记了需要加密的passportId
、bloodType
、insurance.policyNumber
、insurance.provider
和medicalRecords
字段。
passportId
、bloodType
、insurance.policyNumber
和provider
字段需要使用指定的密钥进行确定性加密。medicalRecords
字段需要使用指定的密钥进行随机加密。
虽然可查询加密不支持加密单个数组元素,但随机加密支持加密字段中的整个数组,而不是单个元素。示例自动加密规则指定了对medicalRecords
字段进行随机加密以加密整个数组。如果自动加密规则在medicalRecords.items
或medicalRecords.additionalItems
中指定了encrypt
或encryptMetadata
,则自动字段级加密将失败并返回错误。
官方MongoDB驱动程序,mongosh
和旧的mongo
shell需要在创建数据库连接对象时指定自动加密规则。
对于
mongosh
,使用Mongo()
构造函数来创建数据库连接。将自动加密规则指定给AutoEncryptionOpts
参数的schemaMap
键。请参阅启用自动客户端加密的集群连接以获取完整示例。对于官方MongoDB驱动程序,使用特定于驱动程序的数据库连接构造函数(
MongoClient
)来创建包含查询加密配置对象中自动加密规则的数据库连接。请参阅驱动程序API参考以获取更完整的信息和教程。
对于所有客户端,指定给可查询加密参数的keyVault
和kmsProviders
必须授权访问自动加密规则中指定的数据加密密钥,以及用于加密数据加密密钥的客户主密钥。
加密架构 - 具有继承的多个字段
考虑一个集合 MedCo.patients
,其中每个文档具有以下结构
{ "fname" : "<String>", "lname" : "<String>", "passportId" : "<String>", "bloodType" : "<String>", "medicalRecords" : [ {<object>} ], "insurance" : { "policyNumber" : "<string>", "provider" : "<string>" } }
以下字段包含可能被查询的私有数据
passportId
bloodType
insurance.policyNumber
insurance.provider
确定性的加密算法保证值的加密输出保持静态。这允许对特定值的查询返回有意义的成果,但代价是增加了对频率分析恢复的敏感性。因此,确定性的加密算法满足数据的加密和可查询性要求。
以下字段包含可能永远不会被查询的私有数据
medicalRecords
随机的加密算法保证值的加密输出始终是唯一的。这防止了对特定字段值的查询返回有意义的成果,同时支持对字段内容最高级别的保护。因此,随机的加密算法满足数据的加密和可查询性要求。
以下模式指定了自动加密规则,这些规则满足 MedCo.patients
集合的加密要求
{ "MedCo.patients" : { "bsonType" : "object", "encryptMetadata" : { "keyId" : [UUID("6c512f5e-09bc-434f-b6db-c42eee30c6b1")], "algorithm" : "AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic" }, "properties" : { "passportId" : { "encrypt" : { "bsonType" : "string" } }, "bloodType" : { "encrypt" : { "bsonType" : "string" } }, "medicalRecords" : { "encrypt" : { "keyId" : [UUID("6c512f5e-09bc-434f-b6db-c42eee30c6b1")], "algorithm" : "AEAD_AES_256_CBC_HMAC_SHA_512-Random", "bsonType" : "array" } }, "insurance" : { "bsonType" : "object", "properties" : { "policyNumber" : { "encrypt" : { "bsonType" : "string" } }, "provider" : { "encrypt" : { "bsonType" : "string" } } } } } } }
上述自动加密规则标记了需要加密的passportId
、bloodType
、insurance.policyNumber
、insurance.provider
和medicalRecords
字段。
passportId
、bloodType
、insurance.policyNumber
和provider
字段从父encryptMetadata
字段继承其加密设置。具体来说,这些字段继承指定数据加密密钥的确定加密的algorithm
和keyId
值。medicalRecords
字段需要使用指定密钥进行随机加密。encrypt
选项会覆盖父encryptMetadata
字段中指定的选项。
虽然可查询加密不支持加密单个数组元素,但随机加密支持加密字段中的整个数组,而不是单个元素。示例自动加密规则指定了对medicalRecords
字段进行随机加密以加密整个数组。如果自动加密规则在medicalRecords.items
或medicalRecords.additionalItems
中指定了encrypt
或encryptMetadata
,则自动字段级加密将失败并返回错误。
官方MongoDB驱动程序,mongosh
和旧的mongo
shell需要在创建数据库连接对象时指定自动加密规则。
对于
mongosh
,使用Mongo()
构造函数来创建数据库连接。将自动加密规则指定给AutoEncryptionOpts
参数的schemaMap
键。请参阅启用自动客户端加密的集群连接以获取完整示例。对于官方MongoDB驱动程序,使用特定于驱动程序的数据库连接构造函数(
MongoClient
)来创建包含查询加密配置对象中自动加密规则的数据库连接。请参阅驱动程序API参考以获取更完整的信息和教程。
对于所有客户端,指定给可查询加密参数的keyVault
和kmsProviders
必须授权访问自动加密规则中指定的数据加密密钥,以及用于加密数据加密密钥的客户主密钥。
有关更多关于您的密钥管理(CMK)和密钥保管库集合的信息,请参阅密钥保管库页面。
有关加密算法的更多信息,请参阅加密算法页面。
有关 CSFLE 特定的 MongoClient
选项的更多信息,请参阅Mongo 客户端页面。
加密模式 - 使用模式属性进行加密
您可以使用加密模式中的 patternProperties
关键字来定义与正则表达式匹配的所有字段的加密规则。
考虑一个集合 MedCo.patients
,其中每个文档具有以下结构
{ "fname" : "<string>", "lname" : "<string>", "passportId_PIIString" : "<string>", "bloodType_PIIString" : "<string>", "medicalRecords_PIIArray" : [ {<object>} ], "insurance" : { "policyNumber_PIINumber" : "<number>", "provider_PIIString" : "<string>" } }
包含私有数据的字段通过附加在字段名末尾的 "_PII<type>" 标签进行标识。
passportId_PIIString
bloodType_PIIString
medicalRecords_PIIArray
insurance.policyNumber_PIINumber
insurance.provider_PIIString
您可以使用 patternProperties
关键字来配置这些字段进行加密,而无需逐个标识每个字段,也不需要使用完整的字段名。通过使用匹配所有以 "_PII<type>" 标签结尾的字段的正则表达式来完成此操作。
以下 JSON 模式使用 patternProperties
和正则表达式来指定要加密的字段。
{ "MedCo.patients": { "bsonType": "object", "patternProperties": { "_PIIString$": { "encrypt": { "keyId": [UUID("6c512f5e-09bc-434f-b6db-c42eee30c6b1")], "bsonType": "string", "algorithm": "AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic", }, }, "_PIIArray$": { "encrypt": { "keyId": [UUID("6c512f5e-09bc-434f-b6db-c42eee30c6b1")], "bsonType": "array", "algorithm": "AEAD_AES_256_CBC_HMAC_SHA_512-Random", }, }, "insurance": { "bsonType": "object", "patternProperties": { "_PIINumber$": { "encrypt": { "keyId": [UUID("6c512f5e-09bc-434f-b6db-c42eee30c6b1")], "bsonType": "int", "algorithm": "AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic", }, }, "_PIIString$": { "encrypt": { "keyId": [UUID("6c512f5e-09bc-434f-b6db-c42eee30c6b1")], "bsonType": "string", "algorithm": "AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic", }, }, }, }, }, }, }
上述自动加密规则将 passportId_PIIString
、bloodType_PIIString
、medicalRecords_PIIArray
、insurance.policyNumber_PIINumber
、insurance.provider_PIIString
字段标记为加密。
有关 patternProperties
关键字的更多信息,请参阅patternProperties 关键字。