Gestisci i modelli Spark ML utilizzando Vertex AI

Last reviewed 2023-07-11 UTC

I data scientist e i machine learning (ML) engineer richiedono spesso un'architettura di gestione che sia abbastanza veloce da soddisfare le esigenze di generazione di previsioni online (o in tempo reale) dai loro modelli di ML. Vertex AI è in grado di soddisfare questa esigenza.

Con Vertex AI, puoi gestire modelli da vari framework ML. Per framework come TensorFlow, PyTorch, XGBoost e scikit-learn, Vertex AI fornisce container predefiniti in cui eseguire questi modelli ML. Se non stai già utilizzando nessuno di questi framework ML, dovrai creare il tuo container personalizzato da utilizzare con Vertex AI.

Questo documento è rivolto agli utenti che devono creare un container personalizzato per gestire i loro modelli Spark ML. Questo documento include una descrizione dell'architettura di pubblicazione necessaria per i container personalizzati e un'implementazione di riferimento che dimostra questa architettura per un modello MLib Spark.

Per ottenere il massimo dalla parte relativa all'implementazione di riferimento di questo documento, dovresti avere familiarità con l'esportazione dei modelli MLlib di Spark in formato MLeap, sapere come utilizzare Vertex AI per la pubblicazione delle previsioni e avere esperienza nell'utilizzo delle immagini container.

Architettura

Sebbene i container predefiniti siano disponibili per alcuni framework ML, gli utenti di altri framework ML, come Spark, devono creare container personalizzati in cui Vertex AI può eseguire previsioni. Il seguente diagramma illustra l'architettura di gestione necessaria per gestire i modelli MLib Spark e altri modelli che richiedono un container personalizzato:

L'architettura di gestione per il modello utilizzato nel documento.

Questa architettura include i seguenti componenti:

  • Cloud Storage: fornisce spazio di archiviazione per gli artefatti del modello necessari per eseguire il modello. Per il modello Spark ML utilizzato nell'implementazione del riferimento di accompagnamento, gli artefatti del modello sono costituiti da un pacchetto MLeap e da uno schema del modello.
  • Cloud Build: utilizza l'immagine del builder per creare un'immagine container personalizzata chiamata immagine container di pubblicazione. Il processo di compilazione compila e pacchettizza il codice di pubblicazione del modello, crea l'immagine container di gestione ed esegue il push dell'immagine container di gestione ad Artifact Registry.
  • Artifact Registry: contiene i seguenti oggetti:
    • L'immagine container del builder scala-sbt utilizzata da Cloud Build per creare l'immagine container di pubblicazione.
    • L'immagine container di gestione creata da Cloud Build.
  • Vertex AI: contiene il modello ML che è stato caricato da Cloud Storage. Il modello caricato è configurato con la località degli artefatti del modello in Cloud Storage e la località dell'immagine container di gestione all'interno di Artifact Registry. Vertex AI include anche un endpoint in cui è stato eseguito il deployment del modello. Una volta eseguito il deployment del modello nell'endpoint, Vertex AI associa le risorse fisiche al modello in modo che questo possa fornire previsioni online.

Come parte dell'implementazione di questa architettura di gestione, dovrai esportare il tuo modello ML per l'utilizzo da parte di altre applicazioni e definire la tua immagine container di pubblicazione. L'implementazione di riferimento fornita in questo documento fornisce il codice usato per definire e creare l'immagine container di gestione. Questo codice include anche gli artefatti del modello per un modello Spark ML esportato in precedenza. Con alcune modifiche alla configurazione, puoi utilizzare questa implementazione di riferimento per gestire i tuoi modelli Spark ML.

