使用受控識別連線到適用於 PostgreSQL 的 Azure 資料庫
適用於: 適用於 PostgreSQL 的 Azure 資料庫 - 單一伺服器
重要
適用於 PostgreSQL 的 Azure 資料庫 - 單一伺服器即將淘汰。 強烈建議您升級至適用於 PostgreSQL 的 Azure 資料庫 - 彈性伺服器。 如需移轉至適用於 PostgreSQL 的 Azure 資料庫 - 彈性伺服器的詳細資訊,請參閱適用於 PostgreSQL 的 Azure 資料庫單一伺服器會發生什麼情況? (部分機器翻譯)。
您可以使用系統指派和使用者指派的受控識別,來向適用於 PostgreSQL 的 Azure 資料庫進行驗證。 本文描述如何將系統指派的受控識別用於 Azure 虛擬機器 (VM),以存取適用於 PostgreSQL 的 Azure 資料庫伺服器。 Azure 會自動管理受控識別 ,讓您不需要將認證插入程式碼中即可驗證支援 Microsoft Entra 驗證的服務。
您將學習如何:
- 將您的 VM 存取權授與適用於 PostgreSQL 的 Azure 資料庫伺服器
- 在資料庫中建立使用者,以代表 VM 系統指派的身分識別
- 使用 VM 身分識別取得存取權杖,並使用其查詢適用於 PostgreSQL 的 Azure 資料庫伺服器
- 在 C# 範例應用程式中實作權杖擷取
必要條件
- 如果您不熟悉適用於 Azure 資源的受控識別功能,請參閱此概觀。 如果您沒有 Azure 帳戶,請先註冊免費帳戶,再繼續進行。
- 若要執行所需的資源建立和角色管理,您的帳戶必須在適當的範圍 (您的訂用帳戶或資源群組) 上具備「擁有者」權限。 如果您需要角色指派的協助,請參閱指派 Azure 角色來管理對您的 Azure 訂用帳戶資源的存取。
- 您需要 Azure VM (例如執行 Ubuntu Linux),以供您使用受控識別來存取資料庫
- 您需要已設定 Microsoft Entra 驗證的適用於 PostgreSQL 的 Azure 資料庫資料庫伺服器
- 若要遵循此 C# 範例,請先完成如何與 C# 連線的指南
為您的 VM 建立系統指派的受控識別
使用 az vm identity assign 與 identity assign
命令在現有的虛擬機器上啟用系統指派的身分識別:
az vm identity assign -g myResourceGroup -n myVm
為系統指派的受控識別擷取應用程式識別碼,後續幾個步驟中將會需要此識別碼:
# Get the client ID (application ID) of the system-assigned managed identity
az ad sp list --display-name vm-name --query [*].appId --out tsv
為您的受控識別建立 PostgreSQL 使用者
現在,以 Microsoft Entra 管理員使用者身分連線到 PostgreSQL 資料庫,然後執行下列 SQL 陳述式,將 CLIENT_ID
取代為您為系統指派的受控識別擷取的用戶端識別碼:
SET aad_validate_oids_in_tenant = off;
CREATE ROLE myuser WITH LOGIN PASSWORD 'CLIENT_ID' IN ROLE azure_ad_user;
當使用 myuser
使用者名稱 (以您選擇的名稱取代) 進行驗證時,受控識別現在具有存取權。
正在從 Azure 執行個體中繼資料服務擷取存取權杖
您的應用程式現在可以從 Azure 執行個體中繼資料服務擷取存取權杖,並用來向資料庫進行驗證。
藉由對 http://169.254.169.254/metadata/identity/oauth2/token
發出 HTTP 要求並傳遞下列參數,即可完成此權杖擷取:
api-version
=2018-02-01
resource
=https://ossrdbms-aad.database.windows.net
client_id
=CLIENT_ID
(您先前擷取的項目)
您將會得到包含 access_token
欄位的 JSON 結果 - 此長文字值是受控識別存取權杖,在連線到資料庫時,您應該用來作為密碼。
針對測試目的,您可以在殼層中執行下列命令。 請注意,您必須安裝 curl
、jq
和 psql
用戶端。
# Retrieve the access token
export PGPASSWORD=`curl -s 'http://169.254.169.254/metadata/identity/oauth2/token?api-version=2018-02-01&resource=https%3A%2F%2Fossrdbms-aad.database.windows.net&client_id=CLIENT_ID' -H Metadata:true | jq -r .access_token`
# Connect to the database
psql -h SERVER --user USER@SERVER DBNAME
您現在已連線到先前設定的資料庫。
在 C# 中使用受控識別進行連線
本節將說明如何使用 VM 使用者指派的受控識別來取得存取權杖,以用來呼叫適用於 PostgreSQL 的 Azure 資料庫。 適用於 PostgreSQL 的 Azure 資料庫原生支援 Microsoft Entra 驗證,因此可以直接接受使用 Azure 資源的受控識別所取得的存取權杖。 建立與 PostgreSQL 的連線時,您將存取權杖傳遞至密碼欄位。
以下是使用存取權杖來開啟與 PostgreSQL 連線的 .NET 程式碼範例。 此程式碼必須在 VM 上執行,才能使用系統指派的受控識別,從 Microsoft Entra ID 取得存取權杖。 取代 HOST、USER、DATABASE 和 CLIENT_ID 的值。
using System;
using System.Net;
using System.IO;
using System.Collections;
using System.Collections.Generic;
using System.Text.Json;
using System.Text.Json.Serialization;
using Npgsql;
using Azure.Identity;
namespace Driver
{
class Script
{
// Obtain connection string information from the portal for use in the following variables
private static string Host = "HOST";
private static string User = "USER";
private static string Database = "DATABASE";
static async Task Main(string[] args)
{
//
// Get an access token for PostgreSQL.
//
Console.Out.WriteLine("Getting access token from Azure AD...");
// Azure AD resource ID for Azure Database for PostgreSQL is https://ossrdbms-aad.database.windows.net/
string accessToken = null;
try
{
// Call managed identities for Azure resources endpoint.
var sqlServerTokenProvider = new DefaultAzureCredential();
accessToken = (await sqlServerTokenProvider.GetTokenAsync(
new Azure.Core.TokenRequestContext(scopes: new string[] { "https://ossrdbms-aad.database.windows.net/.default" }) { })).Token;
}
catch (Exception e)
{
Console.Out.WriteLine("{0} \n\n{1}", e.Message, e.InnerException != null ? e.InnerException.Message : "Acquire token failed");
System.Environment.Exit(1);
}
//
// Open a connection to the PostgreSQL server using the access token.
//
string connString =
String.Format(
"Server={0}; User Id={1}; Database={2}; Port={3}; Password={4}; SSLMode=Prefer",
Host,
User,
Database,
5432,
accessToken);
using (var conn = new NpgsqlConnection(connString))
{
Console.Out.WriteLine("Opening connection using access token...");
conn.Open();
using (var command = new NpgsqlCommand("SELECT version()", conn))
{
var reader = command.ExecuteReader();
while (reader.Read())
{
Console.WriteLine("\nConnected!\n\nPostgres version: {0}", reader.GetString(0));
}
}
}
}
}
}
執行時,此命令會提供如下的輸出:
Getting access token from Azure AD...
Opening connection using access token...
Connected!
Postgres version: PostgreSQL 11.11, compiled by Visual C++ build 1800, 64-bit