Esegui il deployment dell'elaborazione delle immagini utilizzando microservizi e messaggistica asincrona

Last reviewed 2023-07-17 UTC

Questo documento descrive come implementare l'architettura di riferimento descritta in Integrare microservizi con Pub/Sub e GKE. L'architettura è progettata per gestire processi di lunga durata utilizzando container e messaggi asincroni.

Il documento utilizza un'applicazione di condivisione di foto di esempio che genera miniature delle foto. Puoi eseguire il deployment dell'applicazione utilizzando Google Kubernetes Engine (GKE) e utilizzare Pub/Sub per richiamare i processi a lunga esecuzione in modo asincrono. Puoi inoltre utilizzare le notifiche Pub/Sub per Cloud Storage per aggiungere job collaterali senza modificare il codice dell'applicazione.

L'applicazione è containerizzata da Cloud Build e archiviata in Artifact Registry. Utilizza Cloud Vision per rilevare immagini inappropriate.

Architettura

Il seguente diagramma illustra il design dell'applicazione per album di foto di esempio che implementa l'architettura di riferimento.

Architettura dell'applicazione per l'album fotografico.

Figura 1. architettura per l'elaborazione delle immagini basata su container e messaggistica asincrona.

Il diagramma precedente illustra come viene generata la miniatura:

  1. Un client carica un'immagine nell'applicazione.
  2. L'applicazione archivia l'immagine in Cloud Storage.
  3. Viene generata una richiesta per la miniatura.
  4. Il generatore di miniature genera la miniatura.
  5. La risposta corretta viene inviata all'applicazione per l'album fotografico.
  6. La risposta corretta viene inviata al client e puoi trovare la miniatura in Cloud Storage.

Il seguente diagramma mostra come l'applicazione implementa la generazione delle miniature come servizio separato in modo asincrono.

Architettura del processo di estrazione delle miniature.

Figura 2. Architettura del processo di estrazione delle miniature.

Puoi utilizzare Pub/Sub per inviare richieste di servizio al servizio di generazione miniature. Questa nuova architettura rende asincrona la chiamata di servizio, in modo che venga creata una miniatura in background dopo che l'applicazione invia la risposta a un client. Inoltre, il servizio di generazione delle miniature può scalare in modo da eseguire più job in parallelo.

Obiettivi

  • Esegui il deployment di un'applicazione di album di foto di esempio su GKE.
  • Effettua chiamate di servizio asincrone dall'applicazione.
  • Utilizza le notifiche Pub/Sub per Cloud Storage per attivare l'applicazione quando viene caricato un nuovo file nel bucket Cloud Storage.
  • Utilizza Pub/Sub per eseguire più attività senza modificare l'applicazione.

Costi

In questo documento, utilizzi i seguenti componenti fatturabili di Google Cloud:

Per generare una stima dei costi in base all'utilizzo previsto, utilizza il Calcolatore prezzi. I nuovi utenti di Google Cloud potrebbero essere idonei per una prova gratuita.

Una volta completata la creazione dell'applicazione di esempio, puoi evitare di continuare la fatturazione eliminando le risorse che hai creato. Per ulteriori informazioni, consulta Pulizia.

Prima di iniziare

  1. Accedi al tuo account Google Cloud. Se non conosci Google Cloud, crea un account per valutare le prestazioni dei nostri prodotti in scenari reali. I nuovi clienti ricevono anche 300 $di crediti gratuiti per l'esecuzione, il test e il deployment dei carichi di lavoro.
  2. In the Google Cloud console, on the project selector page, select or create a Google Cloud project.

    Go to project selector

  3. Assicurati che la fatturazione sia attivata per il tuo progetto Google Cloud.

  4. Abilita le API GKE, Cloud SQL, Cloud Build, Artifact Registry, and Cloud Vision.

    Abilita le API

  5. In the Google Cloud console, on the project selector page, select or create a Google Cloud project.

    Go to project selector

  6. Assicurati che la fatturazione sia attivata per il tuo progetto Google Cloud.

  7. Abilita le API GKE, Cloud SQL, Cloud Build, Artifact Registry, and Cloud Vision.

    Abilita le API

  8. Nella console Google Cloud, attiva Cloud Shell.

    Attiva Cloud Shell

    Nella parte inferiore della console Google Cloud viene avviata una sessione di Cloud Shell che mostra un prompt della riga di comando. Cloud Shell è un ambiente shell con Google Cloud CLI già installato e con valori già impostati per il progetto attuale. L'inizializzazione della sessione può richiedere alcuni secondi.

