Évaluer les interactions individuelles à partir de modèles et d’agents déployés avec Microsoft SDK Foundry

Important

Les éléments indiqués comme (aperçu) dans cet article sont en aperçu public. Cette version préliminaire est fournie sans contrat de niveau de service, et nous la déconseillons pour les charges de travail en production. Certaines fonctionnalités peuvent ne pas être prises en charge ou avoir des fonctionnalités contraintes. Pour plus d’informations, consultez Conditions d'utilisation supplémentaires pour les versions préliminaires de Microsoft Azure.

Évaluez les réponses stockées ou les traces OpenTelemetry à partir des agents et des modèles déployés sans relire les requêtes d’origine.

Prerequisites

  • Remplissez les conditions préalables à l’évaluation cloud et la configuration du client.
  • Les identifiants de réponse stockés pour l’évaluation des réponses, ou une ressource Application Insights connectée à votre projet Foundry pour l’évaluation des traces.
  • Les étendues OpenTelemetry qui répondent aux exigences relatives aux données de traçage lors de l’évaluation des traces.

Les exemples utilisent le client sdk configuré dans Configurer le client sdk.

Évaluer les interactions par ID de réponse

Récupérez et évaluez les réponses de l’agent Foundry par ID de réponse à l’aide du azure_ai_responses type de source de données. Utilisez ce scénario pour évaluer des interactions d’agent spécifiques après qu’ils se produisent.

Tip

Avant de commencer, effectuez la configuration du client.

Un ID de réponse est un identificateur unique retourné chaque fois qu’un agent Foundry génère une réponse. Vous pouvez collecter des ID de réponse à partir d’interactions de l’agent à l’aide de l’API Réponses ou des journaux de trace de votre application. Fournissez les identifiants directement comme contenu du fichier.

Important

Les évaluations de réponse de l’agent (azure_ai_responses) prennent uniquement en charge file_content pour la fourniture d’ID de réponse. Le file_id type source n’est pas pris en charge et retourne une 400 Bad Request erreur.

Collecter les ID de réponse

Chaque appel à l’API Réponses retourne un objet de réponse avec un champ unique id . Collectez ces ID à partir des interactions de votre application ou générez-les directement :

# Generate response IDs by calling a model through the Responses API
response = openai_client.responses.create(
    model=model_deployment_name,
    input="What is machine learning?",
)
print(response.id)  # Example: resp_abc123

Vous pouvez également collecter des ID de réponse à partir des interactions de l'agent dans les journaux de traces ou dans la chaîne de surveillance de votre application. Chaque ID de réponse identifie de manière unique une réponse stockée que le service d’évaluation peut récupérer.

Créer une évaluation et exécuter

from azure.ai.projects.models import TestingCriterionAzureAIEvaluator

data_source_config = {"type": "azure_ai_source", "scenario": "responses"}

testing_criteria = [
    TestingCriterionAzureAIEvaluator(
        type="azure_ai_evaluator",
        name="coherence",
        evaluator_name="builtin.coherence",
        initialization_parameters={"model": model_deployment_name},
    ),
    TestingCriterionAzureAIEvaluator(
        type="azure_ai_evaluator",
        name="violence",
        evaluator_name="builtin.violence",
    ),
]

eval_object = openai_client.evals.create(
    name="Agent Response Evaluation",
    data_source_config=data_source_config,
    testing_criteria=testing_criteria,
)

data_source = {
    "type": "azure_ai_responses",
    "item_generation_params": {
        "type": "response_retrieval",
        "data_mapping": {"response_id": "{{item.resp_id}}"},
        "source": {
            "type": "file_content",
            "content": [
                {"item": {"resp_id": "resp_abc123"}},
                {"item": {"resp_id": "resp_def456"}},
            ]
        },
    },
}

eval_run = openai_client.evals.runs.create(
    eval_id=eval_object.id,
    name="agent-response-evaluation",
    data_source=data_source,
)

Pour obtenir un exemple exécutable complet, consultez sample_agent_response_evaluation.py sur GitHub. Pour vérifier si l’opération est terminée et interpréter les résultats, consultez Obtenir les résultats de l’évaluation dans le cloud.

Évaluer les traces (aperçu)

Évaluez les interactions de l’agent que Application Insights a déjà capturées. Utilisez le type de azure_ai_traces source de données. Ce scénario est utile pour l’évaluation post-déploiement du trafic de production réel. Vous sélectionnez des traces à partir de votre pipeline de supervision et exécutez des évaluateurs sur ces derniers sans relire les requêtes.

Important

L’évaluation des traces est l’approche recommandée pour évaluer les agents non conçus avec Microsoft Foundry Agent Service, y compris LangChain et les frameworks personnalisés. Tant que votre agent émet des spans OpenTelemetry conformes aux conventions sémantiques GenAI vers Application Insights, l’évaluation des traces peut évaluer ses interactions à l’aide des mêmes évaluateurs que ceux disponibles pour les agents Foundry.

