Premiers pas avec Endpoints pour GKE avec ESPv2

Ce tutoriel explique comment déployer un exemple de service gRPC simple avec Extensible Service Proxy V2 (ESPv2) sur Google Kubernetes. App Engine (GKE). Il utilise la version Python de l'exemple bookstore-grpc. Consultez la section Étapes suivantes pour obtenir des exemples gRPC dans d'autres langages.

Ce tutoriel utilise des images de conteneur prédéfinies du code d'exemple et du proxy ESPv2 stockées dans Container Registry. Si vous n'êtes pas encore familiarisé avec les conteneurs, consultez les sections suivantes pour plus d'informations :

Pour obtenir une présentation de Cloud Endpoints, consultez les pages À propos de Cloud Endpoints et Présentation de l'architecture Cloud Endpoints.

Objectifs

Tout au long du tutoriel, reportez-vous au récapitulatif des étapes présenté ci-dessous. Toutes les tâches sont nécessaires pour envoyer des requêtes à l'API.

  1. Configurez un projet Google Cloud et téléchargez le logiciel requis. Consultez la section Avant de commencer.
  2. Copiez et configurez les fichiers figurant dans l'exemple bookstore-grpc. Consultez la section Configurer Endpoints.
  3. Déployez la configuration Endpoints pour créer un service Endpoints. Consultez la section Déployer la configuration Endpoints.
  4. Créez un backend pour diffuser et déployer l'API. Consultez la section Déployer le backend de l'API.
  5. Obtenez l'adresse IP externe du service. Consultez la section Obtenir l'adresse IP externe du service.
  6. Envoyez une requête à l'API. Consultez la section Envoyer une requête à l'API.
  7. Faites le nécessaire pour éviter que des frais ne soient facturés sur votre compte Google Cloud. Consultez la section Effectuer un nettoyage.

Coûts

Ce tutoriel utilise les composants facturables suivants de Google Cloud :

Obtenez une estimation des coûts en fonction de votre utilisation prévue à l'aide du simulateur de coût. Les nouveaux utilisateurs de Google Cloud peuvent bénéficier d'un essai gratuit.

Une fois que vous avez terminé ce tutoriel, vous pouvez éviter de continuer à payer des frais en supprimant les ressources que vous avez créées. Pour en savoir plus, consultez la section Effectuer un nettoyage.

Avant de commencer

  1. Connectez-vous à votre compte Google Cloud. Si vous débutez sur Google Cloud, créez un compte pour évaluer les performances de nos produits en conditions réelles. Les nouveaux clients bénéficient également de 300 $ de crédits gratuits pour exécuter, tester et déployer des charges de travail.
  2. Dans Google Cloud Console, sur la page de sélection du projet, sélectionnez ou créez un projet Google Cloud.

    Accéder au sélecteur de projet

  3. Assurez-vous que la facturation est activée pour votre projet Cloud. Découvrez comment vérifier que la facturation est activée pour votre projet.

  4. Dans Google Cloud Console, sur la page de sélection du projet, sélectionnez ou créez un projet Google Cloud.

    Accéder au sélecteur de projet

  5. Assurez-vous que la facturation est activée pour votre projet Cloud. Découvrez comment vérifier que la facturation est activée pour votre projet.

  6. Notez l'ID du projet Google Cloud, car vous en aurez besoin ultérieurement.
  7. Installez et initialisez le SDK Cloud.
  8. Mettez à jour le SDK Cloud et installez les composants Endpoints.
    gcloud components update
  9. Assurez-vous que le SDK Cloud (gcloud) est autorisé à accéder à vos données et services sur Google Cloud :
    gcloud auth login
    Un nouvel onglet de navigateur vous invite à choisir un compte.
  10. Définissez le projet par défaut sur votre ID de projet.
    gcloud config set project YOUR_PROJECT_ID

    Remplacez YOUR_PROJECT_ID par l'ID du projet.

    Si vous avez d'autres projets Google Cloud et que vous voulez les gérer à l'aide de gcloud, consultez la page Gérer les configurations du SDK Cloud.

  11. Installez kubectl :
    gcloud components install kubectl
  12. Obtenez de nouveaux identifiants utilisateur à utiliser comme identifiants par défaut de l'application. Les identifiants utilisateur sont nécessaires pour autoriser kubectl.
    gcloud auth application-default login
    Dans le nouvel onglet de navigateur, choisissez un compte.
  13. Suivez les étapes figurant sur la page gRPC Python Quickstart pour installer gRPC et les outils gRPC.

