对于 AI 代理:可在 https://www.mongodb.com/zh-cn/docs/llms.txt 获取文档索引—通过在任何 URL 路径后添加 .md 可获取所有页面的 Markdown 版本。

将自动可查询加密与 KMIP 结合使用

本指南向您展示如何构建一个应用程序,实现 MongoDB 可查询加密功能以自动加密和解密文档字段,并使用符合密钥管理互操作性协议 (KMIP) 的密钥提供程序进行密钥管理。

在完成本指南中的步骤后,您应该具有:

  • 由KMIP兼容的提供商托管的客户主密钥

  • 有效的客户端应用程序,可使用客户主密钥插入具有加密字段的文档

提示

客户主密钥

要了解有关客户主密钥的更多信息,请阅读 加密密钥和密钥保管库 文档。

要完成并运行本指南中的代码,您需要设立开发环境,如安装Queryable Encryption兼容的驱动程序和依赖项页面所示。

提示

请参阅:完整应用程序

要查看此示例应用程序的完整代码,请选择与您的编程语言相对应的标签页,然后点击所提供的链接。每个示例应用程序存储库都包含一个 README.md 文件,您可以使用该文件来了解如何设置环境并运行应用程序。

1

要将 MongoDB 驱动程序客户端连接到KMIP兼容密钥提供商,您必须配置KMIP兼容密钥提供商,使其接受客户端的 TLS 证书。

有关如何接受客户端证书的信息,请参阅符合KMIP的密钥提供商的文档。

2

客户端必须通过 TLS 连接到KMIP兼容密钥提供商,并提供KMIP兼容密钥提供商接受的客户端证书:

