Panoramica delle app contenitore Python in Azure

Questo articolo descrive come passare dal codice del progetto Python (ad esempio, un'app Web) a un contenitore Docker distribuito in Azure. Di seguito è illustrato il processo generale di containerizzazione, le opzioni di distribuzione per i contenitori in Azure e la configurazione specifica di Python dei contenitori in Azure.

La natura dei contenitori Docker è che la creazione di un'immagine Docker dal codice e la distribuzione di tale immagine in un contenitore in Azure è simile nei linguaggi di programmazione. Le considerazioni specifiche del linguaggio, Python in questo caso, sono nella configurazione durante il processo di containerizzazione in Azure, in particolare la struttura e la configurazione dockerfile che supportano framework Web Python, ad esempio Django, Flask e FastAPI.

Scenari del flusso di lavoro del contenitore

Per lo sviluppo di contenitori Python, alcuni flussi di lavoro tipici per lo spostamento dal codice al contenitore sono:

Scenario Descrizione Workflow
Dev Compilare immagini Docker Python nell'ambiente di sviluppo. Codice: codice clone git nell'ambiente di sviluppo (con Docker installato).

Compilazione: usare l'interfaccia della riga di comando di Docker, VS Code (con estensioni), PyCharm (con plug-in). Descritto nella sezione Uso di immagini e contenitori Docker Python.

Test: nell'ambiente di sviluppo in un contenitore Docker.

Push: in un registro come Registro Azure Container, hub Docker o registro privato.

Distribuire: nel servizio di Azure dal Registro di sistema.
Ibrido Dall'ambiente di sviluppo compilare immagini Docker Python in Azure. Codice: codice clone git nell'ambiente di sviluppo (non necessario per l'installazione di Docker).

Build: VS Code (con estensioni), interfaccia della riga di comando di Azure.

Push: per Registro Azure Container

Distribuire: nel servizio di Azure dal Registro di sistema.
Azure Tutto nel cloud; usare Azure Cloud Shell per compilare codice di immagini Docker Python dal repository GitHub. Codice: repository GitHub clone git in Azure Cloud Shell.

Compilazione: in Azure Cloud Shell usare l'interfaccia della riga di comando di Azure o l'interfaccia della riga di comando di Docker.

Push: per eseguire il registro, ad esempio Registro Azure Container, Hub Docker o registro privato.

Distribuire: nel servizio di Azure dal Registro di sistema.

L'obiettivo finale di questi flussi di lavoro è avere un contenitore in esecuzione in una delle risorse di Azure che supportano i contenitori Docker, come indicato nella sezione successiva.

Un ambiente di sviluppo può essere la workstation locale con Visual Studio Code o PyCharm, Codespaces (un ambiente di sviluppo ospitato nel cloud) o i contenitori di sviluppo di Visual Studio (un contenitore come ambiente di sviluppo).

Opzioni del contenitore di distribuzione in Azure

Le app contenitore Python sono supportate nei servizi seguenti.

Servizio Descrizione
App Web per contenitori Servizio di hosting completamente gestito per applicazioni Web in contenitori, inclusi siti Web e API Web. Le app Web in contenitori nel servizio app Azure possono essere ridimensionate in base alle esigenze e usare flussi di lavoro CI/CD semplificati con l'hub Docker, Registro Azure Container e GitHub. Ideale come semplice implementazione per gli sviluppatori per sfruttare la piattaforma del servizio app Azure completamente gestita, ma che vuole anche un singolo artefatto distribuibile contenente un'app e tutte le relative dipendenze.

Esempio: distribuire un'app Web Flask o FastPI nel servizio app Azure.
App Azure Container (ACA) Un servizio contenitore serverless completamente gestito basato su Kubernetes e tecnologie open source come Dapr, KEDA e envoy. In base alle procedure consigliate e ottimizzate per i contenitori per utilizzo generico. L'infrastruttura del cluster è gestita da ACA e l'accesso diretto all'API Kubernetes non è supportato. Fornisce molti concetti specifici dell'applicazione oltre ai contenitori, tra cui certificati, revisioni, scalabilità e ambienti. Ideale per i team che vogliono iniziare a creare microservizi contenitore senza dover gestire la complessità sottostante di Kubernetes.

Esempio: distribuire un'app Web Flask o FastPI in App Contenitore di Azure.
Istanze di Azure Container Offerta serverless che fornisce un singolo pod di contenitori isolati Hyper-V su richiesta. Fatturata in base al consumo anziché alle risorse di cui è stato effettuato il provisioning. I concetti come scalabilità, bilanciamento del carico e certificati non vengono forniti con i contenitori ACI. Gli utenti spesso interagiscono con ACI tramite altri servizi; ad esempio servizio Azure Kubernetes per l'orchestrazione. Ideale se è necessario un blocco predefinito meno "opinioneato" che non è allineato agli scenari per cui App Contenitore di Azure sta ottimizzando.

Esempio: creare un'immagine del contenitore per la distribuzione in Istanze di Azure Container. L'esercitazione non è specifica di Python, ma i concetti illustrati si applicano a tutti i linguaggi.
Servizio Azure Kubernetes (AKS) Opzione Kubernetes completamente gestita in Azure. Supporta l'accesso diretto all'API Kubernetes ed esegue qualsiasi carico di lavoro Kubernetes. Il cluster completo si trova nella sottoscrizione, con le configurazioni e le operazioni del cluster all'interno del controllo e della responsabilità. Ideale per i team che cercano una versione completamente gestita di Kubernetes in Azure.

Esempio: distribuire un cluster servizio Azure Kubernetes usando l'interfaccia della riga di comando di Azure.
Funzioni di Azure Soluzione di funzioni serverless basate su eventi (FAAS). Condivide molte caratteristiche con App Contenitore di Azure per la scalabilità e l'integrazione con gli eventi, ma è ottimizzata per le funzioni temporanee distribuite come codice o contenitori. Ideale per i team che cercano di attivare l'esecuzione di funzioni sugli eventi; ad esempio, per eseguire l'associazione ad altre origini dati.

Esempio: creare una funzione in Linux usando un contenitore personalizzato.

Per un confronto più dettagliato di questi servizi, vedere Confronto tra app contenitore e altre opzioni del contenitore di Azure.

Ambienti virtuali e contenitori

Quando si esegue un progetto Python in un ambiente di sviluppo, l'uso di un ambiente virtuale è un modo comune per gestire le dipendenze e garantire la riproducibilità della configurazione del progetto. Un ambiente virtuale include un interprete Python, librerie e script installati richiesti dal codice del progetto in esecuzione in tale ambiente. Le dipendenze per i progetti Python vengono gestite tramite il file requirements.txt .

Suggerimento

Con i contenitori, gli ambienti virtuali non sono necessari a meno che non vengano usati per i test o altri motivi. Se si usano ambienti virtuali, non copiarli nell'immagine Docker. Usare il file con estensione dockerignore per escluderli.

È possibile considerare i contenitori Docker come funzionalità simili agli ambienti virtuali, ma con ulteriori vantaggi per la riproducibilità e la portabilità. Il contenitore Docker può essere eseguito ovunque sia possibile eseguire i contenitori, indipendentemente dal sistema operativo.

Un contenitore Docker contiene il codice del progetto Python e tutto il codice necessario per l'esecuzione. A questo punto, è necessario compilare il codice del progetto Python in un'immagine Docker e quindi creare un contenitore, un'istanza eseguibile di tale immagine.

Per la containerizzazione dei progetti Python, i file chiave sono:

File di progetto Descrizione
requirements.txt Usato durante la compilazione dell'immagine Docker per ottenere le dipendenze corrette nell'immagine.
Dockerfile Usato per specificare come compilare l'immagine Docker python. Per altre informazioni, vedere la sezione Istruzioni di Dockerfile per Python.
.dockerignore I file e le directory in .dockerignore non vengono copiati nell'immagine Docker con il COPY comando nel Dockerfile. Il file con estensione dockerignore supporta modelli di esclusione simili ai file con estensione gitignore . Per altre informazioni, vedere file .dockerignore.

L'esclusione dei file consente di migliorare le prestazioni di compilazione delle immagini, ma deve essere usata anche per evitare di aggiungere informazioni riservate all'immagine in cui è possibile esaminarla. Ad esempio, . dockerignore deve contenere righe per ignorare .env e .venv (ambienti virtuali).

Impostazioni del contenitore per framework Web

I framework Web hanno porte predefinite su cui sono in ascolto delle richieste Web. Quando si lavora con alcune soluzioni contenitore di Azure, è necessario specificare la porta su cui il contenitore è in ascolto che riceverà il traffico.

Framework Web Porta
Django 8000
Flask 5000 o 5002
FastAPI (uvicorn) 8000 o 80

La tabella seguente illustra come impostare la porta per le soluzioni contenitore di Azure diverse.

Soluzione contenitore di Azure Come impostare la porta dell'app Web
App Web per contenitori Per impostazione predefinita, servizio app presuppone che il contenitore personalizzato sia in ascolto sulla porta 80 o sulla porta 8080. Se il contenitore è in ascolto di una porta diversa, impostare l'impostazione dell'app WEBSITES_PORT nell'app servizio app. Per altre informazioni, vedere Configurare un contenitore personalizzato per app Azure Servizio.
App per contenitori di Azure App Azure Container consente di esporre l'app contenitore al Web pubblico, alla rete virtuale o ad altre app contenitore all'interno dell'ambiente abilitando l'ingresso. Impostare l'ingresso targetPort sulla porta su cui il contenitore è in ascolto per le richieste in ingresso. L'endpoint di ingresso dell'applicazione viene sempre esposto sulla porta 443. Per altre informazioni, vedere Configurare l'ingresso HTTPS o TCP nelle app contenitore di Azure.
Istanze di Azure Container, Azure Kubernetes Impostare la porta durante la creazione di un contenitore. È necessario assicurarsi che la soluzione abbia un framework Web, un server applicazioni (ad esempio gunicorn, uvicorn) e un server Web (ad esempio, nginx). Ad esempio, è possibile creare due contenitori, un contenitore con un framework Web e un server applicazioni e un altro framework con un server Web. I due contenitori comunicano su una porta e il contenitore del server Web espone 80/443 per le richieste esterne.

Python Dockerfile

Un Dockerfile è un file di testo che contiene istruzioni per la compilazione di un'immagine Docker. La prima riga indica l'immagine di base da cui iniziare. Questa riga è seguita da istruzioni per installare i programmi necessari, copiare i file e altre istruzioni per creare un ambiente di lavoro. Ad esempio, alcuni esempi specifici di Python per le istruzioni chiave di Python Dockerfile vengono mostrati nella tabella seguente.

Istruzione Scopo Esempio
FROM Imposta l'immagine di base per le istruzioni successive. FROM python:3.8-slim
EXPO edizione Standard Indica a Docker che il contenitore è in ascolto sulle porte di rete specificate in fase di esecuzione. EXPOSE 5000
COPIA Copia file o directory dall'origine specificata e li aggiunge al file system del contenitore nel percorso di destinazione specificato. COPY . /app
CORRERE Esegue un comando all'interno dell'immagine Docker. Ad esempio, eseguire il pull delle dipendenze. Il comando viene eseguito una sola volta in fase di compilazione. RUN python -m pip install -r requirements.txt
CMD Il comando fornisce l'impostazione predefinita per l'esecuzione di un contenitore. Può essere presente una sola istruzione CMD. CMD ["gunicorn", "--bind", "0.0.0.0:5000", "wsgi:app"]

Il comando di compilazione Docker compila immagini Docker da un Dockerfile e da un contesto. Il contesto di una compilazione è il set di file che si trovano nel percorso o nell'URL specificato. In genere, si compilerà un'immagine dalla radice del progetto Python e il percorso del comando di compilazione è ".", come illustrato nell'esempio seguente.

docker build --rm --pull  --file "Dockerfile"  --tag "mywebapp:latest"  .

Il processo di compilazione può fare riferimento a uno qualsiasi dei file nel contesto. Ad esempio, la compilazione può usare un'istruzione COPY per fare riferimento a un file nel contesto. Ecco un esempio di Dockerfile per un progetto Python usando il framework Flask :

FROM python:3.8-slim

EXPOSE 5000

# Keeps Python from generating .pyc files in the container.
ENV PYTHONDONTWRITEBYTECODE=1

# Turns off buffering for easier container logging
ENV PYTHONUNBUFFERED=1

# Install pip requirements.
COPY requirements.txt .
RUN python -m pip install -r requirements.txt

WORKDIR /app
COPY . /app

# Creates a non-root user with an explicit UID and adds permission to access the /app folder.
RUN adduser -u 5678 --disabled-password --gecos "" appuser && chown -R appuser /app
USER appuser

# Provides defaults for an executing container; can be overridden with Docker CLI.
CMD ["gunicorn", "--bind", "0.0.0.0:5000", "wsgi:app"]

È possibile creare un Dockerfile a mano o crearlo automaticamente con VS Code e l'estensione Docker. Per altre informazioni, vedere Generazione di file Docker.

Il comando di compilazione Docker fa parte dell'interfaccia della riga di comando di Docker. Quando si usano IDE come VS Code o PyCharm, i comandi dell'interfaccia utente per l'uso delle immagini Docker chiamano automaticamente il comando di compilazione e automatizzano la specifica delle opzioni.

Uso di immagini e contenitori Docker python

VS Code e PyCharm

L'uso di un ambiente di sviluppo integrato (IDE) per lo sviluppo di contenitori Python non è necessario, ma può semplificare molte attività correlate ai contenitori. Ecco alcune delle operazioni che è possibile eseguire con VS Code e PyCharm.

  • Scaricare e compilare immagini Docker.

    • Creare immagini nell'ambiente di sviluppo.
    • Compilare immagini Docker in Azure senza Docker installato nell'ambiente di sviluppo. Per PyCharm, usare l'interfaccia della riga di comando di Azure per compilare immagini in Azure.
  • Creare ed eseguire contenitori Docker da un'immagine esistente, un'immagine estratta o direttamente da un Dockerfile.

  • Eseguire applicazioni multicontainer con Docker Compose.

  • Connessione e usare registri contenitori come Docker Hub, GitLab, JetBrains Space, Docker V2 e altri registri Docker self-hosted.

  • (solo VS Code) Aggiungere file Dockerfile e Docker compose personalizzati per il progetto Python.

Per configurare VS Code e PyCharm per eseguire contenitori Docker nell'ambiente di sviluppo, seguire questa procedura.

Se non è già stato fatto, installare Azure Tools per VS Code.

Istruzioni Schermata
Passaggio 1: usare MAIUSC + ALT + A per aprire l'estensione di Azure e verificare di essere connessi ad Azure.

È anche possibile selezionare l'icona di Azure sulla barra delle estensioni di VS Code.

Se non si è connessi, selezionare Accedi ad Azure e seguire le istruzioni.

Se si verificano problemi durante l'accesso alla sottoscrizione di Azure, è possibile che si trovi dietro un proxy. Per risolvere i problemi di connessione, vedere Connessione di rete in Visual Studio Code.
Screenshot showing how Azure Tools looks once signed in.Screenshot showing how Azure Tools looks if you aren't signed in.
Passaggio 2: usare CTRL + MAIUSC + X per aprire Estensioni, cercare l'estensione Docker e installare l'estensione.

È anche possibile selezionare l'icona Estensioni sulla barra delle estensioni di VS Code.
Screenshot showing how to add Docker extension to VS Code.
Passaggio 3: Selezionare l'icona Docker nella barra dell'estensione, espandere le immagini e fare clic con il pulsante destro del mouse su un'immagine eseguirla come contenitore. Screenshot showing how to use the Docker extension in VS Code to run a container from a Docker image.
Passaggio 4: Monitorare l'output dell'esecuzione di Docker nella finestra Del terminale . Screenshot showing an example of running a container in VS Code.

Interfaccia della riga di comando di Azure e interfaccia della riga di comando di Docker

È anche possibile usare immagini e contenitori Docker Python usando l'interfaccia della riga di comando di Azure e l'interfaccia della riga di comando di Docker. Sia VS Code che PyCharm hanno terminali in cui è possibile eseguire queste interfacce di riga.

Usare un'interfaccia della riga di comando per controllare in modo più corretto gli argomenti di compilazione ed esecuzione e per l'automazione. Ad esempio, il comando seguente illustra come usare l'interfaccia della riga di comando di Azure az acr build per specificare il nome dell'immagine Docker.

az acr build --registry <registry-name> \
  --resource-group <resource-group> \
  --target pythoncontainerwebapp:latest .

Come altro esempio, si consideri il comando seguente che illustra come usare il comando di esecuzione dell'interfaccia della riga di comando docker. L'esempio illustra come eseguire un contenitore Docker che comunica con un'istanza di MongoDB nell'ambiente di sviluppo, all'esterno del contenitore. I diversi valori per completare il comando sono più facili da automatizzare quando specificati in una riga di comando.

docker run --rm -it \
  --publish <port>:<port> --publish 27017:27017 \
  --add-host mongoservice:<your-server-IP-address> \
  --env CONNECTION_STRING=mongodb://mongoservice:27017 \
  --env DB_NAME=<database-name> \
  --env COLLECTION_NAME=<collection-name> \
  containermongo:latest  

Per altre informazioni su questo scenario, vedere Compilare e testare un'app Web Python in contenitori in locale.

Variabili di ambiente nei contenitori

I progetti Python spesso usano variabili di ambiente per passare i dati al codice. Ad esempio, è possibile specificare le informazioni di connessione al database in una variabile di ambiente in modo che possa essere facilmente modificata durante il test. In alternativa, quando si distribuisce il progetto nell'ambiente di produzione, è possibile modificare la connessione al database per fare riferimento a un'istanza del database di produzione.

I pacchetti come python-dotenv vengono spesso usati per leggere coppie chiave-valore da un file con estensione env e impostarle come variabili di ambiente. Un file con estensione env è utile quando viene eseguito in un ambiente virtuale, ma non è consigliabile quando si usano i contenitori. Non copiare il file con estensione env nell'immagine Docker, soprattutto se contiene informazioni riservate e il contenitore verrà reso pubblico. Usare il file con estensione dockerignore per escludere la copia dei file nell'immagine Docker. Per altre informazioni, vedere la sezione Ambienti virtuali e contenitori in questo articolo.

È possibile passare variabili di ambiente ai contenitori in diversi modi:

  1. Definito nel Dockerfile come istruzioni di ENV .
  2. Passato come --build-arg argomenti con il comando di compilazione Docker.
  3. Passato come --secret argomenti con il comando di compilazione Docker e il back-end BuildKit .
  4. Passato come --env argomento o --env-file con il comando Docker run .

Le prime due opzioni presentano lo stesso svantaggio indicato in precedenza con i file con estensione env , vale a dire che si stanno hardcoding delle informazioni potenzialmente sensibili in un'immagine Docker. È possibile esaminare un'immagine Docker e visualizzare le variabili di ambiente, ad esempio, con il comando docker image inspect.

La terza opzione con BuildKit consente di passare informazioni segrete da usare nel Dockerfile per la compilazione di immagini Docker in modo sicuro che non finiranno archiviate nell'immagine finale.

La quarta opzione di passaggio delle variabili di ambiente con il comando Docker run indica che l'immagine Docker non contiene le variabili. Tuttavia, le variabili sono ancora visibili esaminando l'istanza del contenitore, ad esempio con docker container inspect. Questa opzione può essere accettabile quando l'accesso all'istanza del contenitore è controllato o in scenari di test o sviluppo.

Di seguito è riportato un esempio di passaggio di variabili di ambiente usando il comando di esecuzione dell'interfaccia della riga di comando docker e l'argomento --env .

# PORT=8000 for Django and 5000 for Flask
export PORT=<port-number>

docker run --rm -it \
  --publish $PORT:$PORT \
  --env CONNECTION_STRING=<connection-info> \
  --env DB_NAME=<database-name> \
  <dockerimagename:tag>

Se si usa VS Code o PyCharm, le opzioni dell'interfaccia utente per l'uso di immagini e contenitori usano infine comandi dell'interfaccia della riga di comando docker come quello illustrato in precedenza.

Infine, la specifica delle variabili di ambiente durante la distribuzione di un contenitore in Azure è diversa dall'uso di variabili di ambiente nell'ambiente di sviluppo. Ad esempio:

  • Per App Web per contenitori, configurare le impostazioni dell'applicazione durante la configurazione di servizio app. Queste impostazioni sono disponibili per il codice dell'app come variabili di ambiente e sono accessibili tramite il modello os.environ standard. È possibile modificare i valori dopo la distribuzione iniziale quando necessario. Per altre informazioni, vedere Accedere alle impostazioni dell'app come variabili di ambiente.

  • Per le app contenitore di Azure, è possibile configurare le variabili di ambiente durante la configurazione iniziale dell'app contenitore. La modifica successiva delle variabili di ambiente crea una revisione del contenitore. Inoltre, App Azure Container consente di definire segreti a livello di applicazione e quindi farvi riferimento nelle variabili di ambiente. Per altre informazioni, vedere Gestire i segreti in App Azure Container.

Come altra opzione, è possibile usare Service Connessione or per connettere i servizi di calcolo di Azure ad altri servizi di backup. Questo servizio configura le impostazioni di rete e le informazioni di connessione (ad esempio, generando variabili di ambiente) tra i servizi di calcolo e i servizi di backup di destinazione nel piano di gestione.

Visualizzare i log dei contenitori

Visualizzare i log dell'istanza del contenitore per visualizzare l'output dei messaggi di diagnostica dal codice e risolvere i problemi nel codice del contenitore. Ecco diversi modi per visualizzare i log quando si esegue un contenitore nell'ambiente di sviluppo:

  • L'esecuzione di un contenitore con VS Code o PyCharm, come illustrato nella sezione VS Code e PyCharm, è possibile visualizzare i log nelle finestre del terminale aperte quando viene eseguita l'esecuzione di Docker.

  • Se si usa il comando di esecuzione dell'interfaccia della riga di comando di Docker con il flag -itinterattivo , l'output verrà visualizzato dopo il comando .

  • In Docker Desktop è anche possibile visualizzare i log per un contenitore in esecuzione.

Quando si distribuisce un contenitore in Azure, è anche possibile accedere ai log dei contenitori. Ecco diversi servizi di Azure e come accedere ai log dei contenitori in portale di Azure.

Servizio di Azure Come accedere ai log in portale di Azure
App Web per contenitori Passare alla risorsa Diagnostica e risoluzione dei problemi per visualizzare i log. La diagnostica è un'esperienza intelligente e interattiva che consente di risolvere i problemi dell'app senza alcuna configurazione necessaria. Per una visualizzazione in tempo reale dei log, passare al flusso del log di monitoraggio - . Per informazioni più dettagliate sulle query di log e sulla configurazione, vedere le altre risorse in Monitoraggio.
App contenitore di Azure Passare alla risorsa dell'ambiente Diagnosticare e risolvere i problemi relativi all'ambiente. Più spesso, è consigliabile visualizzare i log dei contenitori. Nella risorsa contenitore, in Gestione revisione applicazione - , selezionare la revisione e da qui è possibile visualizzare i log di sistema e console. Per query e configurazione di log più dettagliate, vedere le risorse in Monitoraggio.
Istanze di Azure Container Passare alla risorsa Contenitori e selezionare Log.

Per gli stessi servizi elencati in precedenza, ecco i comandi dell'interfaccia della riga di comando di Azure per accedere ai log.

Servizio di Azure Comando dell'interfaccia della riga di comando di Azure per accedere ai log
App Web per contenitori az webapp log
App contenitore di Azure az containerapps logs
Istanze di Azure Container az container logs

È disponibile anche il supporto per la visualizzazione dei log in VS Code. È necessario aver installato Strumenti di Azure per VS Code . Di seguito è riportato un esempio di visualizzazione di App Web per i log dei contenitori (servizio app) in VS Code.

Screenshot showing how to view logs in VS Code for Web Apps for Containers.

Passaggi successivi