Configurer Endpoints

L'exemple bookstore-grpc contient les fichiers que vous devez copier localement puis configurer.

  1. Créez un fichier descripteur protobuf autonome à partir de votre fichier de service .proto :
    1. Enregistrez une copie du fichier bookstore.proto à partir de l'exemple de dépôt. Ce fichier définit l'API du service Bookstore.
    2. Créez le répertoire suivant : mkdir generated_pb2.
    3. Créez le fichier descripteur api_descriptor.pb à l'aide du compilateur de tampons de protocole protoc. Exécutez la commande suivante dans le répertoire où vous avez enregistré bookstore.proto :
      python -m grpc_tools.protoc \
          --include_imports \
          --include_source_info \
          --proto_path=. \
          --descriptor_set_out=api_descriptor.pb \
          --python_out=generated_pb2 \
          --grpc_python_out=generated_pb2 \
          bookstore.proto
      

      Dans la commande ci-dessus, --proto_path est défini sur le répertoire de travail actuel. Dans votre environnement de compilation gRPC, si vous utilisez un autre répertoire pour les fichiers d'entrée .proto, modifiez --proto_path pour que le compilateur recherche le répertoire dans lequel vous avez enregistré votre fichier bookstore.proto.

  2. Créez un fichier YAML de configuration d'API gRPC :
    1. Enregistrez une copie du fichier api_config.yaml. Ce fichier définit la configuration d'API gRPC pour le service Bookstore.
    2. Remplacez MY_PROJECT_ID dans votre fichier api_config.yaml par votre ID de projet Google Cloud. Exemple :
      #
      # Name of the service configuration.
      #
      name: bookstore.endpoints.example-project-12345.cloud.goog
      

      Notez que la valeur du champ apis.name dans ce fichier correspond exactement au nom d'API complet du fichier .proto. À défaut, le déploiement échouera. Le service Bookstore est défini dans bookstore.proto dans le package endpoints.examples.bookstore. Son nom d'API complet est endpoints.examples.bookstore.Bookstore, tel qu'il apparaît dans le fichier api_config.yaml

      apis:
        - name: endpoints.examples.bookstore.Bookstore
      

Pour en savoir plus, consultez la page Configurer Endpoints.

Déployer la configuration Endpoints

Pour déployer la configuration Endpoints, exécutez la commande gcloud endpoints services deploy. Cette commande crée un service géré à l'aide de Service Management.

  1. Vérifiez que vous êtes bien dans le répertoire contenant les fichiers api_descriptor.pb et api_config.yaml.
  2. Vérifiez que le projet par défaut actuellement utilisé par l'outil de ligne de commande gcloud est bien le projet Google Cloud vers lequel vous souhaitez déployer la configuration Endpoints. Validez l'ID de projet renvoyé par la commande suivante, afin de vous assurer que le service est créé dans le bon projet.
    gcloud config list project
    

    Si vous devez modifier le projet par défaut, exécutez la commande suivante :

    gcloud config set project YOUR_PROJECT_ID
    
  3. Déployez le fichier proto descriptor et le fichier de configuration à l'aide de l'outil de ligne de commande gcloud :
    gcloud endpoints services deploy api_descriptor.pb api_config.yaml
    

    Lors de la création et de la configuration du service, Service Management envoie des informations au terminal. Une fois le déploiement terminé, un message semblable au suivant s'affiche :

    Service Configuration [CONFIG_ID] uploaded for service [bookstore.endpoints.example-project.cloud.goog]

    CONFIG_ID correspond à l'ID unique de configuration du service Endpoints créé par le déploiement. Exemple :

    Service Configuration [2017-02-13r0] uploaded for service [bookstore.endpoints.example-project.cloud.goog]
    

    Dans l'exemple précédent, 2017-02-13r0 correspond à l'ID de configuration du service et bookstore.endpoints.example-project.cloud.goog au nom du service. L'ID de configuration du service se compose d'un horodatage suivi d'un numéro de révision. Si vous déployez à nouveau la configuration Endpoints le même jour, le numéro de révision est incrémenté dans l'ID de configuration du service.