const tlsOptions = { kmip: { tlsCAFile: process.env["KMIP_TLS_CA_FILE"], // Path to your TLS CA file tlsCertificateKeyFile: process.env["KMIP_TLS_CERT_FILE"], // Path to your TLS certificate key file },};
1

本教程中的代码示例使用以下变量来执行 Queryable Encryption 工作流:

  • kmsProviderName - 您用于存储客户主密钥的KMS 。 在本教程中,将此变量设置为"kmip" 。

  • uri - 您的MongoDB 部署连接 URI。 在MONGODB_URI环境变量中设置连接 URI 或直接替换该值。

  • keyVaultDatabaseName - MongoDB 中将存储您的数据加密密钥 (DEK) 的数据库。将此变量设置为 "encryption"。

  • keyVaultCollectionName - MongoDB 中将存储您的 DEK 的集合。 将此变量设置为"__keyVault" 。

  • keyVaultNamespace - MongoDB中将存储您的 DEK 的命名空间。 将此变量设置为keyVaultDatabaseName和keyVaultCollectionName变量的值,并用句点分隔。

  • cryptoDatabaseName - MongoDB 中将存储您的加密数据的数据库。将此变量设置为 "medicalRecords"。

  • cryptoCollectionName - MongoDB 中将存储您的加密数据的集合。将此变量设置为 "patients"。

您可以使用以下代码来声明这些变量:

// KMS provider name should be one of the following: "aws", "gcp", "azure", "kmip" or "local"const kmsProviderName = "<Your KMS Provider Name>";const uri = process.env.MONGODB_URI; // Your connection URIconst keyVaultDatabaseName = "encryption";const keyVaultCollectionName = "__keyVault";const keyVaultNamespace = `${keyVaultDatabaseName}.${keyVaultCollectionName}`;const encryptedDatabaseName = "medicalRecords";const encryptedCollectionName = "patients";

重要

密钥保管库集合命名空间权限

密钥保管库集合位于encryption.__keyVault命名空间中。 确保应用程序用于连接到 MongoDB 的数据库用户对此命名空间具有ReadWrite权限。

提示

环境变量

本教程中的示例代码引用了您需要设置的环境变量。或者,您也可以直接在代码中替换这些值。

要了解如何设置这些环境变量,请参阅 GitHub 上的示例应用程序中包含的 README.md 文件。

2

创建一个变量,其中包含具有以下结构的符合 KMIP 的密钥提供商的端点:

kmsProviderCredentials = { kmip: { endpoint: process.env["KMIP_KMS_ENDPOINT"], // Your KMIP KMS endpoint },};

创建一个空对象,如以下代码示例所示。 这会提示符合KMIP的提供商生成新的客户主密钥。

customerMasterKeyCredentials = {};

创建一个包含以下选项的autoEncryptionOptions对象:

  • 密钥保管库集合的命名空间

  • kmsProviderCredentials对象,其中包含您的KMIP端点

  • 您在“指定证书”步骤中创建的tlsOptions对象

const autoEncryptionOptions = { keyVaultNamespace: keyVaultNamespace, kmsProviders: kmsProviderCredentials, tlsOptions,};

注意

自动加密选项

自动加密选项向自动加密共享库提供配置信息,这将修改应用程序在访问加密字段时的行为。

要了解有关自动加密共享库的更多信息,请参阅 Queryable Encryption 的自动加密共享库页面。

要创建用于对集合中的数据进行加密和解密的客户端,请使用您的连接 URI 和自动加密选项实例化一个新的 MongoClient。

const encryptedClient = Mongo(uri, autoEncryptionOptions);

如要加密字段,请将其添加到加密模式中。要启用对字段的查询,请添加“queries”属性。创建加密模式,如下所示:

const encryptedFieldsMap = { encryptedFields: { fields: [ { path: "patientRecord.ssn", bsonType: "string", queries: { queryType: "equality" }, }, { path: "patientRecord.billing", bsonType: "object", }, ], },};

注意

在前面的代码示例中,“ssn”和“billing”字段都经过加密,但只能查询“ssn”字段。

实例化 ClientEncryption 以访问加密辅助方法的 API。

const clientEncryption = encryptedClient.getClientEncryption()

使用可通过ClientEncryption类访问的加密助手方法创建加密集合。 此方法自动为加密字段生成数据加密密钥并创建加密集合:

await clientEncryption.createEncryptedCollection( encryptedDatabaseName, encryptedCollectionName, { provider: kmsProviderName, createCollectionOptions: encryptedFieldsMap, masterKey: customerMasterKeyCredentials, });
3

创建描述患者个人信息的示例文档。使用加密的客户端将其插入到 patients 集合中,如以下示例所示:

const patientDocument = { patientName: "Jon Doe", patientId: 12345678, patientRecord: { ssn: "987-65-4320", billing: { type: "Visa", number: "4111111111111111", }, },}; const encryptedCollection = encryptedClient.getDB(encryptedDatabaseName).getCollection(encryptedCollectionName); const insertResult = await encryptedCollection.insertOne(patientDocument);
4

下面的代码示例对加密字段执行查找查询,并打印解密后的数据:

const findResult = await encryptedCollection.findOne({ "patientRecord.ssn": "987-65-4320",});console.log(findResult);

上述代码示例的输出应类似于以下内容:

{ "_id": { "$oid": "648b384a722cb9b8392df76a" }, "name": "Jon Doe", "record": { "ssn": "987-65-4320", "billing": { "type": "Visa", "number": "4111111111111111" } }, "__safeContent__": [ { "$binary": { "base64": "L1NsYItk0Sg+oL66DBj6IYHbX7tveANQyrU2cvMzD9Y=", "subType": "00" } } ]}

警告

不要修改 __safeContent__ 字段

__safeContent__ 字段对于 Queryable Encryption 至关重要。请勿修改此字段的内容。

要学习;了解Queryable Encryption 的工作原理,请参阅Queryable Encryption基础知识。

如需详细了解本指南中提到的主题,请参阅以下链接:

  • 有关 Queryable Encryption 组件的更多信息,请参阅参考页面。

  • 在加密密钥和密钥保管库页面上了解客户主密钥和数据加密密钥的工作原理。

  • 在 KMS 提供商页面上查看 KMS 提供商如何管理您的可查询加密密钥。