L’évaluation de trace prend en charge deux modes :

  • Par ID de trace : évaluez des interactions d’agent spécifiques en fournissant leurs operation_Id valeurs à partir d’Application Insights.
  • Par filtre d’agent : détectez et évaluez automatiquement les traces récentes pour un agent donné, sans collecter manuellement les ID de trace.

Tip

Avant de commencer, effectuez la configuration du client. Ce scénario nécessite également une ressource Application Insights connectée à votre projet Foundry.

Échantillonnage intelligent

L’évaluation de trace prend en charge l’échantillonnage intelligent, qui sélectionne un sous-ensemble représentatif de traces pour l’évaluation au lieu d’évaluer chaque trace capturée. Activez le bouton bascule Échantillonnage intelligent sur le portail Foundry lorsque vous configurez une exécution d’évaluation des traces. L’échantillonnage intelligent réduit le coût d’évaluation tout en préservant la diversité des traces , en garantissant que les cas de périphérie, les chemins d’erreur et les modèles de conversation variés sont inclus dans l’ensemble évalué.

Fonctionnement de l’échantillonnage intelligent

L’algorithme d’échantillonnage utilise une approche de diversification « farthest-first » fondée sur MinHash, qui se déroule en plusieurs étapes :

  1. Déduplication exacte : supprime les traces dupliquées du pool.
  2. Filtres durs : supprime les sessions interrompues, les traces tronquées et les appels d’outils mal formés qui ne conviennent pas à l’évaluation.
  3. Agrégation : combine les signaux au niveau de la trace dans une représentation unifiée.
  4. MinHash farthest-first selection - Calcule les hachages sensibles à la localité (signatures MinHash) du texte utilisateur pour estimer la similarité entre les traces, puis sélectionne de manière itérative la trace la plus dissimilante du pool restant. Chaque choix successif optimise la distance de toutes les traces précédemment sélectionnées.

Cette approche produit une diversité lexicale beaucoup plus élevée et une couverture de vocabulaire plus large par rapport à l’échantillonnage aléatoire, ce qui signifie que l’ensemble évalué représente mieux la gamme complète d’interactions de l’agent , y compris des cas rares, difficiles et nouveaux que l’échantillonnage aléatoire a tendance à manquer.

L’échantillonnage intelligent est particulièrement efficace pour :

  • Évaluation et benchmarks : optimise la couverture de la distribution des entrées afin que les scores d’évaluation reflètent la diversité réelle.
  • Génération de rubriques : produit des rubriques plus ciblées et exploitables en exposant divers modèles de conversation.
  • Ajustement de la curation du jeu de données : sélectionne les traces qui aident les modèles à apprendre plus efficacement.

L’algorithme s’exécute entièrement sur le calcul local sans appel d’API supplémentaire. Il n’entraîne donc pas de coûts supplémentaires d’inférence de modèle au-delà de l’évaluation elle-même.

Exemple d’échantillonnage intelligent

# Eval group for trace-based evaluations
data_source_config = {
    "type": "azure_ai_source",
    "scenario": "traces",
}

print("Creating trace-based evaluation group")
eval_object = client.evals.create(
    name="Trace Evaluation (Agent Smart Filter)",
    data_source_config=data_source_config,  # type: ignore
    testing_criteria=testing_criteria,
)
print(f"Evaluation created (id: {eval_object.id})")

# Compute time window in unix seconds
# Pad end_time by +600s (10 min) to avoid ingestion-delay edge exclusion
now_unix = int(time.time())
end_time = now_unix + 600
start_time = now_unix - (args.lookback_hours * 3600)

# Build trace_source based on mode
trace_source: dict = {
    "type": "agent_filter",
    "start_time": start_time,
    "end_time": end_time,
    "max_traces": args.max_traces,
    "filter_strategy": "smart_filtering"
}

# Add agent name/version or agent id
trace_source["agent_name"] = agent_name
trace_source["agent_version"] = agent_version
## trace_source["agent_id"] = args.agent_id

data_source = {
    "type": "azure_ai_trace_data_source_preview",
    "trace_source": trace_source,
}

eval_run = client.evals.runs.create(
    eval_id=eval_object.id,
    name="trace-evaluation-agent-smart-filter-run",
    data_source=data_source,  # type: ignore
)

Exigences en matière de données de trace

L’évaluation de trace nécessite que votre agent génère des portées en suivant les conventions sémantiques OpenTelemetry pour l’IA générative. Plus précisément, le service d’évaluation lit les invoke_agentspans depuis Application Insights et extrait les données de conversation à partir de leurs attributs.