Vérifier les services requis

Endpoints et ESP requièrent au minimum l'activation des services Google suivants :
Nom Titre
servicemanagement.googleapis.com API Service Management
servicecontrol.googleapis.com API Service Control
endpoints.googleapis.com Google Cloud Endpoints

Dans la plupart des cas, la commande gcloud endpoints services deploy permet d'activer ces services requis. Toutefois, bien que la commande gcloud ait abouti, elle n'active pas les services requis dans les cas suivants :

  • Vous avez utilisé une application tierce telle que Terraform et vous n'incluez pas ces services.

  • Vous avez déployé la configuration Endpoints dans un projet Google Cloud existant dans lequel ces services étaient explicitement désactivés.

Utilisez la commande suivante pour vérifier que les services nécessaires sont activés :

gcloud services list

Si les services requis ne sont pas répertoriés, activez-les :

gcloud services enable servicemanagement.googleapis.com
gcloud services enable servicecontrol.googleapis.com
gcloud services enable endpoints.googleapis.com

Activez également votre service Endpoints :

gcloud services enable ENDPOINTS_SERVICE_NAME

Pour déterminer la valeur de ENDPOINTS_SERVICE_NAME, vous pouvez effectuer l'une des opérations suivantes :

  • Après avoir déployé la configuration Endpoints, accédez à la page Endpoints de Cloud Console. La liste des valeurs ENDPOINTS_SERVICE_NAME possibles s'affiche dans la colonne Nom du service.

  • Pour OpenAPI, ENDPOINTS_SERVICE_NAME correspond à ce que vous avez spécifié dans le champ host de votre spécification OpenAPI. Pour gRPC, ENDPOINTS_SERVICE_NAME correspond à ce que vous avez spécifié dans le champ name de votre configuration Endpoints gRPC.

Pour en savoir plus sur les commandes gcloud, consultez la page Services gcloud.

Si vous recevez un message d'erreur, consultez la page Dépannage du déploiement de la configuration Cloud Endpoints.

Pour en savoir plus, consultez la page Déployer la configuration Endpoints.

Déployer le backend de l'API

Vous avez déployé la configuration de service dans Service Management, mais vous n'avez pas encore déployé le code qui diffuse le backend de l'API. Cette section vous guide dans la création d'un cluster GKE pour héberger le backend de l'API et dans le déploiement de l'API.

Créer un cluster de conteneur

Le cluster nécessite un alias d'adresse IP pour utiliser l'équilibrage de charge natif en conteneurs. Pour créer un cluster de conteneurs avec un alias d'adresse IP pour notre exemple :

gcloud container clusters create espv2-demo-cluster \
    --enable-ip-alias \
    --create-subnetwork="" \
    --network=default \
    --zone=us-central1-a

La commande ci-dessus crée un cluster, espv2-demo-cluster, avec un sous-réseau provisionné automatiquement dans la zone us-central1-a.

Authentifier kubectl sur le cluster de conteneurs

Pour utiliser kubectl afin de créer et gérer des ressources de cluster, vous devez obtenir les identifiants du cluster et les mettre à la disposition de kubectl. Pour ce faire, exécutez la commande suivante, en remplaçant NAME par votre nouveau nom de cluster et ZONE par sa zone de cluster.

gcloud container clusters get-credentials NAME --zone ZONE

Vérifier les autorisations requises

