Routines de prédiction personnalisées

Les routines de prédiction personnalisées vous permettent de déterminer le code qui s'exécute lorsque vous envoyez une requête de prédiction en ligne à AI Platform Prediction.

Lorsque vous déployez une ressource de version sur AI Platform Prediction sans utiliser de routine de prédiction personnalisée, la ressource gère les requêtes de prédiction en effectuant l'opération de prédiction du framework de machine learning utilisé précédemment pour l'entraînement.

Toutefois, lorsque vous déployez une routine de prédiction personnalisée en tant que ressource de version, vous pouvez indiquer à AI Platform Prediction d'exécuter du code Python personnalisé en réponse à chaque requête de prédiction reçue. Vous pouvez prétraiter l'entrée de prédiction avant que votre modèle entraîné n'effectue l'opération ou post-traiter la prédiction du modèle avant d'envoyer le résultat.

Pour créer une routine de prédiction personnalisée, vous devez fournir deux parties à AI Platform Prediction lorsque vous créez la version de votre modèle :

  • Un répertoire de modèle dans Cloud Storage, contenant tous les artefacts à utiliser pour les prédictions

  • Un package de distribution source Python .tar.gz dans Cloud Storage contenant la mise en œuvre de l'interface du prédicteur et tout autre code personnalisé que vous souhaitez qu'AI Platform Prediction utilise au moment de la prédiction.

Vous ne pouvez déployer une routine de prédiction personnalisée que si vous utilisez un ancien type de machine (MLS1) pour votre version de modèle.

Importer des artefacts de modèle vers le répertoire de modèle

Suivez le guide sur le déploiement de modèles pour importer votre modèle entraîné, ainsi que tous les autres fichiers apportant des informations sur les données ou l'état qu'AI Platform Prediction pourra utiliser lors de la prédiction, vers Cloud Storage.

La taille totale du fichier contenant les artefacts du modèle que vous déployez dans AI Platform Prediction doit être inférieure ou égale à 500 Mo. Vous pouvez demander un quota plus élevé pour déployer des modèles plus volumineux.

Vous pouvez importer votre modèle de machine learning entraîné dans le répertoire de modèle à l'aide d'un SavedModel TensorFlow ou d'un fichier model.joblib, model.pkl ou model.bst. Vous pouvez également fournir le modèle avec un fichier HDF5 contenant un modèle tf.keras entraîné ou un fichier dans un autre format sérialisé.

De plus, vous avez la possibilité d'inclure un fichier pickle avec une instance d'une classe de préprocesseur personnalisée contenant l'état sérialisé de l'entraînement.

Par exemple, considérons le préprocesseur suivant, défini dans le fichier nommé preprocess.py :

import numpy as np

class ZeroCenterer(object):
    """Stores means of each column of a matrix and uses them for preprocessing.
    """

    def __init__(self):
        """On initialization, is not tied to any distribution."""
        self._means = None

    def preprocess(self, data):
        """Transforms a matrix.

        The first time this is called, it stores the means of each column of
        the input. Then it transforms the input so each column has mean 0. For
        subsequent calls, it subtracts the stored means from each column. This
        lets you 'center' data at prediction time based on the distribution of
        the original training data.

        Args:
            data: A NumPy matrix of numerical data.

        Returns:
            A transformed matrix with the same dimensions as the input.
        """
        if self._means is None:  # during training only
            self._means = np.mean(data, axis=0)
        return data - self._means

Lors de l'entraînement sur un ensemble de données numérique, le préprocesseur centre les données autour de zéro en soustrayant la moyenne de chaque colonne à chaque valeur dans la colonne. Vous pouvez ensuite exporter l'instance de préprocesseur sous la forme d'un fichier pickle, preprocessor.pkl, qui conserve les moyennes de chaque colonne calculées à partir des données d'entraînement.

Pendant la prédiction, une routine de prédiction personnalisée peut charger le préprocesseur à partir de ce fichier pour effectuer une transformation identique sur l'entrée de prédiction.