Les attributs d’étendue suivants sont utilisés :

Caractéristique Obligatoire Description
gen_ai.operation.name Yes Doit être égal à "invoke_agent". Le service ignore tous les autres spans.
gen_ai.agent.id Pour le mode de filtrage de l’agent Identificateur d’agent unique (format : agent-name:version).
gen_ai.agent.name Pour le mode de filtrage de l’agent Nom d'agent lisible par un humain.
gen_ai.input.messages Entrées de requête pour les évaluateurs Tableau JSON de messages d’entrée suivant le format de message de conventions sémantiques GenAI. Les messages avec le rôle user ou system sont associés à query. Les messages avec le rôle assistant ou tool sont associés à response.
gen_ai.output.messages Entrées de requête pour les évaluateurs Tableau JSON de messages de sortie générés par un modèle. Tous les messages de sortie correspondent à response. Si la sortie contient également type: tool_call ou type: tool_result, elle correspond à tool_calls.
gen_ai.tool.definitions Facultatif Tableau JSON de schémas d’outils disponibles pour l’agent. S’il est absent, le service tente de déduire les définitions d’outils à partir des messages d’appel d’outil, mais les schémas déduits peuvent être incomplets.
gen_ai.conversation.id Facultatif Identificateur de conversation, transmis aux résultats d’évaluation afin d'assurer la corrélation.

Note

Si gen_ai.input.messages et gen_ai.output.messages sont vides ou manquants, les évaluateurs de qualité (cohérence, fluidité, pertinence, résolution d’intention) retournent score=None. Les évaluateurs de sécurité (violence, auto-préjudice, sexuel, haine/injustice) peuvent toujours produire des scores avec des données partielles, mais ils peuvent ne pas produire de résultats significatifs.

Pour les agents Python développés avec le SDK Azure AI Agent Server, ajoutez l'extension [tracing] pour activer l’émission automatique des spans :

pip install "azure-ai-agentserver-core[tracing]"

Prérequis pour l’évaluation des traces

En plus des conditions préalables générales, l’évaluation des traces nécessite :

  • Ressource Application Insights connectée à votre projet Foundry. Consultez Configurer le traçage dans Microsoft Foundry.
  • L'identité managée du projet doit avoir le rôle Log Analytics Reader sur la ressource Application Insights et sur l'espace de travail Log Analytics qui lui est lié. Si les tables qui stockent vos traces sont protégées (leur niveau de protection est protégé), attribuez également le rôle Lecteur de données de surveillance privilégié aux mêmes étendues afin que le service puisse lire les tables de trace protégées.
  • Package azure-monitor-query Python (nécessaire uniquement si vous collectez manuellement les ID de trace).
pip install "azure-ai-projects>=2.2.0" azure-monitor-query

Définissez ces variables d’environnement :

  • APPINSIGHTS_RESOURCE_ID — ID de ressource Application Insights (par exemple, /subscriptions/<subscription_id>/resourceGroups/<rg_name>/providers/Microsoft.Insights/components/<resource_name>).
  • AGENT_ID — Identificateur de l’agent émis par l’intégration de suivi (gen_ai.agent.id attribut), utilisé pour filtrer les traces. Format : agent-name:version.
  • TRACE_LOOKBACK_HOURS — (Facultatif) Nombre d’heures à examiner lors de l’interrogation des traces. La valeur par défaut est 1.

Option A : Évaluer par filtre d’agent

L’approche la plus simple consiste à laisser le service détecter et évaluer automatiquement les traces récentes d’un agent spécifique. Vous n’avez pas besoin de collecter manuellement les ID de trace.

import os

agent_id = os.environ["AGENT_ID"]  # e.g., "my-weather-agent:1"
trace_lookback_hours = int(os.environ.get("TRACE_LOOKBACK_HOURS", "1"))

# Create the evaluation
data_source_config = {
    "type": "azure_ai_source",
    "scenario": "traces",
}

eval_object = openai_client.evals.create(
    name="Agent Trace Evaluation (by agent)",
    data_source_config=data_source_config,
    testing_criteria=testing_criteria,  # See "Set up evaluators" below
)

# Create a run — the service queries App Insights for matching traces
data_source = {
    "type": "azure_ai_traces",
    "agent_id": agent_id,
    "max_traces": 50,           # Maximum number of traces to evaluate
    "lookback_hours": trace_lookback_hours,
}

eval_run = openai_client.evals.runs.create(
    eval_id=eval_object.id,
    name="agent-trace-eval-run",
    data_source=data_source,
)

print(f"Evaluation run started: {eval_run.id}")

Le service filtre les spans invoke_agent selon l’attribut gen_ai.agent.id, échantillonne jusqu’à max_traces ID de trace uniques et évalue tous les spans de ces traces.

Option B : Évaluer par ID de trace

