RousselTMLEARNING

Observabilité

Tracer un RAG et un agent avec OpenInference et Phoenix

Instrumenter une application RAG et un agent : spans RETRIEVER, RERANKER, TOOL et AGENT, sessions de conversation, métadonnées de version, et diagnostic des mauvaises réponses à partir des traces.

1. Un RAG se diagnostique étape par étape #

La plupart des mauvaises réponses viennent de la recherche.

Les étapes #

Étapes d'un RAG dans une trace
Mauvaise réponse due à...Ce que montre la traceCorrection
Documents non pertinentsSpan RETRIEVER : les passages ne parlent pas du sujetDécoupage, embeddings, filtres, recherche hybride
Bon document mal classéScore faible, document en 5e positionReranker, nombre de documents
Bon contexte, mauvaise réponseSpan LLM : la réponse contredit le contextePrompt, modèle, température
Contexte tronquéJetons d'entrée au maximumMoins de documents, passages plus courts

2. Instrumenter un RAG maison #

Quand aucun framework ne le fait pour vous.

Code #

from opentelemetry import trace
from openinference.semconv.trace import SpanAttributes, OpenInferenceSpanKindValues as Kind

tracer = trace.get_tracer("faq-rag")

def answer(question: str) -> str:
    with tracer.start_as_current_span("faq-rag") as root:
        root.set_attribute(SpanAttributes.OPENINFERENCE_SPAN_KIND, Kind.CHAIN.value)
        root.set_attribute(SpanAttributes.INPUT_VALUE, question)
        docs = retrieve(question)                       # span RETRIEVER (voir l'article OpenInference)
        context = "\n".join(d.text for d in docs)
        r = client.chat.completions.create(            # span LLM créé automatiquement
            model=model,
            messages=[{"role": "system", "content": "Réponds uniquement à partir du contexte :\n" + context},
                      {"role": "user", "content": question}])
        text = r.choices[0].message.content
        root.set_attribute(SpanAttributes.OUTPUT_VALUE, text)
        return text
À savoir : Le span racine de type CHAIN porte la question et la réponse finale : c'est lui que l'on évaluera, et c'est lui que l'on exportera vers un dataset.

3. Les agents #

Des traces plus profondes.

Ce qu'il faut voir #

  • Chaque tour de l'agent : l'appel LLM qui décide, l'outil choisi et ses arguments (tool_call.function.arguments), le résultat de l'outil.
  • Les boucles : un agent qui appelle dix fois le même outil coûte cher et répond lentement.
  • Les erreurs d'outils : un span TOOL en erreur que l'agent a ignoré.

Les frameworks d'agents (OpenAI Agents SDK, LangGraph via LangChain, CrewAI, smolagents) ont leur instrumentation OpenInference : auto_instrument=True suffit si le paquet est installé.

Bonne Pratique : Mesurez le nombre de spans TOOL par trace : une hausse soudaine après un changement de prompt révèle souvent un agent qui tourne en rond.

4. Sessions et conversations #

Relier les échanges.

Sessions #

from openinference.instrumentation import using_session

with using_session(session_id=conversation_id):
    reply = answer(question)

Phoenix regroupe alors les traces d'une même conversation : on relit un échange complet, tour par tour, et l'on voit à quel moment il a déraillé.

Articles liés

Arize AI : observabilité et évaluation des applications LLM et des agents

Comprendre Arize AI : Phoenix (open source) et Arize AX (plateforme), traces OpenInference, évaluations par L…

OpenInference : les conventions OpenTelemetry pour tracer les applications d'IA

Guide détaillé d'OpenInference : conventions sémantiques et instrumentations OpenTelemetry pour LLM, RAG et a…

Installer Phoenix et tracer sa première application LLM

Installer Arize Phoenix (pip, Docker), envoyer ses premières traces OpenInference depuis une application Open…

Pour aller plus loin