Esercitazione: Distribuire un'app Django nel servizio Azure Kubernetes con il server flessibile di Database di Azure per PostgreSQL

SI APPLICA A: Database di Azure per PostgreSQL - Server flessibile

In questa guida di avvio rapido si distribuisce un'applicazione Django nel cluster del servizio Azure Kubernetes con il server flessibile di Database di Azure per PostgreSQL usando l'interfaccia della riga di comando di Azure.

Il servizio Azure Kubernetes è un servizio Kubernetes gestito che consente di distribuire e gestire rapidamente i cluster. Il server flessibile di Database di Azure per PostgreSQL è un servizio di database completamente gestito progettato per offrire un controllo più granulare e una maggiore flessibilità rispetto alle funzioni di gestione e alle impostazioni di configurazione del database.

Nota

Questa guida di avvio rapido presuppone una conoscenza di base dei concetti relativi a Kubernetes, Django e PostgreSQL.

Prerequisiti

Se non si ha una sottoscrizione di Azure, creare un account Azure gratuito prima di iniziare.

  • Avviare Azure Cloud Shell nella nuova finestra del browser. È anche possibile installare l'interfaccia della riga di comando di Azure nel computer locale. Se si usa un'installazione locale, accedere con l'interfaccia della riga di comando usando il comando az login. Per completare il processo di autenticazione, seguire la procedura visualizzata nel terminale.
  • Eseguire az version per trovare la versione e le librerie dipendenti installate. Per eseguire l'aggiornamento alla versione più recente, eseguire az upgrade. Questo articolo richiede l'ultima versione dell'interfaccia della riga di comando di Azure. Se si usa Azure Cloud Shell, la versione più recente è già installata.

Creare un gruppo di risorse

Un gruppo di risorse di Azure è un gruppo logico in cui le risorse di Azure vengono distribuite e gestite. Creare un gruppo di risorse denominato django-project usando il comando az-group-createnella località eastus.

az group create --name django-project --location eastus

Nota

La località del gruppo di risorse è quella in cui vengono archiviati i relativi metadati. È anche quella in cui viene eseguita la risorsa in Azure se non si specifica un'area diversa durante la creazione.

L'output di esempio seguente mostra il gruppo di risorse creato correttamente:

{
  "id": "/subscriptions/<guid>/resourceGroups/django-project",
  "location": "eastus",
  "managedBy": null,
  
  "name": "django-project",
  "properties": {
    "provisioningState": "Succeeded"
  },
  "tags": null
}

Creare un cluster del servizio Azure Container

Usare il comando az aks create per creare un cluster del servizio Azure Kubernetes. L'esempio seguente crea un cluster denominato djangoappcluster con un nodo. Questa operazione richiede alcuni minuti.

az aks create --resource-group django-project --name djangoappcluster --node-count 1 --generate-ssh-keys

Il comando viene completato dopo pochi minuti e vengono restituite informazioni in formato JSON sul cluster.

Nota

Quando si crea un cluster del servizio Azure Kubernetes, viene creato automaticamente un secondo gruppo di risorse per archiviare le risorse del servizio Azure Kubernetes. Vedere Perché vengono creati due gruppi di risorse con il servizio Azure Kubernetes?

Stabilire la connessione al cluster

Per gestire un cluster Kubernetes, usare kubectl, il client della riga di comando Kubernetes. Se si usa Azure Cloud Shell, kubectl è già installato.

Nota

Se si esegue l'interfaccia della riga di comando di Azure in locale, eseguire il comando az aks install-cli per installare kubectl.

Per configurare kubectl per la connessione al cluster Kubernetes, usare il comando az servizio Azure Kubernetes get-credentials. Questo comando scarica le credenziali e configura l'interfaccia della riga di comando di Kubernetes per usarli.

az aks get-credentials --resource-group django-project --name djangoappcluster

Per verificare la connessione al cluster, usare il comando kubectl get per restituire un elenco di nodi del cluster.

kubectl get nodes

L'esempio di output seguente mostra il nodo singolo creato nei passaggi precedenti. Assicurarsi che lo stato del nodo sia impostato su Pronto:

NAME                       STATUS   ROLES   AGE     VERSION
aks-nodepool1-31718369-0   Ready    agent   6m44s   v1.12.8

Creare un'istanza del server flessibile di Database di Azure per PostgreSQL

Creare un'istanza del server flessibile di Database di Azure per PostgreSQL con il comando az postgreSQL flexible-server create. Il comando seguente crea un server usando le impostazioni predefinite del servizio e i valori del contesto locale dell'interfaccia della riga di comando di Azure:

az postgres flexible-server create --public-access all