Configura l'ambiente

In questa sezione assegnerai le impostazioni predefinite per i valori utilizzati in tutto il documento. Se chiudi la sessione di Cloud Shell, perdi queste impostazioni di ambiente.

  1. In Cloud Shell, imposta il progetto Google Cloud predefinito:

    gcloud config set project PROJECT_ID
    

    Sostituisci PROJECT_ID con l'ID del tuo progetto Google Cloud.

  2. Imposta la regione predefinita di Compute Engine:

    gcloud config set compute/region REGION
    export REGION=REGION
    

    Sostituisci REGION con una regione nelle vicinanze. Per ulteriori informazioni, consulta Regioni e zone.

  3. Imposta la zona di Compute Engine predefinita:

    gcloud config set compute/zone ZONE
    export ZONE=ZONE
    

    Sostituisci ZONE con una zona vicina a te.

  4. Scarica i file dell'applicazione di esempio e imposta la tua directory attuale:

    git clone https://github.com/GoogleCloudPlatform/gke-photoalbum-example
    cd gke-photoalbum-example
    

Crea un bucket Cloud Storage e carica l'immagine in miniatura predefinita

  1. In Cloud Shell, crea un bucket Cloud Storage per archiviare le immagini e le miniature originali:

    export PROJECT_ID=$(gcloud config get-value project)
    gsutil mb -c regional -l ${REGION} gs://${PROJECT_ID}-photostore
    
  2. Carica il file della miniatura predefinita:

    gsutil cp ./application/photoalbum/images/default.png \
        gs://${PROJECT_ID}-photostore/thumbnails/default.png
    
    • Le immagini caricate sono archiviate nel seguente formato: gs://PROJECT_ID-photostore/FILENAME, dove FILENAME rappresenta il nome del file immagine che viene caricato.
    • Le miniature generate vengono memorizzate nel seguente formato: gs://PROJECT_ID-photostore/thumbnails/FILENAME.
    • L'immagine originale e la miniatura corrispondente hanno lo stesso valore FILENAME, ma la miniatura è archiviata nel bucket thumbnails.
    • Durante la creazione della miniatura, nell'applicazione dell'album fotografico viene visualizzata la seguente immagine in miniatura segnaposto default.png.

      L'immagine in miniatura segnaposto predefinita.

  3. Per rendere pubblico il file della miniatura:

    gsutil acl ch -u AllUsers:R \
        gs://${PROJECT_ID}-photostore/thumbnails/default.png
    

