Accueil / Articles

Agent conversationnel BigQuery sur Vertex AI avec Google ADK : six pièges

Créez un agent BigQuery en langage naturel à l’aide de Google ADK et Gemini, déployez-le dans le Vertex AI Agent Engine, et évitez les pièges liés à Python, aux dépendances, à la facturation et à IAM.

Éditeur : REACTAPP.TOP10 min de lecture2389 mots

Sources: Building a BigQuery Conversational Agent on Vertex AI with ADK and the traps nobody warns you about

Le problème : des questions simples bloquées dans une file d’attente

Les équipes commerciales ont constamment besoin de chiffres déjà disponibles dans le data warehouse. Combien de commandes ont été expédiées le mois dernier ? Quel produit se vend le mieux ? Chaque question se transforme en ticket, puis en extraction manuelle, suivie d’échanges interminables qui peuvent durer des heures ou des jours, alors que la réponse se trouve à quelques clics de requête dans BigQuery.

L’alternative est un agent conversationnel. L’utilisateur tape sa question en anglais simple, l’agent génère lui-même la requête SQL, la lance contre BigQuery et renvoie le résultat. Pas de ticket, pas d’extraction, aucune compétence en SQL requise. Faire fonctionner cela sur un ordinateur portable est la partie facile. Le déploiement correct dans Google Cloud est là que apparaissent les problèmes cachés, notamment des conflits de version de Python, des dépendances non déclarées et une surprise liée à IAM qui ne se manifeste qu’une fois que l’agent est exécuté dans le cloud.

La pile technique de cette compilation se compose de quatre éléments :

  • Google ADK, le framework Agent Development Kit qui orchestre l’agent.
  • Gemini 2.5 Flash sur Vertex AI en tant que moteur de raisonnement.
  • L’ensemble d’outils BigQuery fourni par ADK pour examiner les schémas et exécuter des requêtes SQL.
  • Vertex AI Agent Engine, l’environnement d’exécution géré utilisé pour le déploiement.

Mise en place du projet

Un projet Python frais avec ADK installé constitue la base ; en théorie, cela nécessite trois commandes : créer un environnement virtuel, l’activer et installer le paquet avec pip.

python3 -m venv .venv
source .venv/bin/activate
pip install google-adk

Piège 1 : la version de Python. ADK nécessite Python 3.10 ou une version plus récente. Un Mac qui utilise encore le Python système 3.9 semble fonctionner normalement jusqu’au démarrage de l’agent, après quoi il affiche de nombreux messages FutureWarning, suivis d’une erreur fatale indiquant que MCP exige Python 3.10 ou une version supérieure. Sur macOS, évitez tout conflit avec l’interpréteur système et installez une version propre via Homebrew, comme indiqué dans la section suivante.

brew install python@3.12
python3.12 -m venv .venv
source .venv/bin/activate
pip install --upgrade pip
pip install google-adk

Vérifiez le résultat avec python --version ; vous devez obtenir la version 3.12.x, et assurez-vous que l’invite de shell commence par (.venv). Ensuite, générez le squelette de l’agent à l’aide de la ligne de commande ADK.

adk create bq_agent_app

Piège 2 : noms de dossiers. Le dossier de l’agent doit être un identifiant Python valide, c’est-à-dire qu’il ne peut contenir que des lettres, des chiffres et des underscores. Un nom contenant des tirets comme bq-agent-app provoque l’échec du déploiement avec une erreur Invalid agent name. La forme utilisant des underscores, bq_agent_app, fonctionne. Il s’agit d’un détail mineur qui peut facilement faire perdre dix minutes.

Tout l’agent dans un seul fichier

C’est là que ADK se révèle utile. La logique qui nécessiterait normalement des centaines de lignes de code d’orchestration tient dans un seul fichier déclaratif. Le fichier commence par des importations pour l’authentification Google, la classe Agent, l’ensemble d’outils BigQuery ainsi que leurs classes de configuration des identifiants et des outils.

import google.auth
from google.adk.agents import Agent
from google.adk.tools.bigquery import BigQueryToolset, BigQueryCredentialsConfig
from google.adk.tools.bigquery.config import BigQueryToolConfig

Le reste réutilise les identifiants par défaut de l’application, crée la configuration des identifiants, configure l’ensemble d’outils et définit l’agent lui-même, y compris son modèle, ses instructions et son filtre d’outils.

