チュートリアル: Microsoft Entra アプリケーションを使用してMicrosoft Entraユーザーを作成する

適用対象:Azure SQL データベース

この記事では、Azure SQL DatabaseでMicrosoft Entraユーザーを作成できるようにサービス プリンシパルを構成する方法について説明します。 この機能を使用すると、Microsoft Entra テナント内のユーザーとアプリケーションのAzure SQL リソースへのアクセスをプログラムで管理できます。

注意

Microsoft Entra ID は、以前は Azure Active Directory (Azure AD) と呼れていました。

Azure SQLのMicrosoft Entra認証の詳細については、「 Microsoft Entra 認証の使用を参照してください。

このチュートリアルでは、次の作業を行う方法について説明します。

  • 論理サーバーに ID を割り当てる
  • サーバー ID にディレクトリ閲覧者ロールを割り当てる
  • Microsoft Entra IDにアプリケーションを登録する
  • Azure SQL Databaseでそのアプリケーションのサービス プリンシパルのデータベース ユーザーを作成する
  • サービス プリンシパルを用いてMicrosoft Entra データベース ユーザーを作成する

前提条件

  • 既存の Azure SQL Database デプロイ。 このチュートリアルでは、SQL Database が動作していることを前提としています。
  • Microsoft Entra Privileged Role Administrator 権限は、SQL データベースがあるテナントにあります。
  • 最新バージョンの Az.Sql PowerShell モジュール。
  • 最新バージョンのMicrosoft.Graph PowerShell モジュール。

論理サーバーに ID を割り当てる

  1. SQL データベースをホストするMicrosoft Entra テナントを指定して、Azureに接続します。 テナント ID は、Microsoft Entra ID リソースの Overview ページAzure ポータルにあります。 テナント ID をコピーし、次の PowerShell コマンドを実行します。

    • <TenantId>テナント ID に置き換えてください。
    Connect-AzAccount -Tenant <TenantId>
    

    TenantId は記録しておいてください。後でこのチュートリアルの中で使用します。

  2. システム割り当てマネージド ID を生成し、Azure の logical サーバーに割り当てます。 次の PowerShell コマンドを実行します。

    • <ResourceGroupName><ServerName> のリソースを Set-AzSqlServer コマンドで置き換えます。 実際のサーバー名が myserver.database.windows.net の場合、<ServerName>myserver に置き換えます。
    Set-AzSqlServer -ResourceGroupName <ResourceGroupName> -ServerName <ServerName> -AssignIdentity
    
  3. サーバー ID が正常に割り当てられたことを確認します。 次の PowerShell コマンドを実行します。

    • <ResourceGroupName><ServerName> をリソースに置き換えてください。 実際のサーバー名が myserver.database.windows.net の場合、<ServerName>myserver に置き換えます。
    $xyz = Get-AzSqlServer -ResourceGroupName <ResourceGroupName> -ServerName <ServerName>
    $xyz.identity
    

    出力には、 PrincipalIdType、および TenantIdが表示されます。 PrincipalId が、割り当てられた ID です。

  4. id を確認するには、Azure ポータルに移動します。

    • Microsoft Entra ID リソースで、Enterprise アプリケーション に移動します。 論理サーバーの名前を入力します。 リソースに表示されるオブジェクト ID は、プライマリ サーバー ID の ID です。

    エンタープライズ アプリケーションのオブジェクト ID を見つける場所を示すスクリーンショット。

ヒント

システム割り当てマネージド ID の代わりに、 ユーザー割り当てマネージド ID を使用できます。 ユーザー割り当てマネージド ID は、複数の論理サーバー間で共有できるため、管理する ID の数が減り、ロールの割り当てが簡素化されます。 詳細については、Microsoft Entra ID の Azure SQL におけるユーザー割り当てマネージド ID を参照してください。

ディレクトリ閲覧者ロールにサーバー ID を追加する