Pour plus de contrôle, collectez des ID de trace spécifiques à partir d’Application Insights et évaluez-les. Cette méthode est utile lorsque vous souhaitez évaluer un ensemble organisé d’interactions, telles que les traces signalées par des alertes ou échantillonnée pour l’examen de la qualité.

Collecter des ID de trace à partir d’Application Insights

Interrogez Application Insights pour les valeurs operation_Id provenant des traces de votre agent. Chacune operation_Id représente une interaction complète de l’agent :

import os
from datetime import datetime, timedelta, timezone
from azure.identity import DefaultAzureCredential
from azure.monitor.query import LogsQueryClient, LogsQueryStatus

appinsights_resource_id = os.environ["APPINSIGHTS_RESOURCE_ID"]
agent_id = os.environ["AGENT_ID"]
trace_query_hours = int(os.environ.get("TRACE_LOOKBACK_HOURS", "1"))

end_time = datetime.now(timezone.utc)
start_time = end_time - timedelta(hours=trace_query_hours)

query = f"""dependencies
| where timestamp between (datetime({start_time.isoformat()}) .. datetime({end_time.isoformat()}))
| extend agent_id = tostring(customDimensions["gen_ai.agent.id"])
| where agent_id == "{agent_id}"
| distinct operation_Id"""

credential = DefaultAzureCredential()
logs_client = LogsQueryClient(credential)
response = logs_client.query_resource(
    appinsights_resource_id,
    query=query,
    timespan=None,  # Time range is specified in the query itself
)

trace_ids = []
if response.status == LogsQueryStatus.SUCCESS:
    for table in response.tables:
        for row in table.rows:
            trace_ids.append(row[0])

print(f"Found {len(trace_ids)} trace IDs")

Créer une évaluation et l'exécuter avec des ID de suivi

# Create the evaluation
data_source_config = {
    "type": "azure_ai_source",
    "scenario": "traces",
}

eval_object = openai_client.evals.create(
    name="Agent Trace Evaluation (by trace IDs)",
    data_source_config=data_source_config,
    testing_criteria=testing_criteria,  # See "Set up evaluators" below
)

# Create a run using the collected trace IDs
data_source = {
    "type": "azure_ai_traces",
    "trace_ids": trace_ids,
    "lookback_hours": trace_query_hours,
}

eval_run = openai_client.evals.runs.create(
    eval_id=eval_object.id,
    name="agent-trace-eval-run",
    metadata={
        "agent_id": agent_id,
        "start_time": start_time.isoformat(),
        "end_time": end_time.isoformat(),
    },
    data_source=data_source,
)

print(f"Evaluation run started: {eval_run.id}")

Configurer des évaluateurs et des mappages de données

Lorsque vous évaluez les traces, le service extrait automatiquement les données de conversation des attributs de span OpenTelemetry. Utilisez ces noms de champs directement dans data_mapping (sans les item.sample. préfixes utilisés dans d’autres scénarios) :

Variable Attribut source Description
{{item.query}} gen_ai.input.messages (rôles utilisateur/système) Requête de l’utilisateur extraite de la trace.
{{item.response}} gen_ai.input.messages (rôles assistant/outil) + gen_ai.output.messages Réponse de l’agent extraite de la trace.
{{item.tool_definitions}} gen_ai.tool.definitions Schémas d’outil disponibles pour l’agent. Obligatoire uniquement pour les évaluateurs liés aux outils.
{{item.tool_calls}} Extrait des messages de l’Assistant dans gen_ai.input.messages / gen_ai.output.messages Appels d’outil effectués par l’agent pendant l’interaction. Utilisé par les évaluateurs d’outils. Obligatoire uniquement pour les évaluateurs liés aux outils.
from azure.ai.projects.models import TestingCriterionAzureAIEvaluator

testing_criteria = [
    # Quality evaluators — require query and response from trace data
    TestingCriterionAzureAIEvaluator(
        type="azure_ai_evaluator",
        name="intent_resolution",
        evaluator_name="builtin.intent_resolution",
        data_mapping={
            "query": "{{item.query}}",
            "response": "{{item.response}}",
            "tool_definitions": "{{item.tool_definitions}}",
        },
        initialization_parameters={"model": model_deployment_name},
    ),
    # Tool evaluators — assess tool usage quality
    TestingCriterionAzureAIEvaluator(
        type="azure_ai_evaluator",
        name="tool_call_accuracy",
        evaluator_name="builtin.tool_call_accuracy",
        data_mapping={
            "query": "{{item.query}}",
            "response": "{{item.response}}",
            "tool_calls": "{{item.tool_calls}}",
            "tool_definitions": "{{item.tool_definitions}}",
        },
        initialization_parameters={"model": model_deployment_name},
    ),
]

Étapes suivantes