# Reuse your Application Default Credentials
application_default_credentials, project = google.auth.default()
credentials_config = BigQueryCredentialsConfig(
    credentials=application_default_credentials
)# Google's first-party BigQuery toolset
bigquery_toolset = BigQueryToolset(
    credentials_config=credentials_config,
    bigquery_tool_config=BigQueryToolConfig(
        compute_project_id="your-project-id",  # bills the query jobs
    ),
    tool_filter=[
        "list_dataset_ids",
        "get_dataset_info",
        "list_table_ids",
        "get_table_info",
        "execute_sql",
    ],
)root_agent = Agent(
    model="gemini-2.5-flash",
    name="bq_data_assistant",
    description="Answers natural-language questions over BigQuery data.",
    instruction=(
        "You are a data assistant for business teams. "
        "When asked a question, first inspect the schema of the relevant "
        "tables (get_table_info) BEFORE writing any SQL, so you use real "
        "column names and never invent them. "
        "You always run your query jobs in the configured billing project, "
        "but you CAN read data from any accessible dataset, including public "
        "ones. Reading a public dataset from your billing project is normal "
        "and allowed, never refuse for that reason. "
        "Write standard BigQuery SQL, execute it with execute_sql, then "
        "return a clear answer with the number and, in one line, the query used. "
        "If a question is ambiguous, ask for clarification before running."
    ),
    tools=[bigquery_toolset],
)

Trois éléments clés dans ce fichier représentent véritablement l’idée d’un agent.

Tout d’abord, la réflexion et l’action sont séparées. Gemini s’occupe du raisonnement, mais il ne dispose pas de connaissances sur vos données et n’a aucun accès à BigQuery. Le BigQueryToolset fournit les outils que le modèle peut choisir d’utiliser, tels que vérifier un schéma ou exécuter une requête. Tout se déroule en boucle : le modèle examine la question, choisit un outil, ADK l’exécute, les résultats reviennent, et le modèle choisit sa prochaine action jusqu’à ce qu’il puisse répondre. Cette boucle constitue la frontière entre un agent et un chatbot. Un chatbot parle, tandis qu’un agent agit sur vos systèmes au sein d’un cycle contrôlé.

Deuxièmement, l’instruction constitue le levier principal. La ligne indiquant à l’agent d’examiner le schéma avant d’écrire du SQL est ce qui l’empêche de créer des noms de colonnes au hasard. Le comportement est déterminé par la prompt, et non par du code, ce qui est plus important qu’il n’y paraît au premier abord.

Troisièmement, tool_filter représente le mécanisme de contrôle basé sur les moindres privilèges, ne mettant à disposition que les outils dont l’agent a réellement besoin. Pour un usage en production avec des données sensibles, il convient de le configurer en mode lecture seule afin que l’agent puisse exécuter des requêtes sans pouvoir modifier quoi que ce soit.

Lancement local

ADK propose deux façons de lancer un agent. adk run bq_agent_app ouvre une conversation en terminal simple, tandis que adk web démarre une interface web locale comprenant une zone de chat ainsi qu’une zone Événements listant chaque appel à un outil. L’interface web est plus agréable, mais adk run est le choix préférable pour le débogage, car il affiche les erreurs ouvertement au lieu de provoquer des échecs silencieux.

Piège 3 : dépendances jamais déclarées par l’ensemble d’outils

Des problèmes surviennent à ce stade, et celui-ci entraîne le plus d’échanges. L’ensemble d’outils BigQuery est présenté comme intégré à ADK, pourtant il dépend en silence de paquets que google-adk ne installe pas. La première exécution échoue avec ModuleNotFoundError: No module named 'google.cloud'. L’installation de google-cloud-bigquery provoque un autre échec, cannot import name 'dataplex_v1', suivi d’une demande concernant db-dtypes. Ce sont donc trois échecs consécutifs, chacun causé par un paquet que l’ensemble d’outils suppose mais ne liste jamais.

La solution consiste à installer les trois paquets au préalable afin d’éviter ce cycle infini.

pip install google-cloud-bigquery google-cloud-dataplex db-dtypes

Puis lancez l’interface utilisateur web.

adk web

Ouvrez l’URL locale, sélectionnez l’agent et posez-lui une question simple pour vérifier le système de plomberie.

List the tables in bigquery-public-data.thelook_ecommerce

Les données de test sont thelook_ecommerce, un ensemble de données de e-commerce synthétique publié ouvertement par Google. Les clients, les produits et les commandes en font un excellent choix pour un agent capable de répondre à des questions commerciales, sans qu’aucune donnée réelle ne soit impliquée. Si la liste des tables s’affiche, la configuration fonctionne correctement. Surveillez le panneau des Événements, où l’agent enchaîne les commandes get_table_info puis execute_sql. Ce panneau offre la vision la plus claire du comportement de l’agent et fonctionne très bien lors des démonstrations.

Piège 4 : le projet de facturation

Lorsque les éléments de base sont confirmés, essayez une question réelle.

What is the most sold product?

