Esempio: Usare le librerie di Azure per creare un database

Questo esempio illustra come usare le librerie di gestione di Azure SDK per Python per creare a livello di codice un server flessibile di Database di Azure per MySQL e un database corrispondente. Include anche uno script che usa la mysql-connector-python libreria (non parte del Azure SDK) per connettersi ed eseguire query sul database.

È possibile adattare questo esempio per creare un server flessibile di Database di Azure per PostgreSQL modificando le importazioni e le chiamate API pertinenti dell'SDK.

Se si preferisce usare l'interfaccia della riga di comando di Azure, i comandi equivalenti dell'interfaccia della riga di comando di Azure vengono forniti più avanti in questo articolo. Per un'esperienza grafica, vedere la documentazione del portale di Azure:

Se non diversamente specificato, tutti gli esempi e i comandi di questo articolo funzionano allo stesso modo nelle shell bash di Linux/macOS e nelle shell dei comandi di Windows.

1: Configurare l'ambiente di sviluppo locale

Se non è già stato fatto, configurare un ambiente in cui è possibile eseguire il codice. Ecco alcune opzioni:

  • Configurare un ambiente virtuale Python usando venv o lo strumento preferito. Per iniziare a usare l'ambiente virtuale, assicurarsi di attivarlo. Per installare Python, vedere Installare Python.

    #!/bin/bash
    # Create a virtual environment
    python -m venv .venv
    # Activate the virtual environment
    source .venv/Scripts/activate # only required for Windows (Git Bash)
    
  • Usa un ambiente conda . Per installare Conda, vedere Installare Miniconda.

  • Usare un contenitore di sviluppo in Visual Studio Code o GitHub Codespaces.

2: Installare i pacchetti di libreria di Azure necessari

In questo passaggio si installano le librerie di Azure SDK necessarie per creare il database.

  1. Nella console creare un filerequirements.txt che elenca le librerie di gestione usate in questo esempio:

    azure-mgmt-resource
    azure-mgmt-rdbms
    azure-identity
    mysql-connector-python
    

    Annotazioni

    La mysql-connector-python libreria non fa parte di Azure SDK. Si tratta di una libreria di terze parti che è possibile usare per connettersi ai database MySQL. È anche possibile usare altre librerie, ad esempio PyMySQL o SQLAlchemy.

  2. Nella console con l'ambiente virtuale attivato installare i requisiti:

    pip install -r requirements.txt
    

    Annotazioni

    In Windows, il tentativo di installare la libreria mysql in una libreria Python a 32 bit genera un errore relativo al file mysql.h . In questo caso, installare una versione a 64 bit di Python e riprovare.

3. Impostare le variabili di ambiente

In questo passaggio vengono impostate le variabili di ambiente da usare nel codice in questo articolo. Il codice usa il os.environ metodo per recuperare i valori.