crea un'istanza Cloud SQL e un database MySQL

  1. In Cloud Shell, crea l'istanza Cloud SQL:

    gcloud sql instances create photoalbum-db --region=${REGION} \
        --database-version=MYSQL_8_0
    
  2. Recupera il nome della connessione:

    gcloud sql instances describe photoalbum-db \
        --format="value(connectionName)"
    

    Prendi nota del nome perché lo utilizzerai in seguito.

  3. Imposta la password per l'utente MySQL root@%:

    gcloud sql users set-password root --host=% --instance=photoalbum-db \
        --password=PASSWORD
    

    Sostituisci PASSWORD con una password sicura per l'utente root@%.

  4. Connettiti all'istanza Cloud SQL:

    gcloud sql connect photoalbum-db --user=root --quiet
    

    Quando ti viene richiesto, inserisci la password impostata nel passaggio precedente.

  5. Crea un database denominato photo_db, in cui l'utente è appuser e la password è pas4appuser:

    create database photo_db;
    create user 'appuser'@'%' identified by 'pas4appuser';
    grant all on photo_db.* to 'appuser'@'%' with grant option;
    flush privileges;
    
  6. Conferma il risultato ed esci da MySQL:

    show databases;
    select user from mysql.user;
    exit
    

    Nell'output, conferma che il database photo_db e l'utente appuser siano stati creati:

    mysql> show databases;
    +--------------------+
    | Database           |
    +--------------------+
    | information_schema |
    | mysql              |
    | performance_schema |
    | photo_db           |
    | sys                |
    +--------------------+
    5 rows in set (0.16 sec)
    
    mysql> \t
    Outfile disabled.
    mysql> select user from mysql.user;
    +-------------------+
    | user              |
    +-------------------+
    | appuser           |
    | cloudsqlreplica   |
    | cloudsqlsuperuser |
    | root              |
    | cloudsqlexport    |
    | cloudsqlimport    |
    | cloudsqloneshot   |
    | root              |
    | cloudsqlexport    |
    | cloudsqlimport    |
    | cloudsqloneshot   |
    | root              |
    | cloudsqlapplier   |
    | cloudsqlimport    |
    | mysql.infoschema  |
    | mysql.session     |
    | mysql.sys         |
    | root              |
    +-------------------+
    18 rows in set (0.16 sec)
    
    mysql> exit
    Bye
    

Crea un argomento Pub/Sub e una sottoscrizione

  1. In Cloud Shell, crea un argomento Pub/Sub denominato thumbnail-service:

    gcloud pubsub topics create thumbnail-service
    

    L'applicazione per l'album fotografico invia richieste al servizio di generazione delle miniature pubblicando un messaggio nell'argomento thumbnail-service.

  2. Crea una sottoscrizione Pub/Sub denominata thumbnail-workers:

    gcloud pubsub subscriptions create --topic thumbnail-service thumbnail-workers
    

    Il servizio di generazione delle miniature riceve richieste dall'abbonamento a thumbnail-workers.

crea un cluster GKE

  1. In Cloud Shell, crea un cluster GKE con l'autorizzazione per chiamare le API:

    gcloud container clusters create "photoalbum-cluster" \
        --scopes "https://www.googleapis.com/auth/cloud-platform" \
        --num-nodes "5"
    
  2. Configura le credenziali di accesso in modo da poter gestire il cluster utilizzando il comando kubectl nei passaggi successivi:

    gcloud container clusters get-credentials photoalbum-cluster
    
  3. Visualizza l'elenco dei nodi:

    kubectl get nodes
    

    Nell'output, conferma che ci siano cinque nodi il cui valore STATUS è Ready:

    NAME                                                STATUS   ROLES    AGE     VERSION
    gke-photoalbum-cluster-default-pool-d637570a-2pfh   Ready    <none>   2m55s   v1.24.10-gke.2300
    gke-photoalbum-cluster-default-pool-d637570a-3rm4   Ready    <none>   2m55s   v1.24.10-gke.2300
    gke-photoalbum-cluster-default-pool-d637570a-f7l4   Ready    <none>   2m55s   v1.24.10-gke.2300
    gke-photoalbum-cluster-default-pool-d637570a-qb2z   Ready    <none>   2m53s   v1.24.10-gke.2300
    gke-photoalbum-cluster-default-pool-d637570a-rvnp   Ready    <none>   2m54s   v1.24.10-gke.2300
    

Crea il repository Artifact Registry

  • In Cloud Shell, crea un repository per archiviare le immagini container:

    gcloud artifacts repositories create photoalbum-repo \
        --repository-format=docker \
        --location=us-central1 \
        --description="Docker repository"
    

Crea immagini per l'applicazione

  1. In un editor di testo, apri il file application/photoalbum/src/auth_decorator.py e aggiorna nome utente e password:

    USERNAME = 'username'
    PASSWORD = 'passw0rd'
    
  2. In Cloud Shell, crea un'immagine per l'applicazione dell'album di foto utilizzando il servizio Cloud Build:

    gcloud builds submit ./application/photoalbum -t \
        us-central1-docker.pkg.dev/${PROJECT_ID}/photoalbum-repo/photoalbum-app
    
  3. Crea un'immagine per il servizio di generazione di miniature thumbnail-worker utilizzando il servizio Cloud Build:

    gcloud builds submit ./application/thumbnail -t \
        us-central1-docker.pkg.dev/${PROJECT_ID}/photoalbum-repo/thumbnail-worker
    

