Tutoriel : Utilisation de l'automatisation pour configurer l'administrateur Microsoft Entra pour SQL Server
Article
S’applique à : SQL Server 2022 (16.x)
Remarque
Cette fonctionnalité est disponible dans SQL Server 2022 (16.x) ou versions ultérieures et est prise en charge uniquement pour une instance locale de SQL Server sur les hôtes Windows et Linux et SQL Server 2022 sur les VM Windows Azure.
Dans cet article, nous allons découvrir comment configurer l’administrateur Microsoft Entra pour autoriser l’authentification avec Microsoft Entra ID (anciennement Azure Active Directory) pour SQL Server à l’aide du Portail Azure et des API telles que :
Bien que Microsoft Entra ID soit le nouveau nom d’Azure Active Directory (Azure AD) pour empêcher l’interruption des environnements existants, Azure AD reste toujours dans certains éléments codés en dur, tels que les champs d’interface utilisateur, les fournisseurs de connexions, les codes d’erreur et cmdlets. Dans cet article, ces deux noms sont interchangeables.
Prérequis
SQL Server 2022 (16.x) ou version ultérieure est installé.
Préparation avant de définir l’administrateur Microsoft Entra
Les autorisations suivantes sont nécessaires pour configurer l’administrateur Microsoft Entra dans les ressources SQL Server – Azure Arc et Coffre de clés.
Configurer des autorisations pour Azure Arc
Suivez le guide pour vous assurer que votre serveur SQL Server est connecté à Azure Arc. L’utilisateur qui configure l’administrateur Microsoft Entra pour la ressource SQL Server – Azure Arc doit avoir le rôle Contributeur pour le serveur.
Sélectionnez SQL Server – Azure Arc et sélectionnez l’instance de votre hôte SQL Server.
Sélectionnez Contrôle d’accès (IAM) .
Sélectionnez Ajouter>Ajouter une attribution de rôle pour ajouter le rôle Contributeur à l’utilisateur qui configure l’administrateur Microsoft Entra.
Configurer les autorisations pour Azure Key Vault
Si ce n’est déjà fait, créez un compte Azure Key Vault. L’utilisateur qui configure l’administrateur Microsoft Entra doit avoir le rôle Contributeur pour votre Azure Key Vault. Pour ajouter un rôle à un utilisateur dans Azure Key Vault :
Sélectionnez Ajouter>Ajouter une attribution de rôle pour ajouter le rôle Contributeur à l’utilisateur qui configure l’administrateur Microsoft Entra.
Définir des stratégies d’accès pour l’hôte SQL Server
Dans le portail Azure, accédez à votre instance Azure Key Vault et sélectionnez Stratégies d’accès.
Sélectionnez Ajouter une stratégie d’accès.
Pour les autorisations de clé, utilisez Sign.
Pour les autorisations de secret, sélectionnez Obtenir et Liste.
Pour Autorisations du certificat, sélectionnez Obtenir et Liste.
Cliquez sur Suivant.
Sur la page Principal, recherchez le nom de votre instance Machine – Azure Arc, qui est le nom de l'hôte du serveur SQL.
Ignorez la page Application (facultative) en sélectionnant Suivant deux fois ou en sélectionnant Vérifier + créer.
Vérifiez que l'« ID d'objet » du Principal correspond à l'ID de principal de l'identité managée attribué à l'instance.
Pour confirmer, accédez à la page de ressources et sélectionnez Affichage JSON en haut à droite de la zone Essentials de la page Vue d'ensemble. Sous identité, vous trouverez le principalId.
Sélectionnez Créer.
Vous devez sélectionner Créer pour que les autorisations soient appliquées. Pour vous assurer que les autorisations ont bien été stockées, actualisez la fenêtre du navigateur et vérifiez que la ligne correspondant à votre instance Azure Arc est toujours présente.
Définir des stratégies d’accès pour les utilisateurs Microsoft Entra
Dans le portail Azure, accédez à votre instance Azure Key Vault et sélectionnez Stratégies d’accès.
Sélectionnez Ajouter une stratégie d’accès.
Pour Autorisations de clé, sélectionnez Obtenir, Liste et Créer.
Pour Autorisations de secret, sélectionnez Obtenir, Liste et Définir.
Pour Autorisations du certificat, sélectionnez Obtenir, Liste et Créer.
Pour Sélectionner un principal, ajoutez l’utilisateur Microsoft Entra que vous souhaitez utiliser pour vous connecter à SQL Server.
Sélectionnez Ajouter, puis sélectionnez Enregistrer.
Configurer l’administrateur Microsoft Entra pour SQL Server
Les nouvelles API et fonctionnalités du portail permettent aux utilisateurs de configurer un administrateur Microsoft Entra pour SQL Server sans avoir à créer séparément un certificat Azure et une application Microsoft Entra. Sélectionnez un onglet pour savoir comment configurer un administrateur Microsoft Entra pour votre SQL Server connecté à Azure Arc avec la création automatique du certificat et de l’application.
Remarque
Le modèle ARM nécessite toujours la création d’un certificat Azure Key Vault et d’une application Microsoft Entra avant de configurer un administrateur Microsoft Entra. Pour plus d’informations sur ce processus, consultez Didacticiel: Configurer l’authentification Microsoft Entra pour SQL Server.
Utilisez le Portail Azure pour configurer un administrateur Microsoft Entra, créer un certificat Azure Key Vault et une application Microsoft Entra dans le même processus. Il est nécessaire d’utiliser l’authentification Microsoft Entra avec SQL Server.
Sélectionnez Microsoft Entra ID et Purview sous Paramètres dans le menu des ressources.
Sélectionnez Définir Administration pour ouvrir le volet Microsoft Entra ID, puis choisissez un compte qui sera ajouté en tant que connexion administrateur pour SQL Server.
Sélectionnez Certificat managé par le service.
Sélectionnez Modifier le coffre de clés et sélectionnez votre ressource Azure Key Vault existante.
Sélectionnez Inscription d’application managée par le service.
Cliquez sur Enregistrer. Cela envoie une demande à l'agent de serveur Arc qui configure l'authentification Microsoft Entra pour cette instance SQL Server. L’opération peut prendre plusieurs minutes ; attendez que le processus d’enregistrement soit confirmé avec Saved successfully avant de tenter une connexion Microsoft Entra.
L’inscription d’application gérée par le service effectue les opérations suivantes pour vous :
Crée un certificat dans votre coffre de clés avec un nom sous le forme <hostname>-<instanceName><uniqueNumber>.
Crée une application Microsoft Entra avec un nom tel que <hostname>-<instanceName><uniqueNumber> et attribue les autorisations nécessaires à cette application. Pour plus d’informations, consultez Accorder des autorisations d’application
Affecte le nouveau certificat dans Azure Key Vault à l’application.
Enregistre ces paramètres dans Azure Arc.
Remarque
Il n’y a pas de rotation automatique pour les certificats créés pour Microsoft Entra. Les clients peuvent choisir de fournir leurs propres certificat et application pour la configuration de l’administrateur Microsoft Entra. Pour plus d'informations, consultez Didacticiel : Configurer l’authentification Microsoft Entra pour SQL Server.
Il n’y a pas de rotation automatique pour les certificats créés pour la configuration de Microsoft Entra.
L’Azure CLI version 2.37.0 ou ultérieure est requise
Az.ConnectedMachine 0.5.1 ou version ultérieure est requis
Pour installer le module Az.ConnectedMachine, utilisez az extension add --name ConnectedMachine. Pour vérifier la version d’Azure CLI installée, utilisez az version.
Les paramètres d’entrée suivants sont utilisés dans le sript Azure CLI :
<applicationName> - Nom de l’application qui sera créée
<certSubjectName> - Nom du certificat qui sera créé
<keyVaultName> : Nom de votre coffre de clés. Ce coffre de clés doit être créé avant d’exécuter le script
<machineName> - Nom de l’ordinateur de votre hôte SQL Server
<resourceGroupName>- Nom du groupe de ressources qui contient votre instance SQL Server – Azure Arc
<adminAccountName> - Compte d’administrateur Microsoft Entra que vous souhaitez définir pour votre SQL Server
<instanceName> - Paramètre facultatif pour les instances nommées SQL Server. Utilisez ce paramètre lorsque vous avez une instance nommée. En cas d’omission, la valeur par défaut de MSSQLSERVER est utilisée
<tenantId> - Paramètre facultatif pour l’ID de client. L’ID de client est disponible en accédant à votre ressource Microsoft Entra ID dans le portail Azure. Dans le volet Vue d’ensemble, vous devez voir votre ID de locataire. S’il est omis, l’ID de locataire par défaut est utilisé comme paramètre
<subscriptionId> - Paramètre facultatif pour l’ID d’abonnement. Votre ID d’abonnement est disponible dans le Portail Azure. S’il est omis, l’ID d’abonnement par défaut est utilisé
Pour utiliser le script Azure CLI ci-dessous, enregistrez le script en tant que fichier .ps1 et exécutez la commande suivante :
Pour SQL Server sur des ordinateurs hôtes Linux, remplacez WindowsAgent.SqlServer par LinuxAgent.SqlServer dans le script.
# AZ CLI and AZ CLI's connected machine extension must be installed before running this script
param (
[Parameter(mandatory=$true)] $applicationName,
[Parameter(mandatory=$true)] $certSubjectName,
[Parameter(mandatory=$true)] $keyVaultName,
[Parameter(mandatory=$true)] $machineName,
[Parameter(mandatory=$true)] $resourceGroupName,
[Parameter(mandatory=$true)] $adminAccountName,
$instanceName,
$tenantId,
$subscriptionId
)
# Constants
#
$NUMRETRIES = 60
# Helper functions
#
function ConvertFrom-StringArray {
param (
[string[]] $stringArray
)
if (!$stringArray)
{
return $null
}
else
{
return ConvertFrom-JSON ($stringArray -join "`n")
}
}
# Check parameters
#
if ([string]::IsNullOrEmpty($instanceName))
{
Write-Host "Warning: SQL Instance name (-instanceName) not provided. Default of MSSQLSERVER will be used"
$instanceName = "MSSQLSERVER"
}
$tenantIdArgument = ""
if ([string]::IsNullOrEmpty($tenantId))
{
Write-Host "Warning: Tenant ID (-tenantId) not supplied to the script, so default tenant is being used"
}
else
{
$tenantIdArgument = "-TenantId '" + $tenantId + "'"
}
$subscriptionIdArgument = ""
if ([string]::IsNullOrEmpty($subscriptionId))
{
Write-Host "Warning: Subscription ID (-subscriptionId) not supplied to the script, so default subscription is being used"
}
else
{
$subscriptionIdArgument = "-SubscriptionId '" + $subscriptionId + "'"
}
# Login and select subscription
#
$login = az login --tenant $tenantId --use-device-code
if (!$login)
{
Write-Error "Login to Azure AD failed. Exiting."
exit 1
}
if ($subscriptionId)
{
az account set -s $subscriptionId
}
$accountInfo = ConvertFrom-StringArray (az account show)
if (!$accountInfo)
{
Write-Error "Cannot query logged in Azure AD account. Check that 'az login' and 'az account set' succeeded"
exit 1
}
if ($subscriptionId)
{
if ($subscriptionId.ToLower() -ne $accountInfo.id.ToLower())
{
Write-Error "Could not select the desired subscription"
exit 1
}
}
else
{
$subscriptionId = $accountInfo.id
}
# Check AKV path exists
#
$keyVault = ConvertFrom-StringArray (az keyvault show --name $keyVaultName)
if (!$keyVault)
{
Write-Error "Azure key vault '$keyVaultName' does not exist"
exit 1
}
# Check certificate doesn't exist
#
$cert = ConvertFrom-StringArray (az keyvault certificate show --name $certSubjectName --vault-name $keyVaultName 2>$null)
if ($cert)
{
Write-Error "Certificate '$certSubjectName' already exists in key vault '$keyVaultName'"
exit 1
}
# Check app registration doesn't exist
#
$applications = ConvertFrom-StringArray (az ad app list --display-name $applicationName --only-show-errors)
if ($applications.length -gt 0)
{
Write-Error "App registration with name '$applicationName' already exists"
exit 1
}
# Check Arc SQL instance is valid
#
$extension = ConvertFrom-StringArray (az connectedmachine extension show --machine-name $machineName --name "WindowsAgent.SqlServer" --resource-group $resourceGroupName)
if (!$extension)
{
Write-Error "SQL Server Arc Server not found for machine '$machineName' in resource group '$resourceGroupName'"
exit 1
}
$arcServicePrincipals = ConvertFrom-StringArray(az ad sp list --display-name $machineName --only-show-errors)
if (!$arcServicePrincipals -or $arcServicePrincipals.length -eq 0)
{
Write-Error "Could not find a service principal account with the name '$machineName'"
exit 1
}
else
{
$principalFound = $false
for ($i = 0; $i -lt $arcServicePrincipals.length; $i++)
{
if ($arcServicePrincipals[$i].displayName.toLower() -eq $machineName.toLower()) {
if ($principalFound) {
Write-Error "Could not find exactly one service principal account with the name '$machineName'"
exit 1
}
$arcServicePrincipal = $arcServicePrincipals[$i]
$principalFound = $true
}
}
if (!$principalFound) {
Write-Error "Could not find a service principal account with the name '$machineName'"
exit 1
}
}
# Check if admin account exists
#
$adminAccount = ConvertFrom-StringArray (az ad user show --id $adminAccountName --only-show-errors 2>$null)
$adminAccountType = 0
if (!$adminAccount)
{
$adminAccounts = ConvertFrom-StringArray (az ad user list --filter "mail eq '$adminAccountName'" --only-show-errors 2>$null)
if ($adminAccounts -and $adminAccounts.length -gt 0)
{
if ($adminAccounts.length -eq 1)
{
$adminAccount = $adminAccounts[0]
}
else
{
Write-Error "Multiple Azure AD accounts found with identifier '$adminAccountName'"
exit 1
}
}
else
{
$adminAccount = ConvertFrom-StringArray (az ad group show --group $adminAccountName --only-show-errors 2>$null)
if (!$adminAccount)
{
$adminAccounts = ConvertFrom-StringArray (az ad app list --display-name $adminAccountName --only-show-errors 2>$null)
if ($adminAccounts -and $adminAccounts.length -gt 0)
{
if ($adminAccounts.length -eq 1)
{
$adminAccount = $adminAccounts[0]
}
else
{
Write-Error "Multiple Azure AD applications found with identifier '$adminAccountName'"
exit 1
}
}
else
{
Write-Error "Admin account not found"
exit 1
}
}
else
{
$adminAccountType = 1
}
}
}
if ($adminAccount)
{
$adminAccountSid = $adminAccount.id
}
else
{
Write-Error "Admin account not found"
exit 1
}
# Create certificate in AKV
#
$keyVaultPolicy = ConvertFrom-StringArray (az keyvault certificate get-default-policy)
if (!$keyVaultPolicy)
{
Write-Error "Could not get default key vault policy"
exit 1
}
$keyVaultPolicy.x509CertificateProperties.subject = "CN=" + $certSubjectName
$policyString = (ConvertTo-JSON -Depth 8 $keyVaultPolicy).replace("`r`n", "")
$escapedPolicyString = $policyString.replace("`"", "\`"")
$cert = ConvertFrom-StringArray (az keyvault certificate create --vault-name $keyVaultName --name $certSubjectName --policy $escapedPolicyString)
if (!$cert)
{
Write-Error "Failed to create certificate '$certSubjectName'"
exit 1
}
# Wait until cert is created?
#
$cert = ConvertFrom-StringArray (az keyvault certificate show --vault-name $keyVaultName --name $certSubjectName)
for (($i = 0); $i -lt $NUMRETRIES -and (!$cert -or !$cert.attributes.enabled); $i++)
{
$cert = ConvertFrom-StringArray (az keyvault certificate show --vault-name $keyVaultName --name $certSubjectName)
if (!$cert -or !$cert.attributes.enabled)
{
Start-Sleep -Seconds 5
}
}
# Allow Arc to access AKV
#
$newPerms = ConvertFrom-StringArray (az keyvault set-policy --name $keyVaultName --secret-permissions get list --certificate-permissions get list --object-id $arcServicePrincipal.id)
if (!$newPerms)
{
Write-Host "Warning: Unable to add permissions to key vault '$keyVaultName' for Arc's service principal's identity '$($arcServicePrincipal.id)'. Arc may not be able to configure Azure AD authentication"
}
# Create an Azure AD application
#
$application = ConvertFrom-StringArray (az ad app create --display-name $applicationName --only-show-errors)
if (!$application)
{
Write-Error "Unable to create the app registration '$applicationName'"
exit 1
}
# Set perms on app registration
#
az ad app permission add --id $application.id --api 00000003-0000-0000-c000-000000000000 --api-permissions c79f8feb-a9db-4090-85f9-90d820caa0eb=Scope --only-show-errors # Delegated Application.Read.All
az ad app permission add --id $application.id --api 00000003-0000-0000-c000-000000000000 --api-permissions 0e263e50-5827-48a4-b97c-d940288653c7=Scope --only-show-errors # Delegated Directory.AccessAsUser.All
az ad app permission add --id $application.id --api 00000003-0000-0000-c000-000000000000 --api-permissions 7ab1d382-f21e-4acd-a863-ba3e13f7da61=Role --only-show-errors # Application Directory.Read.All
az ad app permission add --id $application.id --api 00000003-0000-0000-c000-000000000000 --api-permissions 5f8c59db-677d-491f-a6b8-5f174b11ec1d=Scope --only-show-errors # Delegated Group.Read.All
az ad app permission add --id $application.id --api 00000003-0000-0000-c000-000000000000 --api-permissions a154be20-db9c-4678-8ab7-66f6cc099a59=Scope --only-show-errors # Delegated User.Read.All
# Upload cert to Azure AD
#
$certUploadRes = ConvertFrom-StringArray (az ad app credential reset --id $application.id --cert $certSubjectName --keyvault $keyVaultName --append --only-show-errors)
if (!$certUploadRes)
{
Write-Error "Failed to set certificate '$certSubjectName' as a credential for app registration '$applicationName'"
exit 1
}
# Remove the version from the secret ID if present
#
$secretId = $cert.sid
if ($secretId -Match "(https:\/\/[^\/]+\/secrets\/[^\/]+)(\/.*){0,1}$") {
if ($Matches[1]) {
$secretId = $Matches[1]
}
}
# Create the settings object to write to the Azure extension for SQL Server
#
$instanceSettings = @{
instanceName = $instanceName
adminLoginName = $adminAccountName
adminLoginSid = $adminAccountSid
azureCertSecretId = $secretId
azureCertUri = $cert.id
azureKeyVaultResourceUID = $keyVault.id
managedCertSetting = "CUSTOMER MANAGED CERT"
managedAppSetting = "CUSTOMER MANAGED APP"
appRegistrationName = $application.displayName
appRegistrationSid = $application.appId
tenantId = $tenantId
aadCertSubjectName = $certSubjectName
adminLoginType = $adminAccountType
}
$extension = ConvertFrom-StringArray (az connectedmachine extension show --machine-name $machineName --name "WindowsAgent.SqlServer" --resource-group $resourceGroupName)
if ($extension.properties.Settings.AzureAD)
{
$aadSettings = $extension.properties.Settings.AzureAD
$instanceFound = $false
$instanceNameLower = $instanceName.ToLower()
$instanceIndex = 0
for (($i = 0); $i -lt $aadSettings.Length; $i++)
{
if ($aadSettings[$i].instanceName.ToLower() -eq $instanceNameLower)
{
$instanceIndex = $i
$instanceFound = $true
break
}
}
if ($instanceFound)
{
$aadSettings[$instanceIndex] = $instanceSettings
}
else
{
$aadSettings += $instanceSettings
}
$extension.properties.Settings.AzureAD = $aadSettings
}
else
{
$aadSettings = , $instanceSettings
$extension.properties.Settings | Add-Member -Name 'AzureAD' -Value $aadSettings -MemberType NoteProperty
}
$settingsString = (ConvertTo-Json $extension.properties.Settings).replace("`"", "\`"").replace("`r`n", "")
# Push settings to Arc
#
Write-Host "Writing Azure AD setting to Azure extension for SQL Server. This may take several minutes..."
$updateRes = az connectedmachine extension update --machine-name $machineName --name "WindowsAgent.SqlServer" --resource-group $resourceGroupName --settings $settingsString
if (!$updateRes)
{
Write-Error "Failed to update Azure extension for SQL Server with Azure AD settings"
exit 1
}
Write-Output "Success"
L’exécution du script peut prendre plusieurs minutes. Une fois le processus terminé, un message similaire à ce qui suit s’affiche :
Name Location ProvisioningState
---- -------- -----------------
WindowsAgent.SqlServer westus2 Succeeded
Success
Configuration d’un administrateur Microsoft Entra avec un certificat et une application existants à l’aide d’Azure CLI
Si vous disposez déjà d’un certificat Azure Key Vault existant et d’une application Azure que vous souhaitez utiliser pour configurer un administrateur Microsoft Entra, vous pouvez utiliser le script CLI suivant :
# Set up Microsoft Entra admin for user's existing key vault, certificate, and application
# Requires input parameters indicated below
# Connect statement
AZ Login
#Input parameters
$subscriptionId="<subscriptionId>"
$tenantId="<tenantId>"
$machineName="<machineName>" # hostname
$instanceName="<instanceName>" # SQL Server is define as `machine_name\instance_name`
$resourceGroupName="<resourceGroupName>"
$keyVaultName="<keyVaultName>"
$certSubjectName="<certSubjectName>" # Your existing certificate name
$applicationName="<applicationName>" # Your existing application name
$adminAccountName="<adminAccountName>"
$adminAccountSid="<adminID>" # Use object ID for the Azure AD user and group, or client ID for the Azure AD application
$adminAccountType= 0 # 0 – for Azure AD user and application, 1 for Azure AD group
# Helper function
#
function ConvertFrom-StringArray {
param (
[string[]] $stringArray
)
if (!$stringArray)
{
return $null
}
else
{
return ConvertFrom-JSON ($stringArray -join "`n")
}
}
$keyVault = ConvertFrom-StringArray (az keyvault show --name $keyVaultName)
if (!$keyVault)
{
Write-Error "Azure key vault '$keyVaultName' does not exist"
exit 1
}
$cert = ConvertFrom-StringArray (az keyvault certificate show --name $certSubjectName --vault-name $keyVaultName 2>$null)
if (!$cert)
{
Write-Error "Supplied certificate $certSubjectName was not found for this key vault. Please specify an existing certificate"
exit 1
}
$secretId = $cert.sid
if ($secretId -Match "(https:\/\/[^\/]+\/secrets\/[^\/]+)(\/.*){0,1}$") {
if ($Matches[1]) {
$secretId = $Matches[1]
}
}
$application = ConvertFrom-StringArray (az ad app list --display-name $applicationName --only-show-errors)
if (!$application)
{
Write-Error "Supplied application was not found in the subscription. Please specify an existing application"
exit 1
}
# Create the settings object to write to the Arc extension
#
$instanceSettings = @{
instanceName = $instanceName
adminLoginName = $adminAccountName
adminLoginSid = $adminAccountSid
azureCertSecretId = $secretId
azureCertUri = $cert.id
azureKeyVaultResourceUID = $keyVault.id
managedCertSetting = "CUSTOMER MANAGED CERT"
managedAppSetting = "CUSTOMER MANAGED APP"
appRegistrationName = $application.displayName
appRegistrationSid = $application.appId
tenantId = $tenantId
aadCertSubjectName = $certSubjectName
adminLoginType = $adminAccountType
}
$extension = ConvertFrom-StringArray (az connectedmachine extension show --machine-name $machineName --name "WindowsAgent.SqlServer" --resource-group $resourceGroupName)
if ($extension.properties.Settings.AzureAD)
{
$aadSettings = $extension.properties.Settings.AzureAD
$instanceFound = $false
$instanceNameLower = $instanceName.ToLower()
$instanceIndex = 0
for (($i = 0); $i -lt $aadSettings.Length; $i++)
{
if ($aadSettings[$i].instanceName.ToLower() -eq $instanceNameLower)
{
$instanceIndex = $i
$instanceFound = $true
break
}
}
if ($instanceFound)
{
$aadSettings[$instanceIndex] = $instanceSettings
}
else
{
$aadSettings += $instanceSettings
}
$extension.properties.Settings.AzureAD = $aadSettings
}
else
{
$aadSettings = , $instanceSettings
$extension.properties.Settings | Add-Member -Name 'AzureAD' -Value $aadSettings -MemberType NoteProperty
}
$settingsString = (ConvertTo-Json $extension.properties.Settings).replace("`"", "\`"").replace("`r`n", "")
# Push settings to Arc
#
Write-Host "Writing Azure AD setting to SQL Server Arc Extension. This may take several minutes..."
$updateRes = az connectedmachine extension update --machine-name $machineName --name "WindowsAgent.SqlServer" --resource-group $resourceGroupName --settings $settingsString
if (!$updateRes)
{
Write-Error "Failed to update SQL Arc Extension with Azure AD settings"
exit 1
}
Write-Output "Success"
Il n’y a pas de rotation automatique pour les certificats créés pour la configuration de Microsoft Entra.
Les modules suivants sont requis pour suivre ce tutoriel. Installez les dernières versions des modules ou des versions supérieures à la version indiquée ci-dessous :
Az.Accounts 3.37.0
Az.ConnectedMachine 0.5.0
Az.KeyVault 4.5.0
Az.Resources 6.0.0
Les paramètres d’entrée suivants sont utilisés pour le script PowerShell :
<applicationName> - Nom de l’application qui sera créée
<certSubjectName> - Nom du certificat qui sera créé
<keyVaultName> : Nom de votre coffre de clés. Ce coffre de clés doit être créé avant d’exécuter le script
<machineName> - Nom de l’ordinateur de votre hôte SQL Server
<resourceGroupName>- Nom du groupe de ressources qui contient votre instance SQL Server – Azure Arc
<adminAccountName> - Compte d’administrateur Microsoft Entra que vous souhaitez définir pour votre SQL Server
<instanceName> - Paramètre facultatif pour les instances nommées SQL Server. Utilisez ce paramètre lorsque vous avez une instance nommée. En cas d’omission, la valeur par défaut de MSSQLSERVER est utilisée
<tenantId> - Paramètre facultatif pour l’ID de client. L’ID de client est disponible en accédant à votre ressource Microsoft Entra ID dans le portail Azure. Dans le volet Vue d’ensemble, vous devez voir votre ID de locataire. S’il est omis, l’ID de locataire par défaut est utilisé comme paramètre
<subscriptionId> - Paramètre facultatif pour l’ID d’abonnement. Votre ID d’abonnement est disponible dans le Portail Azure. S’il est omis, l’ID d’abonnement par défaut est utilisé
Pour utiliser le script PowerShell ci-dessous, enregistrez le script en tant que fichier .ps1 et exécutez la commande suivante :
Pour SQL Server sur des ordinateurs hôtes Linux, remplacez WindowsAgent.SqlServer par LinuxAgent.SqlServer dans le script.
param (
[Parameter(mandatory=$true)] $applicationName,
[Parameter(mandatory=$true)] $certSubjectName,
[Parameter(mandatory=$true)] $keyVaultName,
[Parameter(mandatory=$true)] $machineName,
[Parameter(mandatory=$true)] $resourceGroupName,
[Parameter(mandatory=$true)] $adminAccountName,
$instanceName,
$tenantId,
$subscriptionId
)
Import-Module Az.Accounts
Import-Module Az.ConnectedMachine
Import-Module Az.KeyVault
Import-Module Az.Resources
# Constants
#
$NUMRETRIES = 60
# Check parameters
#
if ([string]::IsNullOrEmpty($instanceName))
{
Write-Host "Warning: SQL Instance name (-instanceName) not provided. Default of MSSQLSERVER will be used"
$instanceName = "MSSQLSERVER"
}
$tenantIdArgument = ""
if ([string]::IsNullOrEmpty($tenantId))
{
Write-Host "Warning: Tenant ID (-tenantId) not supplied to the script, so default tenant is being used"
}
else
{
$tenantIdArgument = "-TenantId '" + $tenantId + "'"
}
$subscriptionIdArgument = ""
if ([string]::IsNullOrEmpty($subscriptionId))
{
Write-Host "Warning: Subscription ID (-subscriptionId) not supplied to the script, so default subscription is being used"
}
else
{
$subscriptionIdArgument = "-SubscriptionId '" + $subscriptionId + "'"
}
# Login
#
try
{
$loginRes = Invoke-Expression -Command ("Connect-AzAccount " + $tenantIdArgument + " " + $subscriptionIdArgument + " -ErrorAction stop -UseDeviceAuthentication")
}
catch
{
Write-Error $_
Write-Error "Failed to login to Azure. Script can not continue"
exit 1
}
# Get subscription ID
#
if ([string]::IsNullOrEmpty($subscriptionId))
{
$context = Get-AzContext
if ($context)
{
if ($context.Name -Match "[^(]+\(([^)]{36})\)")
{
if ($Matches[1])
{
$subscriptionId = $Matches[1]
}
}
}
}
if ([string]::IsNullOrEmpty($subscriptionId))
{
Write-Error "Failed to find default subscription"
exit 1
}
# Check AKV path exists
#
$keyVault = Get-AzKeyVault -VaultName $keyVaultName
if (!$keyVault)
{
Write-Error "Supplied key vault was not found in the subscription. Please specify an existing key vault"
exit 1
}
# Check certificate doesn't exist
#
$cert = Get-AzKeyVaultCertificate -VaultName $keyVaultName -Name $certSubjectName
if ($cert)
{
Write-Error "Certificate $certSubjectName already exists"
exit 1
}
# Check app registration doesn't exist
#
$application = Get-AzADApplication -DisplayName $applicationName
if ($application)
{
Write-Error "Application $applicationName already exists"
exit 1
}
# Check Arc SQL instance is valid
#
$arcInstance = Get-AzConnectedMachineExtension -SubscriptionId $subscriptionId -MachineName $machineName -ResourceGroupName $resourceGroupName -Name "WindowsAgent.SqlServer"
if (!$arcInstance)
{
Write-Error "Could not find a SQL Server Arc instance in subscription '$subscriptionId' and resource group '$resourceGroupName' with name '$machineName'"
exit 1
}
# Check if admin account exists
#
$adminAccount = Get-AzADUser -UserPrincipalName $adminAccountName
$adminAccountType = 0
if (!$adminAccount)
{
# Check for guest user
#
$adminAccount = Get-AzADUser -Mail $adminAccountName
if (!$adminAccount)
{
$adminAccount = Get-AzADGroup -DisplayName $adminAccountName
if (!$adminAccount)
{
$adminAccount = Get-AzADServicePrincipal -DisplayName $adminAccountName
}
else
{
$adminAccountType = 1
}
}
}
if ($adminAccount)
{
if ($adminAccount.Length -gt 1)
{
Write-Error "Multiple accounts with found with name $adminAccountName"
exit 1
}
$adminAccountSid = $adminAccount.Id
}
else
{
Write-Error "Could not find an account with name $adminAccountName"
exit 1
}
# Create certificate in AKV
#
$Policy = New-AzKeyVaultCertificatePolicy -SecretContentType "application/x-pkcs12" -SubjectName "CN=$certSubjectName" -IssuerName "Self" -ValidityInMonths 12 -ReuseKeyOnRenewal
try
{
$addCertRes = Add-AzKeyVaultCertificate -VaultName $keyVaultName -Name $certSubjectName -CertificatePolicy $Policy -ErrorAction stop
}
catch
{
Write-Error $_
Write-Error "Certificate $certSubjectName could not be created"
exit 1
}
for (($i = 0); $i -lt $NUMRETRIES -and (!$cert -or !$cert.enabled); $i++)
{
$cert = Get-AzKeyVaultCertificate -VaultName $keyVaultName -Name $certSubjectName
if (!$cert -or !$cert.enabled)
{
Start-Sleep -Seconds 5
}
}
if (!$cert)
{
Write-Error "Certificate $certSubjectName could not be created"
exit 1
}
# Allow Arc to access AKV
#
$arcServicePrincipal = Get-AzADServicePrincipal -DisplayName $machineName
if ($arcServicePrincipal -and ![string]::IsNullOrEmpty($arcServicePrincipal.Id))
{
try
{
Set-AzKeyVaultAccessPolicy -VaultName $keyVaultName -ObjectId $arcServicePrincipal.Id -PermissionsToSecrets Get,List -PermissionsToCertificates Get,List
}
catch
{
Write-Error $_
Write-Host "Warning: Could not find the identity of the Azure extension for SQL Server and thus, could not add permissions for the Arc process to read from AKV. Ensure the Arc identity has the required permissions to read from AKV."
}
}
else
{
Write-Host "Warning: Could not find the identity of the Azure extension for SQL Server and thus, could not add permissions for the Arc process to read from AKV. Ensure the Arc identity has the required permissions to read from AKV."
}
# Create an Azure AD application
#
$application = New-AzADApplication -DisplayName $applicationName
if (!$application)
{
Write-Error "Application could not be created"
exit 1
}
# Set perms on app registration
#
Add-AzADAppPermission -ObjectId $application.Id -ApiId 00000003-0000-0000-c000-000000000000 -PermissionId c79f8feb-a9db-4090-85f9-90d820caa0eb # Delegated Application.Read.All
Add-AzADAppPermission -ObjectId $application.Id -ApiId 00000003-0000-0000-c000-000000000000 -PermissionId 0e263e50-5827-48a4-b97c-d940288653c7 # Delegated Directory.AccessAsUser.All
Add-AzADAppPermission -ObjectId $application.Id -ApiId 00000003-0000-0000-c000-000000000000 -PermissionId 7ab1d382-f21e-4acd-a863-ba3e13f7da61 -Type Role # Application Directory.Read.All
Add-AzADAppPermission -ObjectId $application.Id -ApiId 00000003-0000-0000-c000-000000000000 -PermissionId 5f8c59db-677d-491f-a6b8-5f174b11ec1d # Delegated Group.Read.All
Add-AzADAppPermission -ObjectId $application.Id -ApiId 00000003-0000-0000-c000-000000000000 -PermissionId a154be20-db9c-4678-8ab7-66f6cc099a59 # Delegated User.Read.All
# Upload cert to Azure AD
#
try
{
$base64Cert = [System.Convert]::ToBase64String($cert.Certificate.GetRawCertData())
New-AzADAppCredential -ApplicationObject $application -CertValue $base64Cert -EndDate $cert.Certificate.NotAfter -StartDate $cert.Certificate.NotBefore -ErrorAction stop
}
catch
{
Write-Error $_
Write-Error "Failed to add certificate to app registration"
exit 1
}
# Remove the version from the secret ID if present
#
$secretId = $cert.SecretId
if ($secretId -Match "(https:\/\/[^\/]+\/secrets\/[^\/]+)(\/.*){0,1}$") {
if ($Matches[1]) {
$secretId = $Matches[1]
}
}
# Create the settings object to write to the Azure extension for SQL Server
#
$instanceSettings = @{
instanceName = $instanceName
adminLoginName = $adminAccountName
adminLoginSid = $adminAccountSid
azureCertSecretId = $secretId.replace(":443", "")
azureCertUri = $cert.Id.replace(":443", "")
azureKeyVaultResourceUID = $keyVault.ResourceId
managedCertSetting = "CUSTOMER MANAGED CERT"
managedAppSetting = "CUSTOMER MANAGED APP"
appRegistrationName = $application.DisplayName
appRegistrationSid = $application.AppId
tenantId = $tenantId
aadCertSubjectName = $certSubjectName
adminLoginType = $adminAccountType
}
$arcInstance = Get-AzConnectedMachineExtension -SubscriptionId $subscriptionId -MachineName $machineName -ResourceGroupName $resourceGroupName -Name "WindowsAgent.SqlServer"
if ($arcInstance.Setting.AdditionalProperties.AzureAD)
{
$aadSettings = $arcInstance.Setting.AdditionalProperties.AzureAD
$instanceFound = $false
$instanceNameLower = $instanceName.ToLower()
$instanceIndex = 0
for (($i = 0); $i -lt $aadSettings.Length; $i++)
{
if ($aadSettings[$i].instanceName.ToLower() -eq $instanceNameLower)
{
$instanceIndex = $i
$instanceFound = $true
break
}
}
if ($instanceFound)
{
$aadSettings[$instanceIndex] = $instanceSettings
}
else
{
$aadSettings += $instanceSettings
}
$arcInstance.Setting.AdditionalProperties.AzureAD = $aadSettings
}
else
{
$aadSettings = , $instanceSettings
$arcInstance.Setting.AdditionalProperties | Add-Member -Name 'AzureAD' -Value $aadSettings -MemberType NoteProperty
}
Write-Host "Writing Microsoft Entra setting to SQL Server Arc Extension. This may take several minutes..."
# Push settings to Arc
#
try
{
Update-AzConnectedMachineExtension -MachineName $machineName -Name "WindowsAgent.SqlServer" -ResourceGroupName $resourceGroupName -Setting $arcInstance.Setting
}
catch
{
Write-Error $_
Write-Error "Failed to write settings to Arc host"
exit 1
}
Write-Output "Success"
Configuration d’un administrateur Microsoft Entra avec un certificat et une application existants à l’aide de PowerShell
Si vous disposez déjà d’un certificat Azure Key Vault existant et d’une application Azure que vous souhaitez utiliser pour configurer un administrateur Microsoft Entra, vous pouvez utiliser le script PowerShell suivant :
# Connect statement
Connect-AzAccount
#Input parameters
$subscriptionId="<subscriptionId>"
$tenantId="<tenantId>"
$machineName="<machineName>" # hostname
$instanceName="<instanceName>" # SQL Server is define as `machine_name\instance_name`
$resourceGroupName="<resourceGroupName>"
$keyVaultName="<keyVaultName>"
$certSubjectName="<certSubjectName>" # Your existing certificate name
$applicationName="<applicationName>" # Your existing application name
$adminAccountName="<adminAccountName>"
$adminAccountSid="<adminID>" # Use object ID for the Microsoft Entra user and group, or client ID for the Microsoft Entra application
$adminAccountType= 0 # 0 – for Microsoft Entra user and application, 1 for Microsoft Entra group
$keyVault = Get-AzKeyVault -VaultName $keyVaultName
if (!$keyVault)
{
Write-Error "Supplied key vault was not found in the subscription. Please specify an existing key vault"
exit 1
}
$cert = Get-AzKeyVaultCertificate -VaultName $keyVaultName -Name $certSubjectName
if (!$cert)
{
Write-Error "Supplied certificate $certSubjectName was not found for this key vault. Please specify an existing certificate"
exit 1
}
$secretId = $cert.SecretId
if ($secretId -Match "(https:\/\/[^\/]+\/secrets\/[^\/]+)(\/.*){0,1}$") {
if ($Matches[1]) {
$secretId = $Matches[1]
}
}
$application = Get-AzADApplication -DisplayName $applicationName
if (!$application)
{
Write-Error "Supplied application was not found in the subscription. Please specify an existing application"
exit 1
}
# Create the settings object to write to the Arc extension
#
$instanceSettings = @{
instanceName = $instanceName
adminLoginName = $adminAccountName
adminLoginSid = $adminAccountSid
azureCertSecretId = $secretId.replace(":443", "")
azureCertUri = $cert.Id.replace(":443", "")
azureKeyVaultResourceUID = $keyVault.ResourceId
managedCertSetting = "CUSTOMER MANAGED CERT"
managedAppSetting = "CUSTOMER MANAGED APP"
appRegistrationName = $application.DisplayName
appRegistrationSid = $application.AppId
tenantId = $tenantId
aadCertSubjectName = $certSubjectName
adminLoginType = $adminAccountType
}
$arcInstance = Get-AzConnectedMachineExtension -SubscriptionId $subscriptionId -MachineName $machineName -ResourceGroupName $resourceGroupName -Name "WindowsAgent.SqlServer"
if ($arcInstance.Setting.AdditionalProperties.AzureAD)
{
$aadSettings = $arcInstance.Setting.AdditionalProperties.AzureAD
$instanceFound = $false
$instanceNameLower = $instanceName.ToLower()
$instanceIndex = 0
for (($i = 0); $i -lt $aadSettings.Length; $i++)
{
if ($aadSettings[$i].instanceName.ToLower() -eq $instanceNameLower)
{
$instanceIndex = $i
$instanceFound = $true
break
}
}
if ($instanceFound)
{
$aadSettings[$instanceIndex] = $instanceSettings
}
else
{
$aadSettings += $instanceSettings
}
$arcInstance.Setting.AdditionalProperties.AzureAD = $aadSettings
}
else
{
$aadSettings = , $instanceSettings
$arcInstance.Setting.AdditionalProperties | Add-Member -Name 'AzureAD' -Value $aadSettings -MemberType NoteProperty
}
Write-Host "Writing Microsoft Entra setting to SQL Server Arc Extension. This may take several minutes..."
# Push settings to Arc
#
try
{
Update-AzConnectedMachineExtension -MachineName $machineName -Name "WindowsAgent.SqlServer" -ResourceGroupName $resourceGroupName -Setting $arcInstance.Setting
}
catch
{
Write-Error $_
Write-Error "Failed to write settings to Arc host"
exit 1
}
Write-Output "Success"
Le modèle ARM suivant configure un administrateur Microsoft Entra à l’aide d’un certificat Azure Key Vault existant et d’une application Microsoft Entra.
Les paramètres d’entrée suivants sont utilisés pour le modèle ARM :
<machineName> - Nom de l’ordinateur de votre hôte SQL Server
<Location> - Emplacement de votre groupe de ressources SQL Server – Azure Arc , tel que West US, ou Central US
<tenantId> : L’ID de client est disponible en accédant à votre ressource Microsoft Entra ID dans le portail Azure. Dans le volet Vue d’ensemble, vous devez voir votre ID de locataire.
<instanceName> : Nom de l’instance SQL Server. Le nom de l’instance par défaut de SQL Server est MSSQLSERVER
<certSubjectName> - Nom du certificat que vous avez créé
<subscriptionId> : ID d’abonnement. Votre ID d’abonnement est disponible dans le portail Azure.
<resourceGroupName> : Le groupe de ressources contenant votre coffre de clés. La valeur azureKeyVaultResourceUID complète est disponible en accédant à votre ressource Key Vault, en sélectionnant Propriétés et en copiant l’ID de ressource
<keyVaultName> : Nom de votre coffre de clés
<certIdentifier> : L’identificateur du certificat pour votre stockage Azure Key Vault. Pour obtenir l’identificateur de certificat, accédez à votre ressource Key Vault, puis sélectionnez Certificats sous Paramètres. Sélectionnez la version actuelle du certificat que vous avez créé, puis copiez la valeur de l’identificateur de certificat. Pour plus d’informations, consultez Ajouter un certificat dans le coffre de clés.
<certSecret>- L’identificateur du secret de votre certificat se trouve dans le même menu que l’identificateur de certificat
Une fois l’administrateur Microsoft Entra configuré, l’utilisation des informations d’identification de l’administrateur Microsoft Entra vous permet de vous connecter à SQL Server. Toutefois, toutes les autres activités de base de données impliquant la création de connexions et d’utilisateurs Microsoft Entra échouent jusqu’à ce que le consentement de l’administrateur soit accordé à l’application Microsoft Entra.
Remarque
Pour octroyer le consentement administrateur pour l’application, le compte qui octroie nécessite un rôle d'administrateur général ou d'administrateur de rôle privilégié Microsoft Entra ID. Ces rôles sont nécessaires pour accorder le consentement de l’administrateur pour l’application, mais il n’est pas nécessaire de configurer l’administrateur Microsoft Entra.
Dans le Portail Azure, sélectionnez Microsoft Entra ID>Inscriptions d’applications, puis l’application nouvellement créée. L’application doit avoir un nom tel que <hostname>-<instanceName><uniqueNumber>.
Sélectionnez le menu Autorisations d’API.
Sélectionner Accorder le consentement administrateur.
Sans accorder le consentement administrateur à l’application, la création d’une connexion ou d’un utilisateur Microsoft Entra dans SQL Server entraîne l’erreur suivante :
Msg 37455, Level 16, State 1, Line 2
Server identity does not have permissions to access MS Graph.
Utiliser l’authentification Microsoft Entra pour se connecter à SQL Server
L’authentification Microsoft Entra est désormais configurée pour votre serveur SQL Server connecté à Azure Arc. Suivez les sections après avoir configuré l’administrateur Microsoft Entra dans l’article, Didacticiel : Configurer l’authentification Microsoft Entra pour SQL Server pour se connecter à SQL Server à l’aide de l’authentification Microsoft Entra.