Tuttavia, puoi implementare questa architettura di gestione autonomamente e non utilizzare l'implementazione di riferimento. Se decidi di implementare la tua architettura, devi fare quanto segue:

  • Esporta il modello in modo che possa essere utilizzato da altre applicazioni. Questo processo dipende dai framework e dagli strumenti ML che utilizzi. Ad esempio, potresti scegliere di esportare i tuoi modelli MLlib di Spark creando un bundle MLeap come descritto nell'implementazione di riferimento. Puoi vedere altri esempi su come esportare modelli in Esportare gli artefatti dei modelli per la previsione.
  • Progetta la tua immagine container di pubblicazione in modo che soddisfi i requisiti per i container personalizzati che la rendono compatibile con Vertex AI. Il codice può essere nel linguaggio di programmazione che preferisci.
  • Comprimi il codice in un formato di file del pacchetto compatibile con il linguaggio di programmazione che hai utilizzato. Ad esempio, puoi usare un file JAR per il codice Java o una ruota Python per il codice Python.
  • Crea un'immagine container personalizzata in grado di pubblicare il codice della modalità personalizzata.

Implementazione dei riferimenti

La seguente implementazione di riferimento serve un modello Spark MLib che prevede le specie di iride in base alla lunghezza e alla larghezza dei sepali e dei petali del fiore.

Puoi trovare il modello utilizzato in questa implementazione nella directory example_model nel repository vertex-ai-spark-ml-serving.git. La directory contiene gli artefatti del modello utilizzati dal container di pubblicazione per eseguire le previsioni e include i seguenti file:

  • Il file example_model/model.zip è un modello di regressione logistica creato utilizzando Spark MLlib, è stato addestrato utilizzando il set di dati Iris ed è stato convertito in un bundle MLeap. Il modello prevede la specie di un fiore dell'iride utilizzando la lunghezza e la larghezza dei sepali e dei petali del fiore.
  • Il file example_model/schema.json è un file JSON che descrive lo schema del modello. Lo schema del modello descrive i campi di input previsti per le istanze di previsione e i campi di output per i risultati della previsione necessari per lo schema MLeap.

Usa il tuo modello Mlib

Per utilizzare il tuo modello con questa implementazione di riferimento, assicurati innanzitutto che il modello Spark MLlib sia stato esportato in un pacchetto MLeap. Quindi, per gestire il tuo modello MLib Spark, devi fornire gli artefatti del modello appropriati: il bundle MLeap e lo schema del modello.

Pacchetto MLeap

Il container di pubblicazione determina la località del bundle MLeap utilizzando la variabile di ambiente AIP_STORAGE_URI che viene trasmessa da Vertex AI al container all'avvio. Il valore della variabile AIP_STORAGE_URI viene specificato quando carichi il modello in Vertex AI.

Schema modello

Lo schema del modello descrive le caratteristiche di input e l'output di previsione di un modello. Lo schema del modello viene rappresentato utilizzando dati JSON. Di seguito è riportato lo schema utilizzato in questa implementazione di riferimento per prevedere le specie di iride in base alla lunghezza e alla larghezza del fiore dei sepali e dei petali:

{
  "input": [
    {
      "name": "sepal_length",
      "type": "FLOAT"
    },
    {
      "name": "sepal_width",
      "type": "FLOAT"
    },
    {
      "name": "petal_length",
      "type": "FLOAT"
    },
    {
      "name": "petal_width",
      "type": "FLOAT"
    }
  ],
  "output": [
    {
      "name": "probability",
      "type": "DOUBLE",
      "struct": "VECTOR"
    }
  ]
}

Nello schema di esempio, l'array input contiene i campi di input (colonne) del modello, mentre l'array output contiene i campi di output (colonne) da restituire dal modello. In entrambi gli array, ciascun oggetto contiene le seguenti proprietà:

  • name: nome del campo (colonna).
  • type: il tipo di campo (colonna). I tipi validi sono BOOLEAN, BYTE, DOUBLE, FLOAT, INTEGER, LONG, SHORT e STRING.
  • (Facoltativo) struct: la struttura del campo, ad esempio un array o uno scalare. Le strutture valide includono BASIC (tipo a scala), ARRAY (Spark Array) e VECTOR (Scinta DenseVector). BASIC viene utilizzato se il campo struct non è presente.