ESP et ESPv2 appellent les services Google qui utilisent IAM pour vérifier si l'identité appelante dispose des autorisations suffisantes pour accéder aux ressources IAM utilisées. L'identité appelante est le compte de service associé qui déploie ESP et ESPv2.

Lorsqu'il est déployé dans un pod GKE, le compte de service associé est le compte de service de nœud. Il s'agit généralement du compte de service Compute Engine par défaut. Veuillez suivre cette recommandation d'autorisation pour choisir un compte de service de nœud approprié.

Si Workload Identity est utilisé, il est possible d'utiliser un compte de service distinct autre que le compte de service de nœud pour communiquer avec les services Google. Vous pouvez créer un compte de service Kubernetes pour que le pod exécute ESP et ESPv2, créer un compte de service Google et associer le compte de service Kubernetes au compte de service Google.

Pour associer un compte de service Kubernetes à un compte de service Google, suivez ces étapes. Ce compte de service Google est le compte de service associé.

Si le compte de service associé est le compte de service Compute Engine par défaut du projet et que la configuration du service de point de terminaison est déployée dans le même projet, le compte de service doit disposer des autorisations suffisantes pour accéder aux ressources IAM. L'étape de configuration des rôles IAM peut être ignorée. Sinon, les rôles IAM suivants doivent être ajoutés au compte de service associé.

Ajoutez les rôles IAM requis :

Cette section décrit les ressources IAM utilisées par ESP et ESPv2, ainsi que les rôles IAM requis pour que le compte de service associé puisse accéder à ces ressources.

Configuration du service de point de terminaison

ESP et ESPv2 appellent Service Control, qui utilise la configuration du service de point de terminaison. Celle-ci est une ressource IAM. ESP et ESPv2 ont besoin du rôle Contrôleur du service pour y accéder.

Le rôle IAM s'applique à la configuration du service de point de terminaison, et non au projet. Un projet peut posséder plusieurs configurations de service de point de terminaison.

Utilisez la commande gcloud suivante pour ajouter le rôle au compte de service associé pour la configuration du service de point de terminaison.

gcloud endpoints services add-iam-policy-binding SERVICE_NAME \
                --member serviceAccount:SERVICE_ACCOUNT_NAME@DEPLOY_PROJECT_ID.iam.gserviceaccount.com \
                --role roles/servicemanagement.serviceController


* SERVICE_NAME est le nom du service de point de terminaison ;
* SERVICE_ACCOUNT_NAME@DEPLOY_PROJECT_ID.iam.gserviceaccount.com est le compte de service associé.

Cloud Trace

ESP et ESPv2 appellent le service Cloud Trace pour exporter Trace vers un projet. Ce projet est appelé projet de traçage. Dans ESP, le projet de traçage et le projet propriétaire de la configuration du service de point de terminaison sont identiques. Dans ESPv2, le projet de traçage peut être spécifié par l'option --tracing_project_id, et est défini par défaut sur le projet de déploiement.

ESP et ESPv2 nécessitent le rôle Agent Cloud Trace pour activer Cloud Trace.

Exécutez la commande gcloud suivante pour ajouter le rôle au compte de service associé :

gcloud projects add-iam-policy-binding TRACING_PROJECT_ID \
                --member serviceAccount:SERVICE_ACCOUNT_NAME@DEPLOY_PROJECT_ID.iam.gserviceaccount.com \
                --role roles/cloudtrace.agent


* TRACING_PROJECT_ID est l'ID du projet de traçage ;
* SERVICE_ACCOUNT_NAME@DEPLOY_PROJECT_ID.iam.gserviceaccount.com est le compte de service associé. Pour en savoir plus, consultez la page Que sont les rôles et les autorisations ?

Configurer vos clés et certificats SSL