Pour apprendre à utiliser un préprocesseur avec état semblable dans votre routine de prédiction personnalisée, reportez-vous à la section suivante, qui explique comment mettre en œuvre l'interface du prédicteur.

Pour obtenir un exemple complet d'utilisation d'un préprocesseur avec état pendant les opérations d'entraînement et de prédiction, consultez la page Créer une routine de prédiction personnalisée avec Keras ou Créer une routine de prédiction personnalisée avec scikit-learn.

Créer le prédicteur

Indiquez à AI Platform Prediction comment gérer les requêtes de prédiction en lui fournissant une classe de prédicteur. Il s'agit d'une classe qui implémente l'interface suivante :

class Predictor(object):
    """Interface for constructing custom predictors."""

    def predict(self, instances, **kwargs):
        """Performs custom prediction.

        Instances are the decoded values from the request. They have already
        been deserialized from JSON.

        Args:
            instances: A list of prediction input instances.
            **kwargs: A dictionary of keyword args provided as additional
                fields on the predict request body.

        Returns:
            A list of outputs containing the prediction results. This list must
            be JSON serializable.
        """
        raise NotImplementedError()

    @classmethod
    def from_path(cls, model_dir):
        """Creates an instance of Predictor using the given path.

        Loading of the predictor should be done in this method.

        Args:
            model_dir: The local directory that contains the exported model
                file along with any additional files uploaded when creating the
                version resource.

        Returns:
            An instance implementing this Predictor class.
        """
        raise NotImplementedError()

Les nœuds de prédiction d'AI Platform Prediction exploitent la méthode de classe from_path pour charger une instance de votre prédicteur. Cette méthode doit charger les artefacts que vous avez enregistrés dans le répertoire de modèle, dont le contenu est copié depuis Cloud Storage vers un emplacement révélé par l'argument model_dir.

Chaque fois que votre déploiement reçoit une requête de prédiction en ligne, l'instance de la classe de prédicteur renvoyée par from_path utilise sa méthode predict pour générer des prédictions. AI Platform Prediction sérialise la valeur de renvoi de cette méthode au format JSON et l'envoie en tant que réponse à la requête de prédiction.

Notez que la méthode predict n'a pas besoin de convertir les entrées provenant de fichiers JSON en objets Python, ni de convertir un résultat au format JSON. AI Platform Prediction gère ces opérations en dehors de la méthode predict.

AI Platform Prediction fournit l'argument instances en analysant le champ instances du corps de la requête predict adressée à l'API AI Platform Training and Prediction. Le service analyse également tous les autres champs du corps de la requête et les transmet à la méthode predict sous forme d'entrées dans le dictionnaire **kwargs. Pour en savoir plus, découvrez comment structurer une requête predict pour l'API AI Platform Training and Prediction.

En reprenant l'exemple de la section précédente, supposons que le répertoire de modèle contienne preprocessor.pkl (l'instance picklée de la classe ZeroCenterer), ainsi qu'un modèle tf.keras entraîné exporté sous forme de fichier model.h5 ou un modèle scikit-learn entraîné exporté sous forme de fichier model.joblib.

Selon le framework de machine learning utilisé, mettez en œuvre l'une des classes de prédicteur suivantes dans un fichier nommé predictor.py :

TensorFlow

import os
import pickle

import numpy as np
from tensorflow import keras

