使用 PowerShell 就地設定資料行加密

適用於:SQL ServerAzure SQL DatabaseAzure SQL 受控執行個體

本文逐步說明如何使用 SqlServer PowerShell 模組中的 Set-SqlColumnEncryption Cmdlet,為資料庫資料行設定目標永遠加密組態。 Set-SqlColumnEncryption Cmdlet 會同時修改目標資料庫的結構描述及儲存在所選資料行中的資料。 您可以根據資料行的指定目標加密設定和目前的加密組態,對儲存在資料行中的資料進行加密、重新加密或解密。 若要使用記憶體保護區來觸發就地密碼編譯作業,Set-SqlColumnEncryption 必須使用使用連接字串建立的資料庫連線搭配證明通訊協定,以及選擇性地使用證明 URL 關鍵字。

必要條件

若要設定目標加密組態,您必須確定:

  • 資料庫中已設定啟用了記憶體保護區的資料行加密金鑰 (如果您要加密或重新加密資料行)。 如需詳細資訊,請參閱針對具有安全記憶體保護區的 Always Encrypted 管理金鑰
  • 您已連線到啟用了 Always Encrypted 的資料庫,以及連接字串中指定的證明屬性。
  • 您可以從電腦執行 PowerShell Cmdlet,以存取您要加密、重新加密或解密之每個資料行的資料行主要金鑰。
  • 您使用 SqlServer PowerShell 模組 22.0.50 版或更新版本。

可用性考量

就地 Set-SqlColumnEncryption Cmdlet 不支援線上加密。

使用離線方法時,目標資料表 (以及與目標資料表相關的所有資料表,例如,與目標資料表具有外部索引鍵關聯性的所有資料表) 無法在作業持續期間寫入交易。 使用離線方法時,一律會保留外部索引鍵條件約束的語意 (CHECKNOCHECK)。

如果您在加密程式期間負擔不起停機費用,建議您使用透過 Transact-SQL 就地設定資料行加密,以支援線上加密。

安全性考量

用來設定資料庫資料行加密的 Set-SqlColumnEncryption Cmdlet,會處理永遠加密金鑰和儲存在資料庫資料行中的資料。 因此,請務必在安全的電腦上執行 Cmdlet。 如果您的資料庫在 SQL Server 上,請從與裝載您的 SQL Server 執行個體不同的電腦上執行 Cmdlet。 因為永遠加密的主要目標是為了確保已加密的敏感性資料安全無虞,即使資料庫系統遭到入侵亦然,所以在 SQL Server 電腦上執行處理金鑰和/或敏感性資料的 PowerShell 指令碼,可能會降低或損害此功能的優點。

Task 發行項 存取純文字金鑰/金鑰存放區 存取資料庫
步驟 1: 啟動 PowerShell 環境並匯入 SqlServer 模組。 匯入 SqlServer 模組
步驟 2: 連接到您的伺服器和資料庫 連線至資料庫
步驟 3: 如果您的資料行主要金鑰 (用於保護資料行加密金鑰並需要更換) 儲存在 Azure 金鑰保存庫中,請向 Azure 驗證 Connect-AzAccount
步驟 4: 取得 Azure Key Vault 的存取權杖。 Get-AzAccessToken No
步驟 5。 建構 SqlColumnEncryptionSettings 物件的陣列 - 您要加密、重新加密或解密的每個資料庫資料行各有一個物件。 SqlColumnMasterKeySettings 是存在於 PowerShell 記憶體中的物件。 它會指定資料行的目標加密配置。 New-SqlColumnEncryptionSettings
步驟 5。 針對您在上一個步驟中建立的 SqlColumnMasterKeySettings 物件陣列,設定在其中指定的所需加密組態。 將會根據資料行的指定目標設定和目前的加密組態,對資料行進行加密、重新加密或解密。 Set-SqlColumnEncryption

注意︰ 此步驟可能需要很長的時間。 根據您選取的方法 (線上與離線) 而定,您的應用程式可能無法在整個作業期間或作業的部分期間存取資料表。
Yes

使用 VBS 記憶體保護區加密資料行

下列範例示範如何設定兩個資料行的目標加密組態。 若有任何一個資料行尚未經過加密,將會對其進行加密。 若有任何資料行已使用不同的金鑰和/或不同的加密類型加密,則會將它解密,然後使用指定的目標金鑰/類型重新加密。 VBS 記憶體保護區目前不支援證明。 EnclaveAttestationProtocol 參數應該設定為,且不需要 EnclaveAttestationUrl。

# Import modules
Import-Module "SqlServer" -MinimumVersion 22.0.50
Import-Module Az.Accounts -MinimumVersion 2.2.0

#Connect to Azure
Connect-AzAccount