Il server creato ha gli attributi seguenti:

  • La prima volta che si effettua il provisioning del server, viene creato un nuovo database vuoto, postgres. In questa guida di avvio rapido viene usato questo database.
  • Nome del server, nome utente amministratore, password amministratore, nome del gruppo di risorse (se non è già specificato nel contesto locale) generati automaticamente e nella stessa località del gruppo di risorse.
  • L'uso dell'argomento accesso pubblico consente di creare un server con accesso pubblico a qualsiasi client con nome utente e password corretti.
  • Poiché il comando usa il contesto locale, crea il server nel gruppo di risorse django-project e nell'area eastus.

Creare l'immagine Docker di Django

Creare una nuova applicazione Django o usare il progetto Django esistente. Verificare che il codice si trovi in questa struttura di cartelle.

└───my-djangoapp
    └───views.py
    └───models.py
    └───forms.py
    ├───templates
          . . . . . . .
    ├───static
         . . . . . . .
└───my-django-project
    └───settings.py
    └───urls.py
    └───wsgi.py
        . . . . . . .
    └─── Dockerfile
    └─── requirements.txt
    └─── manage.py

Aggiornare ALLOWED_HOSTS in settings.py per assicurarsi che l'applicazione Django usi l'indirizzo IP esterno che viene assegnato all'app kubernetes.

ALLOWED_HOSTS = ['*']

Aggiornare la sezione DATABASES={ } del file settings.py. Il frammento di codice seguente legge l'host di database, il nome utente e la password dal file manifesto di Kubernetes.

DATABASES={
   'default':{
      'ENGINE':'django.db.backends.postgresql_psycopg2',
      'NAME':os.getenv('DATABASE_NAME'),
      'USER':os.getenv('DATABASE_USER'),
      'PASSWORD':os.getenv('DATABASE_PASSWORD'),
      'HOST':os.getenv('DATABASE_HOST'),
      'PORT':'5432',
      'OPTIONS': {'sslmode': 'require'}
   }
}

Generare un file requirements.txt

Creare un file requirements.txt per elencare le dipendenze per l'applicazione Django. Di seguito è riportato un esempio di un file requirements.txt. È possibile usare pip freeze > requirements.txt per generare un file requirements.txt per l'applicazione esistente.

Django==2.2.17
postgres==3.0.0
psycopg2-binary==2.8.6
psycopg2-pool==1.1
pytz==2020.4

Creare un Dockerfile

Creare un nuovo file denominato Dockerfile e copiare il frammento di codice seguente. Questo Dockerfile viene usato per configurare Python 3.8 e installare tutti i requisiti elencati nel file requirements.txt.

# Use the official Python image from the Docker Hub

FROM python:3.8.2

# Make a new directory to put our code in.

RUN mkdir /code

# Change the working directory.

WORKDIR /code

# Copy to code folder

COPY . /code/

# Install the requirements.

RUN pip install -r requirements.txt

# Run the application:

CMD python manage.py runserver 0.0.0.0:8000

Creare l'immagine

Assicurarsi di trovarsi nella directory my-django-app in un terminale usando il comando cd. Eseguire il comando seguente per creare l'immagine di BBS:

docker build --tag myblog:latest .

Distribuire l'immagine nell'hub Docker o in Registro Azure Container.

Importante

Se si usa Registro Azure Container, eseguire il comando az aks update per collegare l'account del registro al cluster del servizio Azure Kubernetes.

az aks update --name djangoappcluster --resource-group django-project --attach-acr <your-acr-name>

Creare il file manifesto di Kubernetes

Un file manifesto di Kubernetes definisce uno stato desiderato per il cluster, ad esempio le immagini del contenitore da eseguire. Creare un file manifesto denominato djangoapp.yaml e copiarlo nella definizione YAML seguente.

Importante

Aggiornare la sezione env seguente con SERVERNAME, YOUR-DATABASE-USERNAME, YOUR-DATABASE-PASSWORD dell'istanza del server flessibile di Database di Azure per PostgreSQL.

apiVersion: apps/v1
kind: Deployment
metadata:
  name: django-app
spec:
  replicas: 1
  selector:
    matchLabels:
      app: django-app
  template:
    metadata:
      labels:
        app: django-app
    spec:
      containers:
      - name: django-app
        image: [DOCKER-HUB-USER-OR-ACR-ACCOUNT]/[YOUR-IMAGE-NAME]:[TAG]
        ports:
        - containerPort: 8000
        env:
        - name: DATABASE_HOST
          value: "SERVERNAME.postgres.database.azure.com"
        - name: DATABASE_USER
          value: "YOUR-DATABASE-USERNAME"
        - name: DATABASE_PASSWORD
          value: "YOUR-DATABASE-PASSWORD"
        - name: DATABASE_NAME
          value: "postgres"
      affinity:
        podAntiAffinity:
          requiredDuringSchedulingIgnoredDuringExecution:
            - labelSelector:
                matchExpressions:
                  - key: "app"
                    operator: In
                    values:
                    - django-app
              topologyKey: "kubernetes.io/hostname"