Implementazione dell'applicazione di album di foto

  1. In Cloud Shell, aggiorna i manifest di Kubernetes Deployment per l'album di foto e il generatore di miniature con i valori del tuo ambiente:

    connection_name=$(gcloud sql instances describe photoalbum-db \
        --format "value(connectionName)")
    
    digest_photoalbum=$(gcloud container images describe \
        us-central1-docker.pkg.dev/${PROJECT_ID}/photoalbum-repo/photoalbum-app:latest --format \
        "value(image_summary.digest)")
    
    sed -i.bak -e "s/\[PROJECT_ID\]/${PROJECT_ID}/" \
        -e "s/\[CONNECTION_NAME\]/${connection_name}/" \
        -e "s/\[DIGEST\]/${digest_photoalbum}/" \
        config/photoalbum-deployment.yaml
    
    digest_thumbnail=$(gcloud container images describe \
        us-central1-docker.pkg.dev/${PROJECT_ID}/photoalbum-repo/thumbnail-worker:latest --format \
        "value(image_summary.digest)")
    
    sed -i.bak -e "s/\[PROJECT_ID\]/${PROJECT_ID}/" \
        -e "s/\[CONNECTION_NAME\]/${connection_name}/" \
        -e "s/\[DIGEST\]/${digest_thumbnail}/" \
            config/thumbnail-deployment.yaml
    
  2. Crea risorse di deployment per avviare l'applicazione per gli album fotografici e il servizio di generazione di miniature:

    kubectl create -f config/photoalbum-deployment.yaml
    kubectl create -f config/thumbnail-deployment.yaml
    
  3. Crea una risorsa di servizio per assegnare un indirizzo IP esterno all'applicazione:

    kubectl create -f config/photoalbum-service.yaml
    
  4. Controlla i risultati per i pod:

    kubectl get pods
    

    Nell'output, verifica che ci siano tre pod per ogni pod photoalbum-app e thumbail-worker e che il loro valore STATUS sia Running:

    NAME                                READY     STATUS    RESTARTS   AGE
    photoalbum-app-555f7cbdb7-cp8nw     2/2       Running   0          2m
    photoalbum-app-555f7cbdb7-ftlc6     2/2       Running   0          2m
    photoalbum-app-555f7cbdb7-xsr4b     2/2       Running   0          2m
    thumbnail-worker-86bd95cd68-728k5   2/2       Running   0          2m
    thumbnail-worker-86bd95cd68-hqxqr   2/2       Running   0          2m
    thumbnail-worker-86bd95cd68-xnxhc   2/2       Running   0          2m
    

    I pod thumbnail-worker sottoscrivono le richieste di generazione delle miniature della sottoscrizione thumbnail-workers. Per ulteriori informazioni, scopri come viene utilizzata la funzione callback nel codice sorgente.

  5. Controlla i risultati per i servizi:

    kubectl get services
    

    Nell'output, conferma che sia presente un indirizzo IP esterno nella colonna EXTERNAL-IP per il servizio photoalbum-service. Potrebbero essere necessari alcuni minuti prima che tutti i servizi siano in esecuzione.

    NAME                 TYPE           CLUSTER-IP      EXTERNAL-IP       PORT(S)        AGE
    kubernetes           ClusterIP      10.23.240.1     <none>            443/TCP        20m
    photoalbum-service   LoadBalancer   10.23.253.241   146.148.111.115   80:32657/TCP   2m
    

    Prendi nota dell'indirizzo IP esterno, perché viene utilizzato in seguito. In questo esempio, è 146.148.111.115.