#!/bin/bash
export AZURE_RESOURCE_GROUP_NAME=<ResourceGroupName> # Change to your preferred resource group name
export LOCATION=<Location> # Change to your preferred region
export AZURE_SUBSCRIPTION_ID=$(az account show --query id --output tsv)
export PUBLIC_IP_ADDRESS=$(curl -s https://api.ipify.org)
export DB_SERVER_NAME=<DB_Server_Name> # Change to your preferred DB server name
export DB_ADMIN_NAME=<DB_Admin_Name> # Change to your preferred admin name
export DB_ADMIN_PASSWORD=<DB_Admin_Password> # Change to your preferred admin password
export DB_NAME=<DB_Name> # Change to your preferred database name
export DB_PORT=3306
export DB_SERVER_VERSION=EIGHT0_21

4: Scrivere codice per creare e configurare un server flessibile MySQL con un database

In questo passaggio viene creato un file Python denominato provision_db.py con il codice seguente. Questo script usa il Azure SDK per Python librerie di gestione per creare un gruppo di risorse, un server flessibile MySQL e un database in tale server.

import random, os
from azure.identity import DefaultAzureCredential
from azure.mgmt.resource import ResourceManagementClient
from azure.mgmt.rdbms.mysql_flexibleservers import MySQLManagementClient
from azure.mgmt.rdbms.mysql_flexibleservers.models import Server, ServerVersion

# Acquire a credential object using CLI-based authentication.
credential = DefaultAzureCredential()

# Retrieve subscription ID from environment variable
subscription_id = os.environ["AZURE_SUBSCRIPTION_ID"]

# Retrieve resource group name and location from environment variables
RESOURCE_GROUP_NAME = os.environ["AZURE_RESOURCE_GROUP_NAME"]
LOCATION = os.environ["LOCATION"]

# Step 1: Provision the resource group.
resource_client = ResourceManagementClient(credential, subscription_id)

rg_result = resource_client.resource_groups.create_or_update(RESOURCE_GROUP_NAME,
    { "location": LOCATION })

print(f"Provisioned resource group {rg_result.name}")

# For details on the previous code, see Example: Provision a resource group
# at https://learn.microsoft.com/azure/developer/python/azure-sdk-example-resource-group


# Step 2: Provision the database server

# Retrieve server name, admin name, and admin password from environment variables

db_server_name = os.environ.get("DB_SERVER_NAME")
db_admin_name = os.environ.get("DB_ADMIN_NAME")
db_admin_password = os.environ.get("DB_ADMIN_PASSWORD")

# Obtain the management client object
mysql_client = MySQLManagementClient(credential, subscription_id)

# Provision the server and wait for the result
server_version = os.environ.get("DB_SERVER_VERSION") 

poller = mysql_client.servers.begin_create(RESOURCE_GROUP_NAME,
    db_server_name, 
    Server(
        location=LOCATION,
        administrator_login=db_admin_name,
        administrator_login_password=db_admin_password,
        version=ServerVersion[server_version]  # Note: dictionary-style enum access
    )
)

server = poller.result()

print(f"Provisioned MySQL server {server.name}")

# Step 3: Provision a firewall rule to allow the local workstation to connect

RULE_NAME = "allow_ip"
ip_address = os.environ["PUBLIC_IP_ADDRESS"]

# Provision the rule and wait for completion
poller = mysql_client.firewall_rules.begin_create_or_update(RESOURCE_GROUP_NAME,
    db_server_name, RULE_NAME, 
    { "start_ip_address": ip_address, "end_ip_address": ip_address }  
)

firewall_rule = poller.result()

print(f"Provisioned firewall rule {firewall_rule.name}")


# Step 4: Provision a database on the server

db_name = os.environ.get("DB_NAME", "example-db1")
 
poller = mysql_client.databases.begin_create_or_update(RESOURCE_GROUP_NAME,
    db_server_name, db_name, {})

db_result = poller.result()

print(f"Provisioned MySQL database {db_result.name} with ID {db_result.id}")

Autenticazione nel codice

Più avanti in questo articolo si accede a Azure usando il interfaccia della riga di comando di Azure per eseguire il codice di esempio. Se l'account dispone di autorizzazioni sufficienti per creare gruppi di risorse e risorse di database nella sottoscrizione Azure, lo script viene eseguito correttamente senza una configurazione aggiuntiva.

Per gli ambienti di produzione, eseguire l'autenticazione usando un'entità servizio e impostare le variabili di ambiente appropriate. Questo approccio consente l'accesso sicuro e non interattivo adatto per l'automazione. Per istruzioni sull'installazione, vedere Come autenticare le app Python con i servizi di Azure.

Assicurarsi che all'entità servizio venga assegnato un ruolo con autorizzazioni adeguate, ad esempio il ruolo Collaboratore a livello di sottoscrizione o di gruppo di risorse. Per informazioni dettagliate sull'assegnazione dei ruoli, vedere Controllo degli accessi in base al ruolo in Azure.

Per il server di database PostgreSQL, vedere:

5: Eseguire lo script

  1. Se non è già stato fatto, accedere a Azure usando il interfaccia della riga di comando di Azure:

    az login
    
  2. Eseguire lo script:

    python provision_db.py
    

    Il completamento dello script richiede un minuto o due.

6: Inserire un record ed eseguire query sul database

In questo passaggio si crea una tabella nel database e si inserisce un record. Usare la mysql-connector libreria per connettersi al database ed eseguire comandi SQL.

  1. Creare un file denominato use_db.py con il codice seguente.

    Questo codice funziona solo per MySQL. Si usano librerie diverse per PostgreSQL.

    import os
    import mysql.connector
    
    db_server_name = os.environ["DB_SERVER_NAME"]
    db_admin_name = os.getenv("DB_ADMIN_NAME")
    db_admin_password = os.getenv("DB_ADMIN_PASSWORD")
    
    db_name = os.getenv("DB_NAME")
    db_port = os.getenv("DB_PORT")
    
    connection = mysql.connector.connect(user=db_admin_name,
        password=db_admin_password, host=f"{db_server_name}.mysql.database.azure.com",
        port=db_port, database=db_name, ssl_ca='./DigiCertGlobalRootG2.crt.pem')
    
    cursor = connection.cursor()
    
    """
    # Alternate pyodbc connection; include pyodbc in requirements.txt
    import pyodbc
    
    driver = "{MySQL ODBC 5.3 UNICODE Driver}"
    
    connect_string = f"DRIVER={driver};PORT=3306;SERVER={db_server_name}.mysql.database.azure.com;" \
                     f"DATABASE={DB_NAME};UID={db_admin_name};PWD={db_admin_password}"
    
    connection = pyodbc.connect(connect_string)
    """
    
    table_name = "ExampleTable1"
    
    sql_create = f"CREATE TABLE {table_name} (name varchar(255), code int)"
    
    cursor.execute(sql_create)
    print(f"Successfully created table {table_name}")
    
    sql_insert = f"INSERT INTO {table_name} (name, code) VALUES ('Azure', 1)"
    insert_data = "('Azure', 1)"
    
    cursor.execute(sql_insert)
    print("Successfully inserted data into table")
    
    sql_select_values= f"SELECT * FROM {table_name}"
    
    cursor.execute(sql_select_values)
    row = cursor.fetchone()
    
    while row:
        print(str(row[0]) + " " + str(row[1]))
        row = cursor.fetchone()
    
    connection.commit()
    

    Tutto questo codice usa l'API mysql.connector . L'unica parte specifica Azure è il dominio host completo per il server MySQL (mysql.database.azure.com).

  2. Scaricare quindi il certificato radice necessario per comunicare tramite TLS/SSL con il server Database di Azure per MySQL. Azure server flessibile MySQL usa il certificato DigiCert Global Root G2. Per altre informazioni, vedere Connect to Database di Azure per MySQL - Flexible Server with encrypted connections.

    #!/bin/bash
    # Download DigiCert Global Root G2 certificate required for Azure MySQL SSL connections
    CERT_URL="https://cacerts.digicert.com/DigiCertGlobalRootG2.crt.pem"
    CERT_FILE="DigiCertGlobalRootG2.crt.pem"
    echo "Downloading SSL certificate..."
    curl -o "$CERT_FILE" "$CERT_URL"
    
  3. Infine, eseguire il codice:

    python use_db.py
    

Se viene visualizzato un errore che indica che l'indirizzo IP del client non è consentito, verificare di aver definito correttamente la variabile PUBLIC_IP_ADDRESS di ambiente. Se il server MySQL è già stato creato con l'indirizzo IP errato, è possibile aggiungere un altro nel portale di Azure. Nel portale selezionare il server MySQL e quindi Rete. Aggiungere l'indirizzo IP della workstation all'elenco di indirizzi IP consentiti.

7: Pulire le risorse

Eseguire il comando az group delete se non è necessario mantenere il gruppo di risorse e le risorse del database create in questo esempio.

I gruppi di risorse non comportano addebiti in corso nella sottoscrizione, ma le risorse nel gruppo di risorse potrebbero continuare a comportare addebiti. È consigliabile pulire qualsiasi gruppo che non si usa attivamente. L'argomento --no-wait consente al comando di restituire immediatamente anziché attendere il completamento dell'operazione.

#!/bin/bash
az group delete -n $AZURE_RESOURCE_GROUP_NAME --no-wait

È anche possibile usare il metodo ResourceManagementClient.resource_groups.begin_delete per eliminare un gruppo di risorse dal codice. Il codice in Esempio: Creare un gruppo di risorse illustra l'utilizzo.

Per riferimento: comandi equivalenti interfaccia della riga di comando di Azure

I seguenti comandi dell'interfaccia della riga di comando di Azure completano gli stessi passaggi di provisioning dello script Python. Per un database PostgreSQL, usa az postgres flexible-server comandi.

#!/bin/bash

# Set variables
export LOCATION=<Location> # Change to your preferred region
export AZURE_RESOURCE_GROUP_NAME=<ResourceGroupName> # Change to your preferred resource group name
export DB_SERVER_NAME=<DB_Server_Name> # Change to your preferred DB server name
export DB_ADMIN_NAME=<DB_Admin_Name> # Change to your preferred admin name
export DB_ADMIN_PASSWORD=<DB_Admin_Password> # Change to your preferred admin password
export DB_NAME=<DB_Name> # Change to your preferred database name
export DB_SERVER_VERSION="8.4"

# Get public IP address
export PUBLIC_IP_ADDRESS=$(curl -s https://api.ipify.org)

# Provision the resource group
echo "Creating resource group: $AZURE_RESOURCE_GROUP_NAME"
az group create \
    --location "$LOCATION" \
    --name "$AZURE_RESOURCE_GROUP_NAME"

# Provision the MySQL Flexible Server
echo "Creating MySQL Flexible Server: $DB_SERVER_NAME"
az mysql flexible-server create \
    --location "$LOCATION" \
    --resource-group "$AZURE_RESOURCE_GROUP_NAME" \
    --name "$DB_SERVER_NAME" \
    --admin-user "$DB_ADMIN_NAME" \
    --admin-password "$DB_ADMIN_PASSWORD" \
    --sku-name Standard_B1ms \
    --version "$DB_SERVER_VERSION" \
    --yes

# Provision a firewall rule to allow access from the public IP address
echo "Creating firewall rule for public IP: $PUBLIC_IP_ADDRESS"
az mysql flexible-server firewall-rule create \
    --resource-group "$AZURE_RESOURCE_GROUP_NAME" \
    --name "$DB_SERVER_NAME" \
    --rule-name allow_ip \
    --start-ip-address "$PUBLIC_IP_ADDRESS" \
    --end-ip-address "$PUBLIC_IP_ADDRESS"

# Provision the database
echo "Creating database: $DB_NAME"
az mysql flexible-server db create \
    --resource-group "$AZURE_RESOURCE_GROUP_NAME" \
    --server-name "$DB_SERVER_NAME" \
    --database-name "$DB_NAME"

echo "MySQL Flexible Server and database created successfully."

Vedere anche