L'équilibrage de charge natif en conteneurs utilise l'équilibrage de charge HTTP2, qui doit être chiffré par TLS. Cela nécessitait le déploiement d'un certificat TLS sur l'entrée GKE et sur ESPv2. Vous pouvez utiliser votre propre certificat ou utiliser un certificat autosigné.

  1. Créez un certificat et une clé autosignés avec openssl. Assurez-vous d'avoir saisi le même nom de domaine complet bookstore.endpoints.MY_PROJECT_ID.cloud.goog lorsque le "Nom commun (CN)" vous est demandé. Ce nom est utilisé par les clients pour valider le certificat du serveur.

    openssl req -x509 -nodes -days 365 -newkey rsa:2048 \
    -keyout ./server.key -out ./server.crt
  2. Créez un secret Kubernetes contenant la clé et le certificat SSL. Notez que le certificat est copié à deux emplacements, server.crt et tls.crt, car le secret est fourni à la fois à l'entrée GKE et à ESPv2. L'entrée GKE recherche le chemin d'accès du certificat tls.crt, et ESPv2 recherche le chemin d'accès du certificat server.crt.

    kubectl create secret generic esp-ssl \
    --from-file=server.crt=./server.crt --from-file=server.key=./server.key \
    --from-file=tls.crt=./server.crt --from-file=tls.key=./server.key

Déployer les exemples d'API et d'ESPv2 bêta sur le cluster

Pour déployer l'exemple de service gRPC sur le cluster afin que les clients puissent l'utiliser :

  1. git clone ce dépôt et ouvrez le fichier manifeste de déploiement grpc-bookstore.yaml pour le modifier.
  2. Remplacez SERVICE_NAME par le nom de votre service de points de terminaison pour l'entrée et le conteneur ESPv2. Il s'agit du nom que vous avez configuré dans le champ name du fichier api_config.yaml.
    # Copyright 2016 Google Inc.
    #
    # Licensed under the Apache License, Version 2.0 (the "License");
    # you may not use this file except in compliance with the License.
    # You may obtain a copy of the License at
    #
    #     http://www.apache.org/licenses/LICENSE-2.0
    #
    # Unless required by applicable law or agreed to in writing, software
    # distributed under the License is distributed on an "AS IS" BASIS,
    # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    # See the License for the specific language governing permissions and
    # limitations under the License
    
    # Use this file to deploy the container for the grpc-bookstore sample
    # and the container for the Extensible Service Proxy (ESP) to
    # Google Kubernetes Engine (GKE).
    
    apiVersion: networking.k8s.io/v1beta1
    kind: Ingress
    metadata:
      name: esp-grpc-bookstore
      annotations:
        kubernetes.io/ingress.class: "gce"
        kubernetes.io/ingress.allow-http: "false"
    spec:
      tls:
      - hosts:
        - SERVICE_NAME
        secretName: esp-ssl
      backend:
        serviceName: esp-grpc-bookstore
        servicePort: 443
    ---
    apiVersion: cloud.google.com/v1
    kind: BackendConfig
    metadata:
      name: esp-grpc-bookstore
    spec:
      healthCheck:
        type: HTTP2
        requestPath: /healthz
        port: 9000
    ---
    apiVersion: v1
    kind: Service
    metadata:
      name: esp-grpc-bookstore
      annotations:
        service.alpha.kubernetes.io/app-protocols: '{"esp-grpc-bookstore":"HTTP2"}'
        cloud.google.com/neg: '{"ingress": true, "exposed_ports": {"443":{}}}'
        cloud.google.com/backend-config: '{"default": "esp-grpc-bookstore"}'
    spec:
      ports:
      # Port that accepts gRPC and JSON/HTTP2 requests over TLS.
      - port: 443
        targetPort: 9000
        protocol: TCP
        name: esp-grpc-bookstore
      selector:
        app: esp-grpc-bookstore
      type: ClusterIP
    ---
    apiVersion: apps/v1
    kind: Deployment
    metadata:
      name: esp-grpc-bookstore
    spec:
      replicas: 1
      selector:
        matchLabels:
          app: esp-grpc-bookstore
      template:
        metadata:
          labels:
            app: esp-grpc-bookstore
        spec:
          volumes:
          - name: esp-ssl
            secret:
              secretName: esp-ssl
          containers:
          - name: esp
            image: gcr.io/endpoints-release/endpoints-runtime:2
            args: [
              "--listener_port=9000",
              "--service=SERVICE_NAME",
              "--rollout_strategy=managed",
              "--backend=grpc://127.0.0.1:8000",
              "--healthz=/healthz",
              "--ssl_server_cert_path=/etc/esp/ssl",
            ]
            ports:
              - containerPort: 9000
            volumeMounts:
            - mountPath: /etc/esp/ssl
              name:  esp-ssl
              readOnly: true
          - name: bookstore
            image: gcr.io/endpointsv2/python-grpc-bookstore-server:1
            ports:
              - containerPort: 8000
    

    L'option --rollout_strategy=managed configure ESPv2 afin d'utiliser la dernière configuration de service déployée. Si cette option est spécifiée, une minute après le déploiement d'une nouvelle configuration de service, ESPv2 détecte la modification et commence à l'utiliser automatiquement. Nous vous recommandons de spécifier cette option plutôt que de fournir un ID de configuration spécifique à utiliser avec ESPv2. Pour en savoir plus sur les arguments d'ESPv2, consultez la page Options de démarrage d'ESPv2.

    Exemple :

        spec:
          containers:
          - name: esp
            image: gcr.io/endpoints-release/endpoints-runtime:2
            args: [
              "--listener_port=9000",
              "--service=bookstore.endpoints.example-project-12345.cloud.goog",
              "--rollout_strategy=managed",
              "--backend=grpc://127.0.0.1:8000"
            ]
    
  3. Démarrez le service :
    kubectl create -f grpc-bookstore.yaml
    