Per passare lo schema del modello al container di pubblicazione, puoi utilizzare uno dei seguenti metodi:

  • Specifica i dati JSON che definiscono lo schema nella variabile di ambiente MLEAP_SCHEMA. La variabile di ambiente MLEAP_SCHEMA deve contenere i dati JSON stessi e non un percorso di un file contenente lo schema JSON.
  • Archivia i dati JSON in un file denominato schema.json e rendi questo file disponibile per il container all'indirizzo ${AIP_STORAGE_URI}/schema.json. Questo è il metodo utilizzato per il modello MLib di esempio fornito con questa documentazione.

Se utilizzi entrambi i metodi per passare lo schema del modello al container di pubblicazione, i dati JSON archiviati nella variabile di ambiente MLEAP_SCHEMA hanno la precedenza.

Costi

Questa implementazione di riferimento utilizza i seguenti componenti fatturabili di Google Cloud:

Per generare una stima dei costi in base all'utilizzo previsto, utilizza il Calcolatore prezzi.

Una volta completata l'implementazione del riferimento, puoi evitare di continuare la fatturazione eliminando le risorse che hai creato. Per ulteriori informazioni, consulta Pulizia.

Prima di iniziare

  1. Nella pagina del selettore di progetti della console Google Cloud, seleziona o crea un progetto Google Cloud.

    Vai al selettore progetti

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

  3. Abilita le API Vertex AI, Cloud Build, Cloud Storage, and Artifact Registry.

    Abilita le API

  4. Nella console Google Cloud, attiva Cloud Shell.

    Attiva Cloud Shell

  5. Individua il tuo ID progetto e impostalo in Cloud Shell.
    export PROJECT_ID=YOUR_PROJECT_ID
    gcloud config set project ${PROJECT_ID}
    

    Sostituisci YOUR_PROJECT_ID con l'ID progetto.

Crea l'immagine del builder scala-sbt

Per creare l'immagine container di gestione, utilizzerai Cloud Build con lo strumento scala-sbt Community Builder. Questo processo di compilazione dipende dall'esistenza dell'immagine del builder sbt-scala nel Container Registry del progetto.

  1. In Cloud Shell, clona il repository cloud-builders-community:

    git clone https://github.com/GoogleCloudPlatform/cloud-builders-community.git
    
  2. Vai alla directory del progetto:

    cd cloud-builders-community/scala-sbt
    
  3. Crea l'immagine del builder scala-sbt ed eseguine il push su Container Registry:

    gcloud builds submit .
    

Crea l'immagine container di pubblicazione

Vertex AI usa il container di pubblicazione per eseguire richieste di previsione per il modello di esempio. Il primo passaggio per creare l'immagine container di gestione è creare un repository Docker in Artifact Registry in cui archiviare l'immagine. Dovrai quindi concedere a Vertex AI l'autorizzazione per eseguire il pull dell'immagine container di gestione dal repository. Dopo aver creato il repository e aver concesso le autorizzazioni, puoi creare l'immagine container di gestione ed eseguirne il push su Artifact Registry.

  1. In Cloud Shell, crea un repository Docker in Artifact Registry:

    REPOSITORY="vertex-ai-prediction"
    LOCATION="us-central1"
    
    gcloud artifacts repositories create $REPOSITORY \
        --repository-format=docker \
        --location=$LOCATION
    
  2. Concedi il ruolo Lettore Artifact Registry all'agente di servizio Vertex AI:

    PROJECT_NUMBER=$(gcloud projects describe $PROJECT_ID \
        --format="value(projectNumber)")
    SERVICE_ACCOUNT="service-$PROJECT_NUMBER@gcp-sa-aiplatform.iam.gserviceaccount.com"
    
    gcloud projects add-iam-policy-binding $PROJECT_ID \
        --member="serviceAccount:$SERVICE_ACCOUNT" \
        --role="roles/artifactregistry.reader"
    
  3. Clona il repository spark-ml-serving:

    git clone https://github.com/GoogleCloudPlatform/vertex-ai-spark-ml-serving.git
    
  4. Vai alla directory del progetto:

    cd vertex-ai-spark-ml-serving
    
  5. Crea l'immagine container di pubblicazione nel tuo progetto:

    IMAGE=spark-ml-serving
    
    gcloud builds submit --config=cloudbuild.yaml \
        --substitutions="_LOCATION=$LOCATION,_REPOSITORY=$REPOSITORY,_IMAGE=$IMAGE" .
    

    Il file cloudbuild.yaml specifica due builder: scala-sbt e docker immagini. Cloud Build utilizza il builder scala-sbt per compilare il codice di pubblicazione del modello da Cloud Storage, quindi pacchettizzare il codice compilato in un file JAR eseguibile. Cloud Build utilizza il builder docker per creare l'immagine container di pubblicazione che contiene il file JAR. Dopo aver creato l'immagine del container di pubblicazione, viene eseguito il push dell'immagine su Artifact Registry.