サーバー ID には、Microsoft Entraユーザーとログインの作成、Microsoft Entra グループ メンバーシップに基づいてユーザーのアクセス許可を適用するためのグループ拡張の実行など、管理機能のMicrosoft Entra IDを照会するためのアクセス許可が必要です。 クエリMicrosoft Entra IDに対するサーバー ID のアクセス許可が取り消された場合、またはサーバー ID が削除された場合、Microsoft Entra認証は機能を停止します。

Directory Readers ロールに追加するか、次の下位レベルのMicrosoft Graphアクセス許可を割り当てることで、Microsoft Entraクエリのアクセス許可をサーバー ID に割り当てます。

注意

このスクリプトは、Microsoft Entra Privileged Role Administrator 以降のロールによって実行する必要があります。

次のスクリプトは、Microsoft Entra Directory Readers Azure SQL Databaseの論理サーバーを表す ID にアクセス許可を付与します。

  • <TenantId> は、先ほど確認した TenantId に置き換えます。
  • <ServerName> を論理サーバー名に置き換えてください。 実際のサーバー名が myserver.database.windows.net の場合、<ServerName>myserver に置き換えます。
# This script grants "Directory Readers" permission to a service principal representing a logical server for Azure SQL Database
# It can be executed only by a user who is a member of the **Privileged Role Administrator** or higher role.
# To check if the "Directory Readers" role was granted, re-execute this script

Import-Module Microsoft.Graph.Authentication
$ServerIdentityName = "<ServerName>"    # Enter your logical server name
$TenantId = "<TenantId>"                # Enter your tenant ID

Connect-MgGraph -TenantId "<TenantId>" -Scopes "RoleManagement.ReadWrite.Directory,Application.Read.All"

# Get Microsoft Entra "Directory Readers" role and create if it doesn't exist
$roleName = "Directory Readers"
$role = Get-MgDirectoryRole -Filter "DisplayName eq '$roleName'"
if ($role -eq $null) {
    # Instantiate an instance of the role template
    $roleTemplate = Get-MgDirectoryRoleTemplate -Filter "DisplayName eq '$roleName'"
    New-MgDirectoryRoleTemplate -RoleTemplateId $roleTemplate.Id
    $role = Get-MgDirectoryRole -Filter "DisplayName eq '$roleName'"
}

# Get service principal for server
$roleMember = Get-MgServicePrincipal -Filter "DisplayName eq '$ServerIdentityName'"
$roleMember.Count
if ($roleMember -eq $null) {
    Write-Output "Error: No service principal with name '$($ServerIdentityName)' found, make sure that ServerIdentityName parameter was entered correctly."
    exit
}
if (-not ($roleMember.Count -eq 1)) {
    Write-Output "Error: Multiple service principals with name '$($ServerIdentityName)'"
    Write-Output $roleMember | Format-List DisplayName, Id, AppId
    exit
}

# Check if service principal is already member of Directory Readers role
$isDirReader = Get-MgDirectoryRoleMember -DirectoryRoleId $role.Id -Filter "Id eq '$($roleMember.Id)'"

if ($isDirReader -eq $null) {
    # Add principal to Directory Readers role
    Write-Output "Adding service principal '$($ServerIdentityName)' to 'Directory Readers' role'..."
    $body = @{
        "@odata.id"= "https://graph.microsoft.com/v1.0/directoryObjects/{$($roleMember.Id)}"
    }
    New-MgDirectoryRoleMemberByRef -DirectoryRoleId $role.Id -BodyParameter $body
    Write-Output "'$($ServerIdentityName)' service principal added to 'Directory Readers' role'."
} else {
    Write-Output "Service principal '$($ServerIdentityName)' is already member of 'Directory Readers' role'."
}

注意

このスクリプトからの出力は、ID がディレクトリ閲覧者ロールに割り当てられているかどうかを示します。 アクセス許可が付与されたかどうかわからない場合は、スクリプトを再実行できます。