Testare l'applicazione per album fotografici

  1. Per accedere all'applicazione di cui è stato eseguito il deployment in un browser web, vai al seguente URL e inserisci il nome utente e la password configurati in precedenza:

    http://EXTERNAL_IP
    

    Sostituisci EXTERNAL_IP con l'indirizzo IP che hai copiato nel passaggio precedente.

  2. Per caricare un file immagine, fai clic su Carica.

    La miniatura del segnaposto visualizzata mentre attendi che il servizio generi una miniatura univoca.

    Sullo schermo viene visualizzato il segnaposto della miniatura.

    In background, il servizio di generazione miniature crea una miniatura dell'immagine caricata. Per visualizzare la miniatura generata, fai clic su Aggiorna. L'API Cloud Vision aggiunge le etichette delle immagini rilevate.

    La miniatura con le etichette delle immagini associate.

    Per visualizzare l'immagine originale, fai clic sulla miniatura.

Aggiungere una funzionalità di rilevamento di immagini inappropriate

L'immagine seguente illustra come utilizzare le notifiche Pub/Sub per Cloud Storage per attivare un servizio che rileva contenuti inappropriati. Questa funzionalità sfoca l'immagine quando un nuovo file con contenuti inappropriati viene archiviato nel bucket Cloud Storage.

Architettura della funzionalità dei contenuti inappropriati.

Nell'immagine precedente, il servizio utilizza la funzionalità Rilevamento di Safe Search dell'API Vision per rilevare contenuti inappropriati all'interno di un'immagine.

L'applicazione foto attiva il generatore di miniature e il controllo immagini in modo asincrono. Di conseguenza, non vi è alcuna garanzia che vengano eseguite in un ordine specifico. Se la generazione della miniatura avviene prima che l'immagine sia sfocata, per un po' potresti vedere una miniatura inappropriata. Tuttavia, lo strumento di controllo delle immagini alla fine sfoca sia l'immagine inappropriata che quella non appropriata.

Crea un argomento, una sottoscrizione e una notifica Pub/Sub

  1. In Cloud Shell, crea un argomento Pub/Sub denominato safeimage-service:

    gcloud pubsub topics create safeimage-service
    
  2. Crea una sottoscrizione Pub/Sub denominata safeimage-workers:

    gcloud pubsub subscriptions create --topic safeimage-service \
        safeimage-workers
    
  3. Configura una notifica Pub/Sub in modo che venga inviato un messaggio all'argomento safeimage-service quando viene caricato un nuovo file nel bucket Cloud Storage:

    gsutil notification create -t safeimage-service -f json \
        gs://${PROJECT_ID}-photostore
    

Crea ed esegui il deployment dell'immagine worker

  1. In Cloud Shell, crea un'immagine container per l'abbonamento safeimage-workers utilizzando Cloud Build:

    gcloud builds submit ./application/safeimage \
        -t us-central1-docker.pkg.dev/${PROJECT_ID}/photoalbum-repo/safeimage-worker
    
  2. Aggiorna i manifest del deployment di Kubernetes per il servizio immagine sicura con il tuo ID progetto Google Cloud, il nome della connessione Cloud SQL e i digest delle immagini container:

    digest_safeimage=$(gcloud container images describe \
        us-central1-docker.pkg.dev/${PROJECT_ID}/photoalbum-repo/safeimage-worker:latest --format \
        "value(image_summary.digest)")
    sed -i.bak -e "s/\[PROJECT_ID\]/${PROJECT_ID}/" \
        -e "s/\[CONNECTION_NAME\]/${connection_name}/" \
        -e "s/\[DIGEST\]/${digest_safeimage}/" \
        config/safeimage-deployment.yaml
    

