在本教學課程中,您會部署 Python Flask 程式碼,以建立及部署在 Azure 應用程式服務中執行的 Web 應用程式。 Web 應用程式會使用其系統指派的 受控識別(無密碼連線),搭配 Azure 角色型存取控制來存取 Azure 儲存體 和 適用於 PostgreSQL 的 Azure 資料庫 - 彈性伺服器 資源。 此程式碼使用 Azure 身分識別用戶端程式庫中適用於 Python 的 DefaultAzureCredential 類別。
DefaultAzureCredential
類別會自動偵測 App Service 中受控識別的存在,並使用它來存取其他 Azure 資源。
您可以使用 Service Connector 設定 Azure 服務的無密碼連線,也可以手動設定它們。 本教學課程示範如何使用 Service Connector。 如需有關無密碼連線的更多資訊,請參閱《Azure 服務無密碼連線》。 如需 Service Connector 的相關信息,請參閱 Service Connector 檔。
本教學課程說明如何使用 Azure CLI 建立及部署 Python Web 應用程式。 本教學課程中的命令是用於在 Bash Shell 中執行的。 您可以在任何已安裝 CLI 的 Bash 環境中執行教學命令,例如本機環境或 Azure Cloud Shell。 透過一些修改 -- 例如,設定和使用環境變數 -- 您可以在 Windows 命令殼層等其他環境中執行這些命令。 如需使用者指派受控識別的範例,請參閱 建立和部署具有使用者指派受控識別的 Django Web 應用程式至 Azure。
取得範例應用程式
您可以使用 Flask 架構的範例 Python 應用程式,協助您遵循本教學課程。 下載或複製其中一個範例應用程式至本機工作站。
在 Azure Cloud Shell 環境中複製範例。
git clone https://github.com/Azure-Samples/msdocs-flask-web-app-managed-identity.git
瀏覽至應用程式資料夾。
cd msdocs-flask-web-app-managed-identity
檢查驗證碼
範例 Web 應用程式必須向兩個不同的資料存放區進行驗證:
- Azure Blob 記憶體伺服器會儲存並擷取檢閱者提交的相片。
- 適用於 PostgreSQL 的 Azure 資料庫 - 彈性伺服器資料庫,其儲存餐廳與評論。
它使用 DefaultAzureCredential 來對兩個資料儲存區進行身份驗證。 使用 DefaultAzureCredential
,應用程式可以設定為在不同的服務主體身份下執行,而不需改變代碼,這取決於其所在運行的環境。 例如,在本機開發環境中,應用程式可以在開發人員登入 Azure CLI 的身分識別下執行,而在 Azure 中,如本教學課程所示,它可以在其系統指派的受控識別下執行。
不論是哪一種情況,應用程式執行的安全性主體都必須在應用程式所使用的每個 Azure 資源上具有角色,才能在應用程式所需的資源上執行動作。 在本教學課程中,您會使用服務連接器,在 Azure 中的應用程式中自動啟用系統指派的受控識別,並在 Azure 記憶體帳戶和 適用於 PostgreSQL 的 Azure 資料庫 伺服器上指派該身分識別適當的角色。
啟用系統指派的管理型識別並在資料存儲上指派適當的角色之後,您可以使用 DefaultAzureCredential
來驗證所需的 Azure 資源。
下列程式碼用於建立 Blob 儲存用戶端,以在app.py
中上傳相片。 用戶端會收到一個 DefaultAzureCredential
實例,以用來取得存取令牌,從而對 Azure 儲存體執行作業。
from azure.identity import DefaultAzureCredential
from azure.storage.blob import BlobServiceClient
azure_credential = DefaultAzureCredential()
blob_service_client = BlobServiceClient(
account_url=account_url,
credential=azure_credential)
在DefaultAzureCredential
中使用的實例也可用來取得Azure Database for PostgreSQL的存取令牌,位於./azureproject/get_conn.py
。 在此情況下,令牌會直接透過在認證實例上呼叫 get_token 並傳入適當的 scope
值來取得。 然後,令牌會用來取代傳回給呼叫端的 PostgreSQL 連線 URI 中的密碼。
azure_credential = DefaultAzureCredential()
token = azure_credential.get_token("https://ossrdbms-aad.database.windows.net")
conn = str(current_app.config.get('DATABASE_URI')).replace('PASSWORDORTOKEN', token.token)
若要深入瞭解如何使用適用於 Python 的 Azure SDK 驗證您的 Python 應用程式至 Azure 服務,請參閱 利用 Azure SDK 驗證 Python 應用程式的指引。 若要深入瞭解 DefaultAzureCredential
,包括如何針對您的環境自定義其所評估的認證鏈結,請參閱 DefaultAzureCredential 概觀。
建立 Azure PostgreSQL 伺服器
設定教學課程所需的環境變數。
LOCATION="eastus" RAND_ID=$RANDOM RESOURCE_GROUP_NAME="msdocs-mi-web-app" APP_SERVICE_NAME="msdocs-mi-web-$RAND_ID" DB_SERVER_NAME="msdocs-mi-postgres-$RAND_ID" ADMIN_USER="demoadmin" ADMIN_PW="ChAnG33#ThsPssWD$RAND_ID"
重要
ADMIN_PW
必須包含下列三個類別的8到128個字元:英文大寫字母、英文小寫字母、數字和特殊符號。 建立使用者名稱或密碼時不要使用 字元。 稍後,您將使用這些值創建環境變數,其中$
字元在 Linux 容器中具有特殊意義,該容器用來運行 Python 應用程式。使用 az group create 命令來建立資源群組。
az group create --location $LOCATION --name $RESOURCE_GROUP_NAME
使用 az postgres flexible-server create 命令建立 PostgreSQL 伺服器。 這個和後續的命令會使用Bash Shell的行接續字元('\')。 如果需要,變更命令行介面的行續延字符。
az postgres flexible-server create \ --resource-group $RESOURCE_GROUP_NAME \ --name $DB_SERVER_NAME \ --location $LOCATION \ --admin-user $ADMIN_USER \ --admin-password $ADMIN_PW \ --sku-name Standard_D2ds_v4
sku-name 是定價層和計算組態的名稱。 如需更多資訊,請參閱 Azure PostgreSQL 資料庫的定價資訊。 若要列出可用的 SKU, 請使用
az postgres flexible-server list-skus --location $LOCATION
。使用 az postgres flexible-server execute 命令建立名為
restaurant
的資料庫。az postgres flexible-server execute \ --name $DB_SERVER_NAME \ --admin-user $ADMIN_USER \ --admin-password $ADMIN_PW \ --database-name postgres \ --querytext 'create database restaurant;'
建立 Azure App 服務並部署程序代碼
使用 az webapp up 命令建立 App Service。
az webapp up \ --resource-group $RESOURCE_GROUP_NAME \ --name $APP_SERVICE_NAME \ --runtime PYTHON:3.9 \ --sku B1
SKU 會定義 App Service 方案的大小(CPU、記憶體)和成本。 B1 (基本) 服務方案會在您的 Azure 訂用帳戶中產生少量成本。 如需 App Service 方案的完整清單,請檢視 App Service 定價頁面。
將 App Service 設定為使用 存放庫中的 start.sh 與 az webapp config set 命令。
az webapp config set \ --resource-group $RESOURCE_GROUP_NAME \ --name $APP_SERVICE_NAME \ --startup-file "start.sh"
建立 Azure 資源的無密碼連接器
Service Connector 命令會將 Azure 儲存體 和 適用於 PostgreSQL 的 Azure 資料庫 資源設定為使用受控識別和 Azure 角色型存取控制。 命令會在 App Service 中建立應用程式設定,以將 Web 應用程式連線到這些資源。 命令的輸出會列出用來啟用無密碼功能的服務連接器動作。
使用 az webapp connection create postgres-flexible 命令新增 PostgreSQL 服務連接器。 系統指派的受控識別可用來向目標資源驗證 Web 應用程式,在此案例中為 PostgreSQL。
az webapp connection create postgres-flexible \ --resource-group $RESOURCE_GROUP_NAME \ --name $APP_SERVICE_NAME \ --target-resource-group $RESOURCE_GROUP_NAME \ --server $DB_SERVER_NAME \ --database restaurant \ --client-type python \ --system-identity
使用 az webapp connection create storage-blob 命令新增記憶體服務連接器。
此命令也會新增記憶體帳戶,並將具有記憶體 Blob 資料參與者角色的 Web 應用程式新增至記憶體帳戶。
STORAGE_ACCOUNT_URL=$(az webapp connection create storage-blob \ --new true \ --resource-group $RESOURCE_GROUP_NAME \ --name $APP_SERVICE_NAME \ --target-resource-group $RESOURCE_GROUP_NAME \ --client-type python \ --system-identity \ --query configurations[].value \ --output tsv) STORAGE_ACCOUNT_NAME=$(cut -d . -f1 <<< $(cut -d / -f3 <<< $STORAGE_ACCOUNT_URL))
在儲存體帳戶中建立容器
範例 Python 應用程式會將檢閱者提交的相片儲存為記憶體帳戶中容器中的 Blob。
當使用者提交相片檢閱時,範例應用程式會使用其系統指派的受控識別將映像寫入容器,以進行驗證和授權。 您在上一節中設定了這項功能。
當用戶檢視餐廳的評論時,應用程式會針對每個與該評論相關聯的檢閱,傳回 Blob 記憶體中相片的連結。 若要讓瀏覽器顯示相片,它必須能夠在記憶體帳戶中存取它。 Blob 數據必須可供透過匿名(未經驗證)存取公開讀取。
為了增強安全性,記憶體帳戶預設會以匿名存取已停用的 Blob 數據來建立。 在本節中,您會在記憶體帳戶上啟用匿名讀取許可權,然後建立名為 photos 的容器,以提供其 Blob 的公用(匿名)存取權。
使用 az storage account update 命令來更新記憶體帳戶,以允許匿名讀取 Blob。
az storage account update \ --name $STORAGE_ACCOUNT_NAME \ --resource-group $RESOURCE_GROUP_NAME \ --allow-blob-public-access true
在記憶體帳戶上啟用匿名存取不會影響個別 Blob 的存取。 您必須在容器層級明確啟用 Blob 的公用存取權。
使用 az storage container create 命令,在儲存帳戶中建立名為 photos 的容器。 允許對新建立容器中的 Blob 進行匿名讀取(公用)存取。
az storage container create \ --account-name $STORAGE_ACCOUNT_NAME \ --name photos \ --public-access blob \ --account-key $(az storage account keys list --account-name $STORAGE_ACCOUNT_NAME \ --query [0].value --output tsv)
注意
為了簡潔起見,此命令會使用記憶體帳戶密鑰來授權記憶體帳戶。 在大部分情況下,Microsoft的建議方法是使用Microsoft Entra ID 和 Azure (RBAC) 角色。 如需一組快速的指示,請參閱 快速入門:使用 Azure CLI 建立、下載及列出 Blob。 請注意,數個 Azure 角色可讓您在記憶體帳戶中建立容器,包括「擁有者」、「參與者」、「記憶體 Blob 數據擁有者」和「記憶體 Blob 數據參與者」。
若要深入瞭解 Blob 資料的匿名讀取存取,請參閱 設定容器和 Blob 的匿名讀取存取。
在 Azure 中測試 Python Web 應用程式
範例 Python 應用程式會使用 azure.identity 套件及其對應的類別。 當應用程式在 Azure 中執行時,DefaultAzureCredential
會自動偵測 App Service 是否有受控識別存在。如果是的話,則會使用它來存取其他 Azure 資源(在此案例中為儲存和 PostgreSQL)。 不需要提供記憶體金鑰、憑證或認證給 App Service,才能存取這些資源。
請瀏覽至已部署應用程式的網址
http://$APP_SERVICE_NAME.azurewebsites.net
。應用程式可能需要一兩分鐘的時間才能啟動。 如果您看到的預設應用程式頁面不是預設範例頁面,請稍等一分鐘,再重新整理瀏覽器。
藉由新增餐廳以及一些具有餐廳相片的評論,測試範例應用程式的功能。
餐廳和評論資訊儲存在 適用於 PostgreSQL 的 Azure 資料庫,照片儲存在 Azure 儲存體。 以下是範例螢幕快照:
範例應用程式的螢幕快照顯示餐廳評論功能,其中使用了 Azure App 服務、Azure PostgreSQL 資料庫和 Azure 儲存體。
清理
在本教學課程中,所有 Azure 資源都是在相同的資源群組中建立的。 使用 az group delete 命令移除資源群組,會移除該資源群組中的所有資源,這是移除應用程式所用所有 Azure 資源最快的方式。
az group delete --name $RESOURCE_GROUP_NAME
您可以選擇性地新增--no-wait
參數,以允許命令在操作完成之前返回。
下一步
使用使用者指派的受控識別建立並部署 Django 網頁應用程式至 Azure
在 Azure App Service 中使用 PostgreSQL 部署 Python Web 應用程式(Django 或 Flask)