Importa il modello in Vertex AI

Il container di gestione legge gli artefatti del modello da Cloud Storage. Devi creare una località di archiviazione per questi artefatti prima di importare il modello in Vertex AI. Quando poi importi il modello, sono necessarie sia la località di archiviazione degli artefatti del modello sia l'immagine container di gestione in Artifact Registry.

  1. In Cloud Shell, crea un bucket per gli artefatti del modello:

    REGION="us-central1"
    BUCKET="YOUR_BUCKET_NAME"
    gsutil mb -l $REGION gs://$BUCKET
    

    Sostituisci YOUR_BUCKET_NAME con il nome del bucket.

  2. Copia gli artefatti del modello nel bucket:

    gsutil cp example_model/* gs://$BUCKET/example_model/
    
  3. Importa il modello in Vertex AI:

    DISPLAY_NAME="iris-$(date +'%Y%m%d%H%M%S')"
    IMAGE_URI="${LOCATION}-docker.pkg.dev/$PROJECT_ID/${REPOSITORY}/${IMAGE}"
    ARTIFACT_URI="gs://$BUCKET/example_model/"
    
    gcloud ai models upload \
        --region=$REGION \
        --display-name=$DISPLAY_NAME \
        --container-image-uri=$IMAGE_URI \
        --artifact-uri=$ARTIFACT_URI \
        --container-health-route="/health" \
        --container-predict-route="/predict"
    

    Nel comando gcloud ai models upload, il valore del parametro --artifact-uri specifica il valore della variabile AIP_STORAGE_URI. Questa variabile fornisce la posizione del bundle MLeap che viene importato in Vertex AI.

Esegui il deployment del modello su un nuovo endpoint

Affinché Vertex AI possa eseguire previsioni, è necessario eseguire il deployment del modello importato in un endpoint. Quando esegui il deployment del modello, sono necessari sia l'ID dell'endpoint sia l'ID del modello.

  1. In Cloud Shell, crea l'endpoint del modello:

    gcloud ai endpoints create \
        --region=$REGION \
        --display-name=$DISPLAY_NAME
    

    Lo strumento a riga di comando gcloud potrebbe richiedere alcuni secondi per creare l'endpoint.

  2. Ottieni l'ID endpoint dell'endpoint appena creato:

    ENDPOINT_ID=$(gcloud ai endpoints list \
        --region=$REGION \
        --filter=display_name=$DISPLAY_NAME \
        --format='value(name)')
    
    # Print ENDPOINT_ID to the console
    echo "Your endpoint ID is: $ENDPOINT_ID"
    
  3. Ottieni l'ID del modello che hai importato nella sezione Importa il modello in Vertex AI:

    MODEL_ID=$(gcloud ai models list \
        --region=$REGION \
        --filter=display_name=$DISPLAY_NAME \
        --format='value(name)')
    
    # Print MODEL_ID to the console
    echo "Your model ID is: $MODEL_ID"
    
  4. Esegui il deployment del modello nell'endpoint:

    gcloud ai endpoints deploy-model $ENDPOINT_ID \
        --region=$REGION \
        --model=$MODEL_ID \
        --display-name=$DISPLAY_NAME \
        --traffic-split="0=100"
    

    Il comando gcloud esegue il deployment del modello sull'endpoint. I valori predefiniti vengono utilizzati per il tipo di risorsa della macchina, il numero minimo e massimo di nodi e altre opzioni di configurazione. Per ulteriori informazioni sulle opzioni di deployment per i modelli, consulta la documentazione di Vertex AI.

Testa l'endpoint

Dopo aver eseguito il deployment del modello sull'endpoint, puoi testare l'implementazione. Per testare l'endpoint, puoi utilizzare il client di esempio incluso nel codice di implementazione di riferimento. Il client di esempio genera istanze di previsione e invia richieste di previsione all'endpoint. Ogni istanza di previsione contiene valori casuali per sepal_length, sepal_width, petal_length e petal_width. Per impostazione predefinita, il client di esempio combina più istanze di previsione in una singola richiesta. La risposta dalla risposta dell'endpoint include una previsione per ogni istanza inviata nella richiesta. La previsione contiene le probabilità per ogni classe nel set di dati Iris (setosa, versicolor e virginica).

  • In Cloud Shell, esegui il client di previsione di esempio:

    cd example_client
    ./run_client.sh --project $PROJECT_ID \
        --location $LOCATION \
        --endpoint $ENDPOINT_ID
    

    Quando esegui lo script per la prima volta, crea un ambiente virtuale Python e installa le dipendenze. Dopo aver installato le dipendenze, lo script esegue il client di esempio. Per ogni richiesta, il client stampa le istanze di previsione e le probabilità di classe corrispondenti al terminale. Di seguito è riportato un estratto dell'output:

    Sending 10 asynchronous prediction requests with 3 instances per request ...
    
    ==> Response from request #10:
    
    Instance 1:     sepal_length:   5.925825137450266
                    sepal_width:    4.5047557888651
                    petal_length:   1.0432434310300223
                    petal_width:    0.5050397721287457
    
    Prediction 1:   setosa:         0.2036041134824573
                    versicolor:     0.6062980065549213
                    virginica:      0.1900978799626214
    
    Instance 2:     sepal_length:   6.121228622484405
                    sepal_width:    3.406317728235072
                    petal_length:   3.178583759980504
                    petal_width:    2.815141143581328
    
    Prediction 2:   setosa:         0.471811302254083
                    versicolor:     0.2063720436033448
                    virginica:      0.3218166541425723
    
    Instance 3:     sepal_length:   7.005781590327274
                    sepal_width:    2.532116893508745
                    petal_length:   2.6351337947193474
                    petal_width:    2.270855223519198
    
    Prediction 3:   setosa:         0.453579051699638
                    versicolor:     0.2132869980698818
                    virginica:      0.3331339502304803
    

Esegui la pulizia

Per evitare che al tuo account Google Cloud vengano addebitati costi relativi alle risorse utilizzate in questa implementazione di riferimento, elimina il progetto che le contiene o mantieni il progetto ed elimina le singole risorse.

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 singole risorse

  1. In Cloud Shell, annulla il deployment del modello dall'endpoint:

    DEPLOYED_MODEL_ID=$(gcloud ai endpoints describe $ENDPOINT_ID \
        --region=$REGION \
        --format='value(deployedModels.id)')
    
    gcloud ai endpoints undeploy-model $ENDPOINT_ID \
        --region=$REGION \
        --deployed-model-id=$DEPLOYED_MODEL_ID
    
  2. Elimina l'endpoint:

    gcloud ai endpoints delete $ENDPOINT_ID \
        --region=$REGION \
        --quiet
    
  3. Elimina il modello:

    gcloud ai models delete $MODEL_ID \
        --region=$REGION
    
  4. Elimina l'immagine container di pubblicazione:

    gcloud artifacts docker images delete \
        $LOCATION-docker.pkg.dev/$PROJECT_ID/$REPOSITORY/$IMAGE \
        --delete-tags \
        --quiet
    
  5. Elimina il container del builder scala-sbt:

    gcloud container images delete gcr.io/$PROJECT_ID/scala-sbt \
        --force-delete-tags \
        --quiet
    
  6. Elimina tutti i bucket Cloud Storage non più necessari:

    gsutil rm -r YOUR_BUCKET_NAME
    

    Se elimini un bucket, verranno eliminati anche tutti gli oggetti archiviati al suo interno. I bucket e gli oggetti eliminati non possono essere recuperati dopo l'eliminazione.

Passaggi successivi