---
apiVersion: v1
kind: Service
metadata:
  name: python-svc
spec:
  type: LoadBalancer
  ports:
    - protocol: TCP
      port: 80
      targetPort: 8000
  selector:
    app: django-app

Distribuire Django nel cluster del servizio Azure Kubernetes

Distribuire l'applicazione usando il comando kubectl apply e specificare il nome del manifesto YAML:

kubectl apply -f djangoapp.yaml

L'output di esempio seguente mostra le distribuzioni e i servizi creati correttamente:

deployment "django-app" created
service "python-svc" created

Un servizio django-app consente di descrivere i dettagli della distribuzione, ad esempio le immagini da usare per l'app, il numero di pod e la configurazione dei pod. Viene creato un servizio python-svc per esporre l'applicazione tramite un indirizzo IP esterno.

Testare l'applicazione

Quando l'applicazione viene eseguita, un servizio Kubernetes espone il front-end dell'applicazione a Internet. Questo processo può richiedere alcuni minuti.

Per monitorare lo stato, usare il comando kubectl get service con l'argomento --watch.

kubectl get service python-svc --watch

Inizialmente il valore di EXTERNAL-IP per il servizio django-app è visualizzato come pending.

NAME               TYPE           CLUSTER-IP   EXTERNAL-IP   PORT(S)        AGE
django-app   LoadBalancer   10.0.37.27   <pending>     80:30572/TCP   6s

Quando EXTERNAL-IP passa da pending a un effettivo indirizzo IP pubblico, usare CTRL-C per arrestare il processo di controllo kubectl. L'output di esempio seguente mostra un indirizzo IP pubblico valido assegnato al servizio:

django-app  LoadBalancer   10.0.37.27   52.179.23.131   80:30572/TCP   2m

Ora aprire un Web browser all'indirizzo IP esterno del servizio (http://<service-external-ip-address>) per visualizzare l'applicazione Django.

Nota

Eseguire le migrazioni del database

Per qualsiasi applicazione Django, è necessario eseguire la migrazione del database o raccogliere file statici. È possibile eseguire questi comandi della shell Django usando $ kubectl exec <pod-name> -- [COMMAND]. Prima di eseguire il comando è necessario trovare il nome del pod usando kubectl get pods.

$ kubectl get pods

Viene visualizzato un output simile al seguente:

NAME                             READY   STATUS          RESTARTS   AGE
django-app-5d9cd6cd8-l6x4b     1/1     Running              0       2m

Una volta trovato il nome del pod, è possibile eseguire le migrazioni di database Django con il comando $ kubectl exec <pod-name> -- [COMMAND]. Si noti che /code/ è la directory di lavoro per il progetto definito nel Dockerfile precedente.

$ kubectl exec django-app-5d9cd6cd8-l6x4b -- python /code/manage.py migrate

L'output sarà simile al seguente:

Operations to perform:
  Apply all migrations: admin, auth, contenttypes, sessions
Running migrations:
  Applying contenttypes.0001_initial... OK
  Applying auth.0001_initial... OK
  Applying admin.0001_initial... OK
  Applying admin.0002_logentry_remove_auto_add... OK
  Applying admin.0003_logentry_add_action_flag_choices... OK
  . . . . . . 

Se si verificano problemi, eseguire kubectl logs <pod-name> per vedere quale eccezione viene generata dall'applicazione. Se l'applicazione funziona correttamente, verrà visualizzato un output simile al seguente quando si esegue kubectl logs.

Watching for file changes with StatReloader
Performing system checks...

System check identified no issues (0 silenced).

You have 17 unapplied migration(s). Your project may not work properly until you apply the migrations for app(s): admin, auth, contenttypes, sessions.
Run 'python manage.py migrate' to apply them.
December 08, 2020 - 23:24:14
Django version 2.2.17, using settings 'django_postgres_app.settings'
Starting development server at http://0.0.0.0:8000/
Quit the server with CONTROL-C.

Pulire le risorse

Per evitare addebiti per Azure, è necessario eliminare le risorse non necessarie. Quando il cluster non è più necessario, usare il comando az group delete per rimuovere il gruppo di risorse, il servizio contenitore e tutte le risorse correlate.

az group delete --name django-project --yes --no-wait

Nota

Quando si elimina il cluster, l'entità servizio Microsoft Entra usata dal cluster del servizio Azure Kubernetes non viene rimossa. Per istruzioni su come rimuovere l'entità servizio, vedere le considerazioni sull'entità servizio servizio Azure Kubernetes e la sua eliminazione. Se è stata usata un'identità gestita, l'identità viene gestita dalla piattaforma e non richiede la rimozione.

Passaggi successivi