SQL Managed Instanceの Directory Readers ロールを割り当てる方法についても同様の方法については、「管理者 Microsoft Entraの設定」を参照してください。

運用環境では、Microsoft Entra IDのロール割り当て可能なグループに Directory Readers ロールを割り当てることが一般的な管理方法です。 その後、グループの所有者はマネージド ID をグループに追加できます。 これにより、最小限の特権の原則が維持され、 特権ロール管理者ディレクトリ閲覧者 ロールをすべての SQL インスタンスに個別に付与する必要が回避されます。 この機能の詳細については、Microsoft Entra ID の Azure SQL における Directory Readers ロール をご参照ください。

Microsoft Entra IDでアプリケーションを作成する

アプリケーションを登録します。 アプリを登録するには、少なくとも Microsoft Entra ID Application Developer ロールが必要です。 ロールの割り当ての詳細については、「Microsoft Entra IDを参照してください。

このチュートリアルでは、2 つのサービス プリンシパルを使用します。 最初のサービス プリンシパル DBOwnerApp は、データベース内に他のユーザーを作成するために使用されます。 2 番目のサービス プリンシパル myapp は、このチュートリアルの後半で DBOwnerApp がデータベース ユーザーを作成するアプリケーションです。

アプリケーションを登録するには:

  1. Azure ポータルで、Microsoft Entra ID>App registrations>New registration を選択します。

    アプリケーションの登録ページを示すスクリーンショット。

    アプリの登録が作成されると、アプリケーション (クライアント) ID値が生成され、表示されます。 この値は記録しておいてください。後でこのチュートリアルの中で使用します。

    アプリ ID を示す Azure ポータルのスクリーンショット

  2. サインイン用に、アプリケーションのクライアント シークレットを作成します。 「証明書をアップロードするか、サインイン用のシークレットを作成する」に従います。 このチュートリアルで今後使用するために、DBOwnerApp のクライアント シークレットを記録します。

詳細については、「リソースにアクセスできるMicrosoft Entra アプリケーションとサービス プリンシパルを作成するには、ポータルを使用しますを確認してください。

サービス プリンシパル ユーザーを作成する

新しく作成したサービス プリンシパル DBOwnerApp を SQL Database のユーザーとして追加し、それにアクセス許可を割り当てます。

他のユーザーを作成するアクセス許可を持つMicrosoft Entra ID を使用して SQL Database に接続します。

重要

Azure SQL Databaseで他のMicrosoft Entra ユーザーを作成できるのは、Microsoft Entraユーザーだけです。 SQL 認証に基づくユーザー (サーバー管理者を含む) は、Microsoft Entra ユーザーを作成できません。 Microsoft Entra管理者は、SQL Database で最初に他のMicrosoft Entra ユーザーを作成できる唯一のユーザーです。 Microsoft Entra管理者が他のユーザーを作成した後、適切なアクセス許可を持つMicrosoft Entraユーザーは、他のMicrosoft Entraユーザーを作成できます。

  1. 次の T-SQL コマンドを使用して、SQL Database にユーザー DBOwnerApp を作成します。

    CREATE USER [DBOwnerApp] FROM EXTERNAL PROVIDER
    GO
    
  2. 他のMicrosoft Entraユーザーを作成するには、少なくとも、ALTER ANY USER SQL アクセス許可が必要です。 このアクセス許可は、db_owner のメンバーシップと、Microsoft Entra管理者としての割り当てを通じて継承されます。次の例では、DBOwnerApp にアクセス許可を割り当てる 3 つの異なるオプションを示します。これにより、データベースに他のMicrosoft Entra ユーザーを作成できます。

    sp_addrolemember を使って、db_owner の役割に追加できます。

    EXEC sp_addrolemember 'db_owner', [DBOwnerApp]
    GO
    

    次のT-SQLサンプルのように、ALTER ANY USER 権限を DBOwnerApp に割り当てることができます。

    GRANT ALTER ANY USER TO [DBOwnerApp]
    GO
    

    DBOwnerApp をMicrosoft Entra管理者として設定できます。Azure ポータル、PowerShell、またはAzure CLI コマンドを使用します。 詳細については、「set Microsoft Entra admin」を参照>。