L’agent refuse poliment. Il indique qu’il n’a pas l’autorisation de créer des tâches dans le projet bigquery-public-data, puis montre le SQL qu’il aurait exécuté et demande à être orienté vers un projet où il dispose de droits. Il s’agit apparemment d’une mauvaise configuration, mais ce n’est pas le cas. Il s’agit d’un concept de BigQuery qui devient évident avec du recul mais qui embrouille presque tout le monde au début.

bigquery-public-data est un projet en lecture seule appartenant à Google. Vous pouvez lire ses tables, mais vous ne pouvez pas y exécuter de requêtes, car l’exécution d’une requête crée une tâche et cette tâche doit être facturée à un projet où vous avez des droits. Google ne permet à personne de facturer les coûts de calcul sur son projet. La lecture des données et l’exécution d’une requête sont donc deux actions distinctes liées à deux projets différents : l’un contient les données et l’autre paie pour le calcul.

Cette correction indique à l’ensemble d’outils de exécuter les tâches dans votre propre projet tout en continuant à lire depuis l’ensemble de données public. La valeur correspondante est compute_project_id, et elle se trouve dans BigQueryToolConfig, qui doit d’abord être importé.

from google.adk.tools.bigquery.config import BigQueryToolConfig

Ensuite, l’ensemble d’outils est construit avec cette configuration, accompagnée d’un commentaire indiquant quels jobs s’exécutent et sont facturés dans votre projet.

bigquery_toolset = BigQueryToolset(
    credentials_config=credentials_config,
    bigquery_tool_config=BigQueryToolConfig(
        compute_project_id="your-project-id",  # jobs run and bill here
    ),
    tool_filter=[...],
)

Après un nouveau déploiement, une deuxième paroi apparaît, plus intéressante encore. L’agent sait désormais comment facturer votre projet, mais il en conclut qu’il ne peut absolument pas lire l’ensemble de données public et refuse à nouveau. Cette fois, il se trompe, car lire un ensemble de données public depuis son propre projet de facturation est normal et autorisé. L’agent était simplement trop prudent.

C’est là que revient l’idée de l’utiliser instruction comme levier. Le problème réside dans la consigne, et non dans le code, car l’agent a déduit une règle qui n’existe pas. Une phrase explicite dans les instructions suffit à résoudre le problème : elle stipule que les tâches de requête s’exécutent toujours dans le projet de facturation configuré, que les données provenant de tout ensemble de données accessible, y compris ceux qui sont publics, peuvent être lues, et que lire un ensemble de données public depuis le projet de facturation est normal et ne doit jamais être une raison de refus.

Après un autre déploiement, l’agent examine le schéma, écrit l’opération de jointure, la met en œuvre et renvoie le meilleur produit ainsi que la requête utilisée. Cet exemple montre qu’un agent peut disposer des droits techniques adéquats et malgré tout se comporter de manière inappropriée en raison d’une instruction ambiguë. Une formulation précise des instructions fait partie intégrante de l’ingénierie dans ce contexte, et non d’une compétence secondaire.

Déploiement dans l’Agent Engine

Exécuter quelque chose sur un ordinateur portable, c’est une chose ; mais c’est sur l’infrastructure de Google que l’agent devient véritablement opérationnel. Vertex AI Agent Engine est un environnement d’exécution géré conçu spécialement pour les agents ADK : vous lui transmettez l’agent, et Google s’en occupe, en gère l’échelle et le maintient en fonctionnement sans qu’il soit nécessaire de gérer de serveur.

Le déploiement commence par activer quelques API et créer un bucket de préparation où ADK place le code empaqueté.

gcloud services enable aiplatform.googleapis.com storage.googleapis.com
gcloud storage buckets create gs://your-project-id-adk-staging --location=us-central1

Vient ensuite la commande de déploiement, qui prend en compte le projet, la région et le bucket de préparation.

adk deploy agent_engine \
  --project=your-project-id \
  --region=us-central1 \
  --staging_bucket=gs://your-project-id-adk-staging \
  bq_agent_app

Cela prend quelques minutes car un conteneur est créé en arrière-plan, et le prochain piège se trouve à l’intérieur de ce conteneur.

Piège 5 : le conteneur ne sait rien de votre ordinateur portable

La première exécution d’Agent Engine se termine par une panne, avec exactement la même erreur cannot import name 'dataplex_v1' que l’on croyait résolue. Une déploiement ne peut pas voir ce qui est installé sur l’ordinateur d’un développeur. Il ne connaît que les paquets mentionnés dans un fichier requirements.txt placé à l’intérieur du dossier de l’agent. Ainsi, l’ordinateur portable contenait les dépendances tandis que le conteneur ne les possédait pas. Cette leçon s’applique à tous les services GCP, qu’il s’agisse de Cloud Functions, de Cloud Run ou d’Agent Engine. Fonctionner localement et fonctionner en production sont deux situations différentes, et une liste explicite des dépendances relie les deux.