class MyPredictor(object):
    """An example Predictor for an AI Platform custom prediction routine."""

    def __init__(self, model, preprocessor):
        """Stores artifacts for prediction. Only initialized via `from_path`.
        """
        self._model = model
        self._preprocessor = preprocessor

    def predict(self, instances, **kwargs):
        """Performs custom prediction.

        Preprocesses inputs, then performs prediction using the trained Keras
        model.

        Args:
            instances: A list of prediction input instances.
            **kwargs: A dictionary of keyword args provided as additional
                fields on the predict request body.

        Returns:
            A list of outputs containing the prediction results.
        """
        inputs = np.asarray(instances)
        preprocessed_inputs = self._preprocessor.preprocess(inputs)
        outputs = self._model.predict(preprocessed_inputs)
        return outputs.tolist()

    @classmethod
    def from_path(cls, model_dir):
        """Creates an instance of MyPredictor using the given path.

        This loads artifacts that have been copied from your model directory in
        Cloud Storage. MyPredictor uses them during prediction.

        Args:
            model_dir: The local directory that contains the trained Keras
                model and the pickled preprocessor instance. These are copied
                from the Cloud Storage model directory you provide when you
                deploy a version resource.

        Returns:
            An instance of `MyPredictor`.
        """
        model_path = os.path.join(model_dir, 'model.h5')
        model = keras.models.load_model(model_path)

        preprocessor_path = os.path.join(model_dir, 'preprocessor.pkl')
        with open(preprocessor_path, 'rb') as f:
            preprocessor = pickle.load(f)

        return cls(model, preprocessor)

scikit-learn

import os
import pickle

import numpy as np
from sklearn.externals import joblib

class MyPredictor(object):
    """An example Predictor for an AI Platform custom prediction routine."""

    def __init__(self, model, preprocessor):
        """Stores artifacts for prediction. Only initialized via `from_path`.
        """
        self._model = model
        self._preprocessor = preprocessor

    def predict(self, instances, **kwargs):
        """Performs custom prediction.

        Preprocesses inputs, then performs prediction using the trained
        scikit-learn model.

        Args:
            instances: A list of prediction input instances.
            **kwargs: A dictionary of keyword args provided as additional
                fields on the predict request body.

        Returns:
            A list of outputs containing the prediction results.
        """
        inputs = np.asarray(instances)
        preprocessed_inputs = self._preprocessor.preprocess(inputs)
        outputs = self._model.predict(preprocessed_inputs)
        return outputs.tolist()

    @classmethod
    def from_path(cls, model_dir):
        """Creates an instance of MyPredictor using the given path.

        This loads artifacts that have been copied from your model directory in
        Cloud Storage. MyPredictor uses them during prediction.

        Args:
            model_dir: The local directory that contains the trained
                scikit-learn model and the pickled preprocessor instance. These
                are copied from the Cloud Storage model directory you provide
                when you deploy a version resource.

        Returns:
            An instance of `MyPredictor`.
        """
        model_path = os.path.join(model_dir, 'model.joblib')
        model = joblib.load(model_path)

        preprocessor_path = os.path.join(model_dir, 'preprocessor.pkl')
        with open(preprocessor_path, 'rb') as f:
            preprocessor = pickle.load(f)

        return cls(model, preprocessor)

Sachez que la méthode predict convertit les résultats de prédiction en une liste avec la méthode tolist avant de les renvoyer. Les tableaux NumPy ne sont pas sérialisables au format JSON. Par conséquent, vous devez les convertir en listes de nombres (qui sont sérialisables au format JSON). Sinon, AI Platform Prediction ne pourra pas envoyer la réponse de prédiction.

Empaqueter votre prédicteur et ses dépendances

Vous devez empaqueter votre prédicteur en tant que package de distribution source .tar.gz. Comme NumPy, TensorFlow et scikit-learn sont inclus dans l'image de l'environnement d'exécution d'AI Platform Prediction, il n'est pas nécessaire de les ajouter au package tarball. Toutefois, assurez-vous d'intégrer toutes les dépendances du prédicteur qui ne sont pas préinstallées sur AI Platform Prediction.

Pour l'exemple ci-dessus, vous devez inclure preprocess.py dans le package de distribution source, même si votre prédicteur ne l'importe pas explicitement. Sinon, preprocessor = pickle.load(f) échouera, car Python ne reconnaîtra pas la classe de l'instance ZeroCenterer dans le fichier pickle.

Le fichier setup.py suivant illustre une façon d'empaqueter ces scripts :

from setuptools import setup

