Remarque
L’accès à cette page nécessite une autorisation. Vous pouvez essayer de vous connecter ou de modifier des répertoires.
L’accès à cette page nécessite une autorisation. Vous pouvez essayer de modifier des répertoires.
S’applique à :SQL Server
Azure SQL Database
Azure SQL Managed Instance
Cet article décrit les étapes de la mise en service de clés pour Always Encrypted à l’aide du module SqlServer PowerShell. Vous pouvez utiliser PowerShell pour mettre en service des clés Always Encrypted à la fois avec et sans séparation des rôles, ce qui permet de contrôler qui a accès aux clés de chiffrement réelles dans le magasin de clés et qui a accès à la base de données.
Note
Microsoft recommande d’utiliser PowerShell 7 ou version ultérieure lors de l’exécution de scripts PowerShell Always Encrypted. PowerShell 7 offre une prise en charge multiplateforme améliorée, de meilleures performances et la dernière compatibilité avec le module SqlServer (v22+), qui est nécessaire pour de nombreux scénarios Always Encrypted.
Pour obtenir une vue d’ensemble de la gestion des clés Always Encrypted, notamment des recommandations de bonnes pratiques générales, consultez Vue d’ensemble de la gestion des clés pour Always Encrypted. Pour plus d’informations sur l’utilisation du module SqlServer PowerShell pour Always Encrypted, consultez Configurer Always Encrypted à l’aide de PowerShell.
Approvisionnement de clés sans séparation des rôles
La méthode d’approvisionnement de clé décrite dans cette section ne prend pas en charge la séparation des rôles entre les administrateurs de sécurité et les administrateurs de base de données. Certaines des étapes de cette section combinent des opérations sur des clés physiques avec des opérations sur les métadonnées de clé. Par conséquent, utilisez cette méthode d’approvisionnement des clés si votre organisation utilise le modèle DevOps, ou si la base de données est hébergée dans le cloud et que l’objectif principal est de restreindre les administrateurs cloud (mais pas les administrateurs de base de données locaux) à accéder aux données sensibles. N’utilisez pas cette méthode si les adversaires potentiels incluent des administrateurs de base de données ou si les administrateurs de base de données ne doivent pas avoir accès aux données sensibles.
Avant d’exécuter les étapes qui impliquent l’accès aux clés en texte clair ou au magasin de clés (identifié dans la colonne Accéder aux clés en texte clair/magasin de clés dans le tableau suivant), assurez-vous que l’environnement PowerShell s’exécute sur un ordinateur sécurisé différent d’un ordinateur hébergeant votre base de données. Pour plus d’informations, consultez Considérations en matière de sécurité pour la gestion des clés.
| Tâche | Article | Accès aux clés en texte brut/au stockage de clés | Accède à la base de données |
|---|---|---|---|
| Étape 1. Créer une clé maîtresse de colonne dans un magasin de clés. Note : Le module SqlServer PowerShell ne prend pas en charge cette étape. Pour accomplir cette tâche à partir d’une ligne de commande, utilisez les outils qui sont spécifiques à votre magasin de clés sélectionné. |
Créer et stocker des clés principales de colonne pour Always Encrypted | Oui | Non |
| Étape 2. Démarrer un environnement PowerShell et importer le module SqlServer PowerShell. | Configurer Always Encrypted à l’aide de PowerShell | Non | Non |
| Étape 3. Se connecter à votre serveur et à la base de données. | Se connecter à une base de données | Non | Oui |
| Étape 4. Créer un objet SqlColumnMasterKeySettings qui contient des informations sur l’emplacement de votre clé principale de colonne. SqlColumnMasterKeySettings est un objet qui existe en mémoire (dans PowerShell). Utilisez l’applet de commande qui est spécifique à votre magasin de clés. |
New-SqlAzureKeyVaultColumnMasterKeySettings New-SqlCertificateStoreColumnMasterKeySettings new-SqlCngColumnMasterKeySettings new-SqlCspColumnMasterKeySettings |
Non | Non |
| Étape 5. Créer les métadonnées relatives à la clé principale de colonne dans votre base de données. Note: Nous ne vérifions pas la validité des clés ou certificats utilisés pour générer la clé principale de colonne. |
[New-SqlColumnMasterKey](/powershell/sqlserver/sqlserver/vlatest/new-sqlcolumnmasterkey Remarque : sous les couvertures, l’applet de commande émet l’instruction CREATE COLUMN MASTER KEY pour créer des métadonnées de clé. |
Non | Oui |
| Étape 6. S’authentifier auprès d’Azure, si votre clé principale de colonne est stockée dans Azure Key Vault. | Connect-AzAccount | Oui | Non |
| Étape 7. Obtenez un jeton d’accès pour Azure Key Vaults, si votre clé principale de colonne est stockée dans Azure Key Vault. | Get-AzAccessToken | Non | Non |
| Étape 8 : Générer une clé de chiffrement de colonne, la chiffrer avec la clé principale de colonne et créer les métadonnées de clé de chiffrement de colonne dans la base de données. |
New-SqlColumnEncryptionKey Remarque : Utilisez une variation de l’applet de commande qui génère et chiffre en interne une clé de chiffrement de colonne. Note: Sous les couvertures, l’applet de commande émet l’instruction CREATE COLUMN ENCRYPTION KEY pour créer des métadonnées de clé. |
Oui | Oui |
Magasin de certificats Windows sans séparation des rôles (exemple)
Ce script est un exemple de bout en bout de génération d’une clé principale de colonne qui est un certificat dans le magasin de certificats Windows, de génération et de chiffrement d’une clé de chiffrement de colonne, et de création de métadonnées de clé dans une base de données SQL Server.
[CmdletBinding()]
param(
[Parameter(Mandatory = $false)]
[string]$DatabaseName = '<database name>',
[Parameter(Mandatory = $false)]
[string]$ServerName = "<server name>",
[Parameter(Mandatory = $false)]
[string]$CertificateSubject = "AlwaysEncryptedCert",
[Parameter(Mandatory = $false)]
[string]$CmkName = "CMK",
[Parameter(Mandatory = $false)]
[string]$CekName = "CEK"
)
Set-StrictMode -Version Latest
$ErrorActionPreference = "Stop"
Import-Module SqlServer -MinimumVersion 22.0.50 -ErrorAction Stop
Write-Host "[AE] Locating certificate '$CertificateSubject' in CurrentUser\\My"
$cert = Get-ChildItem -Path Cert:CurrentUser\My |
Where-Object { $_.Subject -eq "CN=$CertificateSubject" } |
Sort-Object NotAfter -Descending |
Select-Object -First 1
if (-not $cert) {
Write-Host "[AE] Certificate not found. Creating self-signed certificate."
$cert = New-SelfSignedCertificate `
-Subject $CertificateSubject `
-CertStoreLocation Cert:CurrentUser\My `
-KeyExportPolicy Exportable `
-Type DocumentEncryptionCert `
-KeyUsage DataEncipherment `
-KeySpec KeyExchange
}
Write-Host "[AE] Connecting to SQL Server '$ServerName' / Database '$DatabaseName'"
$connStr = "Server=$ServerName;Database=$DatabaseName;Integrated Security=True;Encrypt=True;TrustServerCertificate=True;Connection Timeout=30"
try {
$database = Get-SqlDatabase -ConnectionString $connStr -ErrorAction Stop
}
catch {
Write-Error "Failed to connect to '$ServerName' database '$DatabaseName'. Verify instance name SQL2025, database existence, and local permissions."
throw
}
Write-Host "[AE] Creating CMK settings from certificate thumbprint"
$cmkSettings = New-SqlCertificateStoreColumnMasterKeySettings -CertificateStoreLocation "CurrentUser" -Thumbprint $cert.Thumbprint
Write-Host "[AE] Ensuring CMK '$CmkName' exists"
$existingCmk = Get-SqlColumnMasterKey -InputObject $database | Where-Object { $_.Name -eq $CmkName }
if (-not $existingCmk) {
New-SqlColumnMasterKey -Name $CmkName -InputObject $database -ColumnMasterKeySettings $cmkSettings | Out-Null
}
Write-Host "[AE] Ensuring CEK '$CekName' exists"
$existingCek = Get-SqlColumnEncryptionKey -InputObject $database | Where-Object { $_.Name -eq $CekName }
if (-not $existingCek) {
New-SqlColumnEncryptionKey -Name $CekName -InputObject $database -ColumnMasterKey $CmkName | Out-Null
}
Write-Host "Completed successfully"
Azure Key Vault sans séparation des rôles (exemple)
Ce script est un exemple de bout en bout de provisionnement et de configuration d’un coffre de clés dans Azure Key Vault, de génération d’une clé principale de colonne dans le coffre, de génération et de chiffrement d’une clé de chiffrement de colonne, et de création de métadonnées de clé dans une base de données Azure SQL.
param(
[Parameter(Mandatory = $true)] [string]$SubscriptionId,
[Parameter(Mandatory = $true)] [string]$ResourceGroupName,
[Parameter(Mandatory = $true)] [string]$AzureLocation,
[Parameter(Mandatory = $true)] [string]$KeyVaultName,
[Parameter(Mandatory = $true)] [string]$KeyName,
[Parameter(Mandatory = $true)] [string]$ServerName,
[Parameter(Mandatory = $true)] [string]$DatabaseName,
[string]$CmkName = "CMK",
[string]$CekName = "CEK",
[bool]$AssignRbacToCurrentPrincipal = $true
)
Set-StrictMode -Version Latest
$ErrorActionPreference = "Stop"
Import-Module Az.Accounts -ErrorAction Stop
Import-Module Az.Resources -ErrorAction Stop
Import-Module Az.KeyVault -ErrorAction Stop
Import-Module SqlServer -ErrorAction Stop
function Get-CurrentPrincipalObjectId {
param([string]$AccountId)
$userSignedIn = Get-AzADUser -SignedIn -ErrorAction SilentlyContinue
if ($userSignedIn) { return $userSignedIn.Id }
$user = Get-AzADUser -UserPrincipalName $AccountId -ErrorAction SilentlyContinue
if ($user) { return $user.Id }
$sp = Get-AzADServicePrincipal -DisplayName $AccountId -ErrorAction SilentlyContinue | Select-Object -First 1
if ($sp) { return $sp.Id }
throw "Could not resolve Microsoft Entra object id for account '$AccountId'."
}
try {
Write-Host "[AE] Signing in and selecting subscription"
Connect-AzAccount | Out-Null
$ctx = Set-AzContext -SubscriptionId $SubscriptionId
Write-Host "[AE] Ensuring resource group exists"
$resourceGroup = Get-AzResourceGroup -Name $ResourceGroupName -ErrorAction SilentlyContinue
if (-not $resourceGroup) {
$resourceGroup = New-AzResourceGroup -Name $ResourceGroupName -Location $AzureLocation
}
Write-Host "[AE] Ensuring key vault exists (RBAC mode)"
$vault = Get-AzKeyVault -VaultName $KeyVaultName -ResourceGroupName $ResourceGroupName -ErrorAction SilentlyContinue
if (-not $vault) {
$vault = New-AzKeyVault -VaultName $KeyVaultName -ResourceGroupName $ResourceGroupName -Location $AzureLocation -EnableRbacAuthorization
}
if (-not $vault.EnableRbacAuthorization) {
throw "Key Vault '$KeyVaultName' is not using RBAC authorization. Enable RBAC authorization on the vault before running this script."
}
if ($AssignRbacToCurrentPrincipal) {
Write-Host "[AE] Ensuring RBAC role assignment"
$principalSignInName = $ctx.Account.Id
$roleName = "Key Vault Crypto Officer"
$existingRole = Get-AzRoleAssignment -SignInName $principalSignInName -Scope $vault.ResourceId -RoleDefinitionName $roleName -ErrorAction SilentlyContinue
if (-not $existingRole) {
New-AzRoleAssignment -SignInName $principalSignInName -Scope $vault.ResourceId -RoleDefinitionName $roleName | Out-Null
}
}
Write-Host "[AE] Ensuring column master key material exists in Key Vault"
$akvKey = Get-AzKeyVaultKey -VaultName $KeyVaultName -Name $KeyName -ErrorAction SilentlyContinue
if (-not $akvKey) {
$akvKey = Add-AzKeyVaultKey -VaultName $KeyVaultName -Name $KeyName -Destination "Software"
}
Write-Host "[AE] Connecting to Azure SQL and creating metadata"
$keyVaultAccessToken = (Get-AzAccessToken -ResourceUrl "https://vault.azure.net").Token
$connStr = "Server=tcp:$ServerName.database.windows.net,1433;Database=$DatabaseName;Encrypt=True;TrustServerCertificate=False;Connection Timeout=30;Authentication=Active Directory Interactive"
$database = Get-SqlDatabase -ConnectionString $connStr -Encrypt Mandatory
$cmkSettings = New-SqlAzureKeyVaultColumnMasterKeySettings -KeyUrl $akvKey.Key.Kid
$existingCmk = Get-SqlColumnMasterKey -InputObject $database | Where-Object { $_.Name -eq $CmkName }
if (-not $existingCmk) {
New-SqlColumnMasterKey -Name $CmkName -InputObject $database -ColumnMasterKeySettings $cmkSettings | Out-Null
}
$existingCek = Get-SqlColumnEncryptionKey -InputObject $database | Where-Object { $_.Name -eq $CekName }
if (-not $existingCek) {
New-SqlColumnEncryptionKey -Name $CekName -InputObject $database -ColumnMasterKey $CmkName -KeyVaultAccessToken $keyVaultAccessToken | Out-Null
}
Write-Host "Completed successfully"
}
catch {
Write-Error "Script failed: $($_.Exception.Message)"
throw
}
CNG/KSP sans séparation de rôle (exemple)
Le script ci-dessous est un exemple de bout en bout de génération d’une clé principale de colonne dans un magasin de clés qui implémente l’API CNG (Cryptography Next Generation), de génération et de chiffrement d’une clé de chiffrement de colonne, et de création de métadonnées de clé dans une base de données SQL Server.
L’exemple utilise le magasin de clés qui utilise le fournisseur de stockage de clés logicielles Microsoft. Vous pouvez choisir de modifier l’exemple pour utiliser un autre stockage, tel que votre module de sécurité matériel. Pour cela, vous devez vous assurer que le fournisseur de magasin de clés (KSP) qui implémente CNG pour votre appareil est installé et correctement configuré sur votre machine. Vous devez remplacer Microsoft Software Key Storage Provider par le nom KSP de votre appareil.
[CmdletBinding()]
param(
[Parameter(Mandatory = $false)]
[string]$ServerName = "<server name>",
[Parameter(Mandatory = $true)]
[string]$DatabaseName = "<database name>",
[Parameter(Mandatory = $false)]
[string]$CngKeyName = "AlwaysEncryptedKey",
[Parameter(Mandatory = $false)]
[string]$CmkName = "CMK",
[Parameter(Mandatory = $false)]
[string]$CekName = "CEK"
)
Set-StrictMode -Version Latest
$ErrorActionPreference = "Stop"
# Local key store provider and key settings.
$cngProviderName = "Microsoft Software Key Storage Provider"
$cngAlgorithmName = "RSA"
$cngKeySize = 2048
Import-Module SqlServer -ErrorAction Stop
Write-Host "[AE] Creating local CNG key '$CngKeyName'"
$cngProvider = New-Object System.Security.Cryptography.CngProvider($cngProviderName)
$cngKeyParams = New-Object System.Security.Cryptography.CngKeyCreationParameters
$cngKeyParams.Provider = $cngProvider
$cngKeyParams.KeyCreationOptions = [System.Security.Cryptography.CngKeyCreationOptions]::OverwriteExistingKey
$keySizeProperty = New-Object System.Security.Cryptography.CngProperty(
"Length",
[System.BitConverter]::GetBytes($cngKeySize),
[System.Security.Cryptography.CngPropertyOptions]::None
)
$cngKeyParams.Parameters.Add($keySizeProperty)
$cngAlgorithm = New-Object System.Security.Cryptography.CngAlgorithm($cngAlgorithmName)
[System.Security.Cryptography.CngKey]::Create($cngAlgorithm, $CngKeyName, $cngKeyParams) | Out-Null
Write-Host "[AE] Connecting to $ServerName / $DatabaseName"
$connStr = "Server=$ServerName;Database=$DatabaseName;Integrated Security=True;Encrypt=True;TrustServerCertificate=True"
$database = Get-SqlDatabase -ConnectionString $connStr
Write-Host "[AE] Preparing column master key settings"
$cmkSettings = New-SqlCngColumnMasterKeySettings -CngProviderName $cngProviderName -KeyName $CngKeyName
Write-Host "[AE] Ensuring CMK exists"
$existingCmk = Get-SqlColumnMasterKey -InputObject $database | Where-Object { $_.Name -eq $CmkName }
if (-not $existingCmk) {
New-SqlColumnMasterKey -Name $CmkName -InputObject $database -ColumnMasterKeySettings $cmkSettings | Out-Null
}
Write-Host "[AE] Ensuring CEK exists"
$existingCek = Get-SqlColumnEncryptionKey -InputObject $database | Where-Object { $_.Name -eq $CekName }
if (-not $existingCek) {
New-SqlColumnEncryptionKey -Name $CekName -InputObject $database -ColumnMasterKey $CmkName | Out-Null
}
Write-Host "Completed successfully"
Approvisionnement en clés avec séparation des rôles
Cette section présente les étapes de la configuration du chiffrement où les administrateurs de la sécurité n’ont pas accès à la base de données et les administrateurs de bases de données n’ont pas accès au magasin de clés ni aux clés en texte clair.
Administrateur de sécurité
Avant d’exécuter les étapes qui impliquent l’accès aux clés en texte clair ou au magasin de clés (identifiés dans la colonne Accéder aux clés en texte clair/magasin de clés dans le tableau suivant), assurez-vous que :
- L’environnement PowerShell s’exécute sur une machine sécurisée qui est différente d’un ordinateur qui héberge votre base de données.
- Les administrateurs de bases de données de votre organisation n’ont aucun accès à l’ordinateur (ce serait en opposition avec l’objectif de la séparation des rôles).
Pour plus d’informations, consultez Considérations en matière de sécurité pour la gestion des clés.
| Tâche | Article | Accès aux clés en texte brut/au stockage de clés | Accède à la base de données |
|---|---|---|---|
| Étape 1. Créer une clé maîtresse de colonne dans un magasin de clés. Note : Le module SqlServer ne prend pas en charge cette étape. Pour accomplir cette tâche à partir d’une ligne de commande, vous devez utiliser les outils propres au type de votre magasin de clés. |
Créer et stocker des clés principales de colonne pour Always Encrypted | Oui | Non |
| Étape 2. Démarrer une session PowerShell et importer le module SqlServer. | Importer le module SqlServer | Non | Non |
| Étape 3. Créer un objet SqlColumnMasterKeySettings qui contient des informations sur l’emplacement de votre clé principale de colonne. SqlColumnMasterKeySettings est un objet qui existe en mémoire (dans PowerShell). Utilisez l’applet de commande qui est spécifique à votre magasin de clés. |
New-SqlAzureKeyVaultColumnMasterKeySettings New-SqlCertificateStoreColumnMasterKeySettings new-SqlCngColumnMasterKeySettings new-SqlCspColumnMasterKeySettings |
Non | Non |
| Étape 4. S’authentifier auprès d’Azure, si votre clé principale de colonne est stockée dans Azure Key Vault. | Connect-AzAccount | Oui | Non |
| Étape 5. Obtenez un jeton d’accès pour Azure Key Vaults, si votre clé principale de colonne est stockée dans Azure Key Vault. | Get-AzAccessToken | Non | Non |
| Étape 6. Générer une clé de chiffrement de colonne, la chiffrer avec la clé principale de colonne pour produire une valeur chiffrée de la clé de chiffrement de colonne. | New-SqlColumnEncryptionKeyEncryptedValue | Oui | Non |
| Étape 7. Fournir l’emplacement de la clé principale de colonne (nom du fournisseur et chemin d’accès à la clé principale de colonne) et une valeur chiffrée de la clé de chiffrement de colonne à l’administrateur de base de données. | Consultez les exemples à la fin de l’article. | Non | Non |
DBA
Les administrateurs de bases de données utilisent les informations qu’ils reçoivent de l’administrateur de la sécurité (étape 7 ci-dessus) pour créer et gérer les métadonnées de clé Always Encrypted dans la base de données.
| Tâche | Article | Accède aux clés en texte clair | Accède à la base de données |
|---|---|---|---|
| Étape 1. Obtenez l’emplacement de la clé maître de colonne et la valeur chiffrée de la clé de chiffrement de colonne auprès de votre administrateur de la sécurité. | Consultez les exemples à la fin de l’article. | Non | Non |
| Étape 2. Démarrer un environnement PowerShell et importer le module SqlServer. | Configurer Always Encrypted à l’aide de PowerShell | Non | Non |
| Étape 3. Se connecter à votre serveur et à une base de données. | Se connecter à une base de données | Non | Oui |
| Étape 4. Créer un objet SqlColumnMasterKeySettings qui contient des informations sur l’emplacement de votre clé principale de colonne. SqlColumnMasterKeySettings est un objet qui existe en mémoire. | New-SqlColumnMasterKeySettings | Non | Non |
| Étape 5. Créer les métadonnées relatives à la clé principale de colonne dans votre base de données. Note: Nous ne vérifions pas la validité des clés ou certificats utilisés pour générer la clé principale de colonne. |
New-SqlColumnMasterKey Remarque : sous les couvertures, l’applet de commande émet l’instruction CREATE COLUMN MASTER KEY (Transact-SQL) pour créer des métadonnées de clé principale de colonne. |
Non | Oui |
| Étape 6. Créer les métadonnées de clé de chiffrement de colonne dans la base de données. | New-SqlColumnEncryptionKey Remarque : Les administrateurs de bases de données utilisent une variation de l’applet de commande qui crée uniquement des métadonnées de clé de chiffrement de colonne. Sous les couvertures, l’applet de commande émet l’instruction CREATE COLUMN ENCRYPTION KEY (Transact-SQL) pour créer des métadonnées de clé de chiffrement de colonne. |
Non | Oui |
Magasin de certificats Windows avec séparation des rôles (exemple)
Administrateur de sécurité
[CmdletBinding()]
param(
[Parameter(Mandatory = $false)]
[string]$ServerName = '<server name>',
[Parameter(Mandatory = $false)]
[ValidateNotNullOrEmpty()]
[string]$DatabaseName = '<database name>',
[Parameter(Mandatory = $false)]
[string]$CertificateSubject = 'AlwaysEncryptedCert',
[Parameter(Mandatory = $false)]
[string]$CmkName = 'CMK1',
[Parameter(Mandatory = $false)]
[string]$CekName = 'CEK1',
[Parameter(Mandatory = $false)]
[string]$ExportKeyDataPath = 'C:\temp\keydata.txt'
)
Set-StrictMode -Version Latest
$ErrorActionPreference = 'Stop'
Import-Module SqlServer -MinimumVersion 22.0.50 -ErrorAction Stop
Write-Host "[AE] Finding certificate '$CertificateSubject' in CurrentUser\\My"
$cert = Get-ChildItem -Path 'Cert:CurrentUser\My' |
Where-Object { $_.Subject -eq "CN=$CertificateSubject" } |
Sort-Object NotAfter -Descending |
Select-Object -First 1
if (-not $cert) {
Write-Host '[AE] Certificate not found. Creating a new self-signed certificate.'
$cert = New-SelfSignedCertificate `
-Subject $CertificateSubject `
-CertStoreLocation 'Cert:CurrentUser\My' `
-KeyExportPolicy Exportable `
-Type DocumentEncryptionCert `
-KeyUsage DataEncipherment `
-KeySpec KeyExchange
}
Write-Host "[AE] Connecting to SQL Server '$ServerName' / Database '$DatabaseName'"
$connStr = "Server=$ServerName;Database=$DatabaseName;Integrated Security=True;Encrypt=True;TrustServerCertificate=True;Connection Timeout=30"
try {
$database = Get-SqlDatabase -ConnectionString $connStr -ErrorAction Stop
}
catch {
Write-Error "Failed to connect to '$ServerName' / '$DatabaseName'. Verify instance name, database, and local permissions."
throw
}
Write-Host '[AE] Building CMK settings from certificate'
$cmkSettings = New-SqlCertificateStoreColumnMasterKeySettings -CertificateStoreLocation 'CurrentUser' -Thumbprint $cert.Thumbprint
Write-Host "[AE] Ensuring CMK '$CmkName' exists"
$existingCmk = Get-SqlColumnMasterKey -InputObject $database | Where-Object { $_.Name -eq $CmkName }
if (-not $existingCmk) {
New-SqlColumnMasterKey -Name $CmkName -InputObject $database -ColumnMasterKeySettings $cmkSettings | Out-Null
}
Write-Host "[AE] Ensuring CEK '$CekName' exists"
$existingCek = Get-SqlColumnEncryptionKey -InputObject $database | Where-Object { $_.Name -eq $CekName }
if (-not $existingCek) {
New-SqlColumnEncryptionKey -Name $CekName -InputObject $database -ColumnMasterKey $CmkName | Out-Null
}
if ($ExportKeyDataPath) {
Write-Host "[AE] Exporting key metadata to '$ExportKeyDataPath'"
$encryptedValue = New-SqlColumnEncryptionKeyEncryptedValue -TargetColumnMasterKeySettings $cmkSettings
"KeyStoreProviderName,KeyPath,EncryptedValue" | Set-Content -Path $ExportKeyDataPath -Encoding UTF8
"$($cmkSettings.KeyStoreProviderName),$($cmkSettings.KeyPath),$encryptedValue" | Add-Content -Path $ExportKeyDataPath -Encoding UTF8
}
Write-Host 'Completed successfully'
DBA
[CmdletBinding()]
param(
[Parameter(Mandatory = $false)]
[string]$ServerName = 'localhost\SQL2025',
[Parameter(Mandatory = $false)]
[ValidateNotNullOrEmpty()]
[string]$DatabaseName = 'AdventureWorks2025',
[Parameter(Mandatory = $false)]
[ValidateNotNullOrEmpty()]
[string]$KeyDataFile = 'C:\temp\keydata.txt',
[Parameter(Mandatory = $false)]
[ValidateNotNullOrEmpty()]
[string]$CmkName = 'CMK1',
[Parameter(Mandatory = $false)]
[ValidateNotNullOrEmpty()]
[string]$CekName = 'CEK1'
)
Set-StrictMode -Version Latest
$ErrorActionPreference = 'Stop'
Import-Module SqlServer -MinimumVersion 22.0.50 -ErrorAction Stop
if (-not (Test-Path -Path $KeyDataFile -PathType Leaf)) {
throw "Key data file not found: $KeyDataFile"
}
Write-Host "[AE] Loading key metadata from '$KeyDataFile'"
$keyData = Import-Csv -Path $KeyDataFile
if (-not $keyData) {
throw "Key data file '$KeyDataFile' is empty."
}
$keyDataRow = $keyData | Select-Object -First 1
if (-not $keyDataRow.KeyStoreProviderName -or -not $keyDataRow.KeyPath -or -not $keyDataRow.EncryptedValue) {
throw "Key data file must include non-empty columns: KeyStoreProviderName, KeyPath, EncryptedValue."
}
Write-Host "[AE] Connecting to SQL Server '$ServerName' / Database '$DatabaseName'"
$connStr = "Server=$ServerName;Database=$DatabaseName;Integrated Security=True;Encrypt=True;TrustServerCertificate=True;Connection Timeout=30"
try {
$database = Get-SqlDatabase -ConnectionString $connStr -ErrorAction Stop
}
catch {
Write-Error "Failed to connect to '$ServerName' / '$DatabaseName'. Verify instance name, database, and local permissions."
throw
}
Write-Host "[AE] Building CMK settings for provider '$($keyDataRow.KeyStoreProviderName)'"
$cmkSettings = New-SqlColumnMasterKeySettings -KeyStoreProviderName $keyDataRow.KeyStoreProviderName -KeyPath $keyDataRow.KeyPath
Write-Host "[AE] Ensuring CMK '$CmkName' exists"
$existingCmk = Get-SqlColumnMasterKey -InputObject $database | Where-Object { $_.Name -eq $CmkName }
if (-not $existingCmk) {
New-SqlColumnMasterKey -Name $CmkName -InputObject $database -ColumnMasterKeySettings $cmkSettings | Out-Null
}
Write-Host "[AE] Ensuring CEK '$CekName' exists"
$existingCek = Get-SqlColumnEncryptionKey -InputObject $database | Where-Object { $_.Name -eq $CekName }
if (-not $existingCek) {
New-SqlColumnEncryptionKey -Name $CekName -InputObject $database -ColumnMasterKey $CmkName -EncryptedValue $keyDataRow.EncryptedValue | Out-Null
}
Write-Host 'Completed successfully'
Contenu connexe
- Configurer le chiffrement de colonne avec Always Encrypted en utilisant PowerShell
- Permuter des clés Always Encrypted à l’aide de PowerShell
- Développer des applications avec Always Encrypted
- Always Encrypted
- Vue d’ensemble de la gestion des clés pour Always Encrypted
- Créer et stocker des clés principales de colonne pour Always Encrypted
- Configurer Always Encrypted à l’aide de PowerShell
- Provisionner des clés Always Encrypted à l’aide de SQL Server Management Studio
- CREATE COLUMN MASTER KEY (Transact-SQL)
- DROP COLUMN MASTER KEY (Transact-SQL)
- CREATE COLUMN ENCRYPTION KEY (Transact-SQL)
- ALTER COLUMN ENCRYPTION KEY (Transact-SQL)
- DROP COLUMN ENCRYPTION KEY (Transact-SQL)
- sys.column_master_keys (Transact-SQL)
- sys.column_encryption_keys (Transact-SQL)