La solution consiste à énumérer clairement les paquets nécessaires.

# requirements.txt
google-adk
google-cloud-bigquery
google-cloud-dataplex
db-dtypes

Redéployez, et le conteneur installe ce dont il a besoin.

Piège 6 : l’agent n’est plus vous

Le dernier piège nous apprend le plus de choses sur les agents en environnement de production. Le déploiement réussit, mais une requête saisie dans le cloud Playground est rejetée par BigQuery faute de la permission bigquery.jobs.create. Ce n’est pas une erreur : c’est IAM qui fonctionne comme conçu.

Au niveau d’un ordinateur portable, l’agent agissait en votre nom, utilisant toutes vos permissions. Après déploiement, il fonctionne sous un compte de service, essentiellement une identité robotique, et cette identité ne dispose initialement d’aucun droit sur BigQuery. C’est ce principe qui rend les agents sûrs lorsqu’ils sont en contact avec des données sensibles. Un agent ne peut pas dépasser les limites fixées par son identité, rien n’est caché, et IAM le restreint tout comme il le fait pour toute personne.

Le compte de service a besoin de deux rôles : l’un pour exécuter des requêtes et l’autre pour lire des données. Le premier bloc accorde le rôle roles/bigquery.jobUser.

gcloud projects add-iam-policy-binding your-project-id \
  --member="serviceAccount:SERVICE_ACCOUNT_EMAIL" \
  --role="roles/bigquery.jobUser"

Le deuxième accorde le rôle roles/bigquery.dataViewer.

gcloud projects add-iam-policy-binding your-project-id \
  --member="serviceAccount:SERVICE_ACCOUNT_EMAIL" \
  --role="roles/bigquery.dataViewer"

Attendez une minute que le changement se propage, puis essayez à nouveau dans l’Environnement de développement. L’agent répond ensuite depuis le cloud, fonctionnant entièrement sur l’infrastructure de Google, tandis que l’ordinateur portable reste fermé.

Leçons tirées de ce processus

  • Un agent n’est pas un chatbot. La différence réside dans la boucle par laquelle le modèle raisonne, appelle un outil, consulte le résultat et répète l’opération jusqu’à pouvoir répondre.
  • L’instruction effectue la majeure partie du travail réel. Un code et des droits d’accès identiques produisent des comportements très différents en fonction de la formulation de l’instruction ; éliminer les noms de colonnes inventés et les refus inutiles relevait entièrement d’une bonne rédaction de l’instruction.
  • Le fait que quelque chose soit intégré ne garantit pas qu’il soit installé. L’ensemble d’outils BigQuery arrive avec ADK, mais dépend de google-cloud-bigquery, google-cloud-dataplex et db-dtypes ; il faut donc les installer en premier.
  • Le mode local et le mode production sont deux mondes distincts. En mode local, l’agent s’exécute sous votre identité avec vos paquets. Une fois déployé, il fonctionne sous un compte de service ne disposant que des éléments listés dans requirements.txt, et ces écarts sont explicitement comblés.
  • IAM constitue la garantie de sécurité. Un agent déployé ne peut pas dépasser les droits de son compte de service, ce qui fait que chaque accès est explicite, traçable et révocable, tout comme pour un utilisateur humain. C’est la assurance dont a besoin un partenaire d’affaires avant d’autoriser un agent à accéder à des données réelles.

Un projet qui commence par une question sur la manière d’obtenir des réponses en langage naturel à partir de BigQuery se termine par un agent Vertex AI entièrement déployé, capable de répondre aux questions métier sans utiliser de SQL ni d’extraction manuelle. Tout cela fait partie intégrante de GCP, ce qui signifie qu’une équipe déjà utilisant BigQuery n’a pas besoin d’adopter un nouveau stack, mais simplement d’intégrer Gemini aux outils qu’elle utilise déjà. Les tutoriels ne mentionnent aucune de ces pièges : la version Python, les dépendances non déclarées, la confusion entre projets de facturation et l’account de service sans droits. Connaître les failles permet d’économiser des heures ; commencez donc petit, testez diverses configurations et lisez les erreurs qui apparaissent.

Lectures complémentaires

  • Un agent analyste BigQuery auto-réparateur grâce à Google ADK et aux mécanismes de vérification des coûts en mode essai — Comment un agent ADK conscient du schéma utilise le stockage en mémoire contextuelle de Vertex AI, des protections limitées aux requêtes SELECT, des vérifications de coûts en mode essai ainsi qu’un cycle SQL auto-corrigé pour répondre aux questions relatives à un lakehouse 360° du client.