setup(
    name='my_custom_code',
    version='0.1',
    scripts=['predictor.py', 'preprocess.py'])

Pour empaqueter et importer l'exemple de code personnalisé décrit sur cette page, procédez comme suit :

  1. Créez dans le même répertoire les fichiers preprocess.py, predictor.py et setup.py décrits dans les sections précédentes. Accédez à ce répertoire depuis votre interface système.

  2. Exécutez python setup.py sdist --formats=gztar pour créer dist/my_custom_code-0.1.tar.gz.

  3. Importez ce package tarball dans un emplacement de préproduction dans Cloud Storage.

    Cet emplacement ne doit pas nécessairement être identique à celui de votre répertoire de modèle. Si vous envisagez de créer et de déployer plusieurs versions de votre routine de prédiction personnalisée, vous pouvez importer vos packages de code personnalisés dans un répertoire de préproduction donné. Vous pouvez incrémenter l'argument version dans le fichier setup.py lorsque vous mettez à jour le code pour effectuer un suivi des différentes versions.

    La commande suivante illustre une manière d'importer votre package de distribution source vers Cloud Storage :

    gsutil cp dist/my_custom_code-0.1.tar.gz gs://your-bucket/path-to-staging-dir/
    

Vous pouvez fournir le code de votre routine de prédiction personnalisée dans un ou plusieurs packages.

Déployer une routine de prédiction personnalisée

Commencez par sélectionner une région où la prédiction en ligne est disponible et utilisez gcloud pour créer une ressource de modèle :

gcloud ai-platform models create model-name \
  --regions chosen-region

Assurez-vous que votre composant gcloud beta est mis à jour, puis créez une ressource de version en prêtant une attention particulière aux indicateurs gcloud suivants :

  • --origin : chemin d'accès au répertoire de modèle dans Cloud Storage.
  • --package-uris : liste séparée par des virgules de packages tarball comprenant du code utilisateur dans Cloud Storage, y compris celui contenant votre classe de prédicteur.
  • --prediction-class : nom complet de votre classe de prédicteur (module_name.class_name).
  • --framework : ne spécifiez pas de framework lors du déploiement d'une routine de prédiction personnalisée.
  • --runtime-version : les routines de prédiction personnalisées sont disponibles dans les versions d'exécution 1.4 à 2.2.

La commande suivante montre comment créer une ressource de version en fonction des fichiers d'exemple décrits dans les sections précédentes :

gcloud components install beta

gcloud beta ai-platform versions create version-name \
  --model model-name \
  --runtime-version 2.2 \
  --python-version 3.7 \
  --origin gs://your-bucket/path-to-model-dir \
  --package-uris gs://your-bucket/path-to-staging-dir/my_custom_code-0.1.tar.gz \
  --prediction-class predictor.MyPredictor

Pour en savoir plus sur la création de modèles et de versions, ou pour apprendre à les créer avec Google Cloud Console plutôt que l'outil de ligne de commande gcloud, consultez le guide sur le déploiement de modèles.

Spécifier un compte de service

Lorsque vous créez une ressource de version, vous pouvez éventuellement spécifier un compte de service que votre routine de prédiction personnalisée utilisera lors de la prédiction. Cela vous permet de personnaliser les autorisations d'accès à d'autres ressources de Google Cloud dont elle peut bénéficier. Découvrez comment spécifier un compte de service pour votre routine de prédiction personnalisée.

Étapes suivantes

  • Suivez un tutoriel sur les routines de prédiction personnalisées avec Keras ou scikit-learn pour obtenir un exemple plus complet d'entraînement et de déploiement d'un modèle à l'aide d'une routine de prédiction personnalisée.
  • Consultez le guide sur l'exportation de modèles pour en savoir plus sur l'exportation d'artefacts à des fins de prédiction, sans utiliser de routine de prédiction personnalisée.
  • Consultez le guide sur le déploiement de modèles pour en savoir plus sur le déploiement des ressources model et version sur AI Platform Prediction afin de diffuser des prédictions.