# Obtain an access token for key vaults.
$keyVaultAccessToken = (Get-AzAccessToken -ResourceUrl https://vault.azure.net).Token  

# Connect to your database.
$serverName = "<servername>.database.windows.net"
$databaseName = "<DatabaseName>"
# Change the authentication method in the connection string, if needed.
$connStr = "Server = " + $serverName + "; Database = " + $databaseName + ";  Integrated Security = True"
$database = Get-SqlDatabase -ConnectionString $connStr

# Encrypt the selected columns (or re-encrypt, if they are already encrypted using keys/encrypt types, different than the specified keys/types.
$ces = @() 
$ces += New-SqlColumnEncryptionSettings -ColumnName "dbo.Employees.SSN" -EncryptionType "Randomized" -EncryptionKey "CEK" 
$ces += New-SqlColumnEncryptionSettings -ColumnName "dbo.Employees.Salary" -EncryptionType "Randomized" -EncryptionKey "CEK" 
Set-SqlColumnEncryption -InputObject $database -ColumnEncryptionSettings $ces -LogFileDirectory . -EnclaveAttestationProtocol "None" -KeyVaultAccessToken $keyVaultAccessToken

解密資料行 - 範例

下列範例示範如何解密目前在資料庫中加密的所有資料行。

# Import modules
Import-Module "SqlServer" -MinimumVersion 22.0.50
Import-Module Az.Accounts -MinimumVersion 2.2.0

#Connect to Azure
Connect-AzAccount

# Obtain an access token for key vaults.
$keyVaultAccessToken = (Get-AzAccessToken -ResourceUrl https://vault.azure.net).Token  

# Connect to your database.
$serverName = "<server name>"
$databaseName = "<database name>"
# Change the authentication method in the connection string, if needed.
$connStr = "Server = " + $serverName + "; Database = " + $databaseName + "; Integrated Security = True"
$database = Get-SqlDatabase -ConnectionString $connStr

# Find all encrypted columns, and create a SqlColumnEncryptionSetting object for each column.
$ces = @()
$tables = $database.Tables
for($i=0; $i -lt $tables.Count; $i++){
    $columns = $tables[$i].Columns
    for($j=0; $j -lt $columns.Count; $j++) {
        if($columns[$j].isEncrypted) {
            $threeColPartName = $tables[$i].Schema + "." + $tables[$i].Name + "." + $columns[$j].Name 
            $ces += New-SqlColumnEncryptionSettings -ColumnName $threeColPartName -EncryptionType "Plaintext" 
        }
    }
}

# Decrypt all columns.
Set-SqlColumnEncryption -ColumnEncryptionSettings $ces -InputObject $database -LogFileDirectory . -EnclaveAttestationProtocol "None" -KeyVaultAccessToken $keyVaultAccessToken

使用 SGX 記憶體保護區加密資料行

下列範例示範如何設定兩個資料行的目標加密組態。 若有任何一個資料行尚未經過加密,將會對其進行加密。 若有任何資料行已使用不同的金鑰和/或不同的加密類型加密,則會將它解密,然後使用指定的目標金鑰/類型重新加密。 若要使用記憶體保護區觸發就地密碼編譯作業,需要 EnclaveAttestationProtocol 和 EnclaveAttestationUrl 參數。

# Import modules
Import-Module "SqlServer" -MinimumVersion 22.0.50
Import-Module Az.Accounts -MinimumVersion 2.2.0

#Connect to Azure
Connect-AzAccount

# Obtain an access token for key vaults.
$keyVaultAccessToken = (Get-AzAccessToken -ResourceUrl https://vault.azure.net).Token  

# Connect to your database.
$serverName = "<servername>.database.windows.net"
$databaseName = "<DatabaseName>"
# Change the authentication method in the connection string, if needed.
$connStr = "Server = " + $serverName + "; Database = " + $databaseName + ";  Integrated Security = True"
$database = Get-SqlDatabase -ConnectionString $connStr

# Encrypt the selected columns (or re-encrypt, if they are already encrypted using keys/encrypt types, different than the specified keys/types.
$ces = @() 
$ces += New-SqlColumnEncryptionSettings -ColumnName "dbo.Employees.SSN" -EncryptionType "Randomized" -EncryptionKey "CEK" 
$ces += New-SqlColumnEncryptionSettings -ColumnName "dbo.Employees.Salary" -EncryptionType "Randomized" -EncryptionKey "CEK" 
Set-SqlColumnEncryption -InputObject $database -ColumnEncryptionSettings $ces -LogFileDirectory . -EnclaveAttestationProtocol "AAS" -EnclaveAttestationURL "https://<attestationURL>"   -KeyVaultAccessToken $keyVaultAccessToken

解密資料行 - 範例

下列範例示範如何解密目前在資料庫中加密的所有資料行。

# Import modules
Import-Module "SqlServer" -MinimumVersion 22.0.50
Import-Module Az.Accounts -MinimumVersion 2.2.0

#Connect to Azure
Connect-AzAccount

# Obtain an access token for key vaults.
$keyVaultAccessToken = (Get-AzAccessToken -ResourceUrl https://vault.azure.net).Token  

# Connect to your database.
$serverName = "<server name>"
$databaseName = "<database name>"
# Change the authentication method in the connection string, if needed.
$connStr = "Server = " + $serverName + "; Database = " + $databaseName + "; Integrated Security = True"
$database = Get-SqlDatabase -ConnectionString $connStr

# Find all encrypted columns, and create a SqlColumnEncryptionSetting object for each column.
$ces = @()
$tables = $database.Tables
for($i=0; $i -lt $tables.Count; $i++){
    $columns = $tables[$i].Columns
    for($j=0; $j -lt $columns.Count; $j++) {
        if($columns[$j].isEncrypted) {
            $threeColPartName = $tables[$i].Schema + "." + $tables[$i].Name + "." + $columns[$j].Name 
            $ces += New-SqlColumnEncryptionSettings -ColumnName $threeColPartName -EncryptionType "Plaintext" 
        }
    }
}

# Decrypt all columns.
Set-SqlColumnEncryption -ColumnEncryptionSettings $ces -InputObject $database -LogFileDirectory . -EnclaveAttestationProtocol "AAS" -EnclaveAttestationURL "https://<attestationURL>" -KeyVaultAccessToken $keyVaultAccessToken

下一步

另請參閱