サービス プリンシパルを使用してユーザーを作成する

  1. 次のスクリプトを使用して、サービス プリンシパル DBOwnerApp を通じて Microsoft Entra サービス プリンシパル ユーザー myapp を作成します。

    • <TenantId> は、先ほど確認した TenantId に置き換えます。
    • <ClientId> は、先ほど確認した ClientId に置き換えます。
    • <ClientSecret> は、先ほど作成したクライアント シークレットに置き換えます。
    • <ServerName> を論理サーバー名に置き換えてください。 実際のサーバー名が myserver.database.windows.net の場合、<ServerName>myserver に置き換えます。
    • SQLデータベースの名前に<database name>を置き換えてください。

    注意

    次のスクリプトには、Microsoft.Data.SqlClient アセンブリが必要です。 スクリプトを実行する前に、NuGet パッケージからインストールし、Add-Type -Path "path\to\Microsoft.Data.SqlClient.dll" で DLL を読み込みます。

    # PowerShell script for creating a new SQL user called myapp using application DBOwnerApp with secret
    # DBOwnerApp is an admin for the server
    
    # Download latest  MSAL  - https://www.powershellgallery.com/packages/MSAL.PS
    Import-Module MSAL.PS
    
    $tenantId = "<TenantId>"   # Microsoft Entra tenant ID where DBOwnerApp resides
    $clientId = "<ClientId>"   # Application (client) ID recorded earlier for DBOwnerApp
    $clientSecret = "<ClientSecret>"   # Client secret for DBOwnerApp
    $scopes = "https://database.windows.net/.default" # The endpoint
    
    $result = Get-MsalToken -RedirectUri $uri -ClientId $clientId -ClientSecret (ConvertTo-SecureString $clientSecret -AsPlainText -Force) -TenantId $tenantId -Scopes $scopes
    
    $Tok = $result.AccessToken
    #Write-host "token"
    $Tok
    
    $SQLServerName = "<ServerName>"    # Logical server name
    $DatabaseName = "<database name>"   # Azure SQL database name
    
    Write-Host "Create SQL connection string"
    $conn = New-Object Microsoft.Data.SqlClient.SqlConnection
    $conn.ConnectionString = "Data Source=$SQLServerName.database.windows.net;Initial Catalog=$DatabaseName;Connect Timeout=30"
    $conn.AccessToken = $Tok
    
    Write-host "Connect to database and execute SQL script"
    $conn.Open()
    $ddlstmt = 'CREATE USER [myapp] FROM EXTERNAL PROVIDER;'
    Write-host " "
    Write-host "SQL DDL command"
    $ddlstmt
    $command = New-Object -TypeName Microsoft.Data.SqlClient.SqlCommand($ddlstmt, $conn)
    
    Write-host "results"
    $command.ExecuteNonQuery()
    $conn.Close()
    

    または、次のコードを使用できます: Azure SQL Database に対する Microsoft Entra サービス プリンシパル認証。 DDL ステートメント CREATE USER [myapp] FROM EXTERNAL PROVIDER を実行するようにスクリプトを変更してください。 同じスクリプトを使用して、データベースにMicrosoft Entraユーザーまたはグループを作成します。

  2. 次のコマンドを実行して、ユーザー myapp がデータベースに存在するかどうかを確認します。

    SELECT name, type, type_desc, CAST(CAST(sid as varbinary(16)) as uniqueidentifier) as appId
    FROM sys.database_principals
    WHERE name = 'myapp'
    GO
    

    同様の出力が表示されます。

    name    type    type_desc    appId
    myapp    E    EXTERNAL_USER    aaaaaaaa-0000-1111-2222-bbbbbbbbbbbb