Si vous recevez un message d'erreur, reportez-vous à la page Dépannage de Cloud Endpoints dans GKE.

Obtenir l'adresse IP externe du service

L'adresse IP externe du service est nécessaire pour envoyer des demandes à l'exemple d'API. Une fois que vous avez démarré le service dans le conteneur, la préparation de l'adresse IP externe peut prendre quelques minutes.

  1. Affichez l'adresse IP externe :

    kubectl get ingress

  2. Notez la valeur de EXTERNAL-IP et enregistrez-la dans une variable d'environnement SERVER_IP. L'adresse IP externe est utilisée pour envoyer des requêtes à l'exemple d'API.

    export SERVER_IP=YOUR_EXTERNAL_IP
    

Envoyer une requête à l'API

Pour envoyer des requêtes à l'exemple d'API, vous pouvez utiliser un exemple de client gRPC écrit en Python.

  1. Clonez le dépôt Git dans lequel le code client gRPC est hébergé :

    git clone https://github.com/GoogleCloudPlatform/python-docs-samples.git
       

  2. Modifiez votre répertoire de travail :

    cd python-docs-samples/endpoints/bookstore-grpc/
      

  3. Installez les dépendances :

    pip install virtualenv
    virtualenv env
    source env/bin/activate
    python -m pip install -r requirements.txt
    

  4. Créer une autorité de certification racine pour le certificat autosigné

    openssl x509 -in server.crt -out client.pem -outform PEM
      

  5. Envoyez une requête à l'exemple d'API :

    python bookstore_client.py --host SERVER_IP --port 443 \
    --servername bookstore.endpoints.MY_PROJECT_ID.cloud.goog --use_tls true --ca_path=client.pem
    

Si vous ne recevez pas de réponse positive, consultez la page Dépanner des erreurs de réponse.

Vous venez de déployer et de tester une API dans Endpoints.

Effectuer un nettoyage

Pour éviter que les ressources utilisées lors de ce tutoriel soient facturées sur votre compte Google Cloud, supprimez le projet contenant les ressources, ou conservez le projet et supprimez les ressources individuelles.

  1. Supprimez l'API :

    gcloud endpoints services delete SERVICE_NAME
    

    Remplacez SERVICE_NAME par le nom de votre API.

  2. Supprimez le cluster GKE :

    gcloud container clusters delete NAME --zone ZONE
    

Étapes suivantes