Crea una risorsa di deployment

  1. Crea una risorsa di deployment denominata safeimage-deployment per eseguire il deployment dell'argomento safeimage-service:

    kubectl create -f config/safeimage-deployment.yaml
    
  2. Controlla i risultati:

    kubectl get pods
    

    Nell'output, conferma che ci siano tre pod safeimage-worker il cui valore STATUS sia Running.

    NAME                                READY     STATUS    RESTARTS   AGE
    photoalbum-app-555f7cbdb7-cp8nw     2/2       Running   0          30m
    photoalbum-app-555f7cbdb7-ftlc6     2/2       Running   0          30m
    photoalbum-app-555f7cbdb7-xsr4b     2/2       Running   8          30m
    safeimage-worker-7dc8c84f54-6sqzs   1/1       Running   0          2m
    safeimage-worker-7dc8c84f54-9bskw   1/1       Running   0          2m
    safeimage-worker-7dc8c84f54-b7gtp   1/1       Running   0          2m
    thumbnail-worker-86bd95cd68-9wrpv   2/2       Running   0          30m
    thumbnail-worker-86bd95cd68-kbhsn   2/2       Running   2          30m
    thumbnail-worker-86bd95cd68-n4rj7   2/2       Running   0          30m
    

    I pod safeimage-worker sottoscrivono le richieste di rilevamento di immagini inappropriate dall'abbonamento safeimage-workers. Per ulteriori informazioni, scopri come viene utilizzata la funzione callback nel codice sorgente.

Testare la funzionalità di rilevamento di immagini inappropriate

In questa sezione, caricherai un'immagine di prova per verificare che la funzionalità Rilevamento di SafeSearch sfoca un'immagine inappropriata. L'immagine di prova è quella di una ragazza travestita da zombie (con licenza CC0 concessa da Pixaby).

  1. Scarica l'immagine di test.
  2. Per caricare l'immagine, vai su http://EXTERNAL_IP e fai clic su Carica.
  3. Fai clic su Aggiorna. Nell'applicazione viene visualizzata una miniatura sfocata.

    Una miniatura sfocata.

    Per vedere che anche l'immagine caricata è sfocata, fai clic sulla miniatura.

Esegui la pulizia

Se non vuoi conservare le risorse Google Cloud che hai creato per l'applicazione di esempio, puoi rimuoverle in modo da non ricevere addebiti in futuro. Puoi eliminare completamente il progetto oppure eliminare le risorse del cluster e poi eliminare il cluster.

Elimina il progetto

  1. Nella console Google Cloud, vai alla pagina Gestisci risorse.

    Vai a Gestisci risorse

  2. Nell'elenco dei progetti, seleziona il progetto che vuoi eliminare, quindi fai clic su Elimina.
  3. Nella finestra di dialogo, digita l'ID del progetto e fai clic su Chiudi per eliminare il progetto.

Elimina le singole risorse

Invece di eliminare il progetto, puoi eliminare le singole risorse che hai creato.

  1. Elimina le risorse da GKE:

    kubectl delete -f config/safeimage-deployment.yaml
    kubectl delete -f config/photoalbum-service.yaml
    kubectl delete -f config/thumbnail-deployment.yaml
    kubectl delete -f config/photoalbum-deployment.yaml
    
  2. Elimina il cluster da GKE:

    gcloud container clusters delete photoalbum-cluster --quiet
    
  3. Elimina il repository da Artifact Registry:

    gcloud artifacts repositories delete photoalbum-repo --location us-central1 --quiet
    
  4. Elimina sottoscrizioni e argomenti da Pub/Sub:

    gcloud pubsub subscriptions delete safeimage-workers
    gcloud pubsub topics delete safeimage-service
    gcloud pubsub subscriptions delete thumbnail-workers
    gcloud pubsub topics delete thumbnail-service
    
  5. Elimina l'istanza Cloud SQL:

    gcloud sql instances delete photoalbum-db --quiet
    
  6. Elimina il bucket Cloud Storage:

    gsutil rm -r gs://${PROJECT_ID}-photostore
    gsutil rm -r gs://${PROJECT_ID}_cloudbuild
    
  7. Elimina i file:

    cd ..
    rm -rf gke-photoalbum-example
    

Passaggi successivi

  • Leggi ulteriori informazioni su DevOps e scopri di più sulle funzionalità di Architettura correlate a questa architettura di riferimento.
  • Esegui il controllo rapido di DevOps per comprendere la tua posizione rispetto al resto del settore.
  • Per ulteriori architetture di riferimento, diagrammi e best practice, esplora il Cloud Architecture Center.