使用 Always Encrypted 将加密数据批量加载到列中

适用于:SQL ServerAzure SQL 数据库Azure SQL 托管实例

若要在大容量复制作业期间加载加密数据而不在服务器上执行元数据检查,请使用选项 ALLOW_ENCRYPTED_VALUE_MODIFICATIONS 创建用户。 此选项旨在由无法使用 Always Encrypted 的旧工具或第三方 Extract-Transform-Load (ETL) 工作流使用。 这使用户可以安全地将加密数据从包含加密列的一组表中移动到具有加密列的另一组表中(在相同或不同的数据库中)。

ALLOW_ENCRYPTED_VALUE_MODIFICATIONS 选项

CREATE USERALTER USER 都有一个选项ALLOW_ENCRYPTED_VALUE_MODIFICATIONS。 设置为 ON (默认值为 OFF)时,此选项禁止在服务器上进行批量复制作中的加密元数据检查,这样用户就可以在表或数据库之间批量复制加密数据,而无需解密数据。

数据迁移应用场景

下表显示了适用于多个迁移方案的建议设置。

显示适用于多个迁移方案的建议设置的表的屏幕截图。

批量加载加密数据

使用以下过程加载加密数据。

  1. 为数据库中作为批量复制操作目标的用户设置选项ON。 例如:

     ALTER USER Bob WITH ALLOW_ENCRYPTED_VALUE_MODIFICATIONS = ON;
    
  2. 运行大容量复制的应用程序或作为该用户进行连接的工具。 (如果应用程序使用启用了 Always Encrypted 的客户端驱动程序,请确保数据源的连接字符串不包含 column encryption setting=enabled 以确保从加密列检索的数据保持加密状态。有关详细信息,请参阅 使用 Always Encrypted 开发应用程序

  3. ALLOW_ENCRYPTED_VALUE_MODIFICATIONS 选项设置回 OFF。 例如:

    ALTER USER Bob WITH ALLOW_ENCRYPTED_VALUE_MODIFICATIONS = OFF;
    

数据损坏的可能性

错误使用此选项可能导致数据损坏。 该 ALLOW_ENCRYPTED_VALUE_MODIFICATIONS 选项允许用户将任何数据插入数据库中的加密列中,包括使用不同密钥加密的数据、未正确加密或根本不加密的数据。 如果用户意外复制了未按目标列的加密方案(列加密密钥、算法、加密类型)正确加密的数据,则无法解密数据(数据已损坏)。 请慎用此选项,因为它将导致数据库中的数据损坏。

下面的方案演示了因错误导入数据而导致数据损坏的方法:

  1. 选项为用户设置为 ON

  2. 用户运行连接到数据库的应用程序。 应用程序使用大容量 API 将纯文本值插入到加密列中。 应用程序需要启用了始终加密的客户端驱动程序对插入的数据进行加密。 但是,应用程序配置不正确,因此它最终使用不支持 Always Encrypted 的驱动程序或连接字符串不包含 column encryption setting=enabled

  3. 应用程序向服务器发送纯文本值。 由于针对用户在服务器中禁用了加密元数据检查,因此该服务器可让不正确的数据(纯文本而不是正确加密的已加密文本)插入到加密列中。

  4. 同一应用程序或其他应用程序使用启用了 Always Encrypted 的驱动程序连接到数据库,并在 column encryption setting=enabled 连接字符串中检索数据。 应用程序要求以透明方式解密数据。 但是,由于数据是错误的密文,因此驱动程序无法解密此数据。

最佳做法

针对使用此选项的长时间运行的工作负荷,使用指定的用户帐户。

对于运行时间短的批量复制应用程序或需要移动加密数据而不解密的工具,请在运行应用程序之前立即将选项设置为 ON,在运行操作之后立即将其设置回 OFF。

不要使用此选项开发新应用程序。 请改用提供 API 的客户端驱动程序来禁止对单个会话进行加密元数据检查,例如 AllowEncryptedValueModifications 适用于 SQL Server 的 .NET Framework 数据提供程序中的选项 - 请参阅 使用 SqlBulkCopy 复制加密数据