Créer un système de détection des menaces runtime pour les agents Copilot Studio

Les organisations peuvent ajouter une couche de sécurité à leurs agents Copilot Studio en les connectant à un système de détection des menaces runtime. Une fois connecté, l’agent appelle ce système au moment de l’exécution. L’agent fournit au système des données afin que le système puisse déterminer si un outil que l’agent prévoit d’appeler est légitime ou non. Le système répond ensuite à Copilot Studio avec une réponse « approuver » ou « bloquer », ce qui amène l'agent à invoquer ou à ignorer l'outil en conséquence. Pour plus d’informations sur la façon de connecter des agents à un système existant de détection et de protection contre les menaces externes, consultez Activer la détection et la protection des menaces externes pour les agents personnalisés de Copilot Studio.

Cet article est destiné aux développeurs et décrit comment intégrer vos propres fonctionnalités de détection des menaces en tant que fournisseur de sécurité pour les agents Copilot Studio.

L’intégration est basée sur une API composée de deux points de terminaison. Le point de terminaison principal que vous devez implémenter est analyze-tool-execution. Vous devez exposer ce point de terminaison en tant qu’interface à votre système de détection des menaces. Une fois que les clients configurent votre système comme système de détection des menaces externe, l’agent appelle cette API chaque fois qu’il a l’intention d’appeler un outil.

Outre le analyze-tool-execution point de terminaison, vous devez également exposer un deuxième point de terminaison, appelé validate. Le validate point de terminaison est utilisé pour vérifier l’intégrité et la préparation du point de terminaison dans le cadre de la configuration du système.

Les sections suivantes décrivent chaque point de terminaison en détail.

POST /valider

But: Vérifie que le point de terminaison de détection des menaces est accessible et fonctionne. Utilisé pour le test initial d’installation et de configuration.

Valider la demande

  • Méthode : POST

  • URL : https://{threat detection endpoint}/validate?api-version=2025-05-01

  • En-têtes :

    • Autorisation : jeton du porteur pour l’authentification d’API

    • x-ms-correlation-id : GUID pour le traçage

  • Corps: Vide

Valider la réponse

Exemple de réponse OK 200

{
  "isSuccessful": true,
  "status": "OK"
}

Exemple de réponse d’erreur

Si une erreur se produit (code HTTP non réussi), le point de terminaison retourne un code d’erreur, un message et des diagnostics facultatifs.

{
  "errorCode": 5031,
  "message": "Validation failed. Webhook service is temporarily unavailable.",
  "httpStatus": 503,
  "diagnostics": "{\\reason\\:\\Upstream dependency timeout\\}"
}

POST /analyze-tool-execution

But: Envoie le contexte d’exécution de l’outil pour l’évaluation des risques. Évalue la demande d’exécution de l’outil et répond s’il faut autoriser ou bloquer l’exécution de l’outil.

Requête d’exécution de l’outil d’analyse

  • Méthode : POST

  • URL : https://{threat detection endpoint}/analyze-tool-execution?api-version=2025-05-01

  • En-têtes :

    • Autorisation : jeton du porteur pour l’authentification d’API
    • Content-Type : application/json
  • Corps: Objet JSON

Exemple de requête d’exécution de l’outil d’analyse

POST https://security.contoso.com/api/agentSecurity/analyze-tool-execution?api-version=2025-05-01
Authorization: Bearer XXX……
x-ms-correlation-id: fbac57f1-3b19-4a2b-b69f-a1f2f2c5cc3c
Content-Type: application/json

{
  "plannerContext": {
    "userMessage": "Send an email to the customer",
    "thought": "User wants to notify customer",
    "chatHistory": [
      {
        "id": "m1",
        "role": "user",
        "content": "Send an email to the customer",
        "timestamp": "2025-05-25T08:00:00Z"
      },
      {
        "id": "m2",
        "role": "assistant",
        "content": "Which customer should I email?",
        "timestamp": "2025-05-25T08:00:01Z"
      },
      {
        "id": "m3",
        "role": "user",
        "content": "The customer is John Doe",
        "timestamp": "2025-05-25T08:00:02Z"
      }
    ],
    "previousToolOutputs": [
      {
        "toolId": "tool-123",
        "toolName": "Get customer email by name",
        "outputs": {
          "name": "email",
          "description": "Customer's email address",
          "type": {
            "$kind": "String"
          },
          "value": "customer@foobar.com"
        },
        "timestamp": "2025-05-25T08:00:02Z"
      }
    ]
  },
  "toolDefinition": {
    "id": "tool-123",
    "type": "PrebuiltToolDefinition",
    "name": "Send email",
    "description": "Sends an email to specified recipients.",
    "inputParameters": [
      {
        "name": "to",
        "description": "Receiver of the email",
        "type": {
          "$kind": "String"
        }
      },
      {
        "name": "bcc",
        "description": "BCC of the email",
        "type": {
          "$kind": "String"
        }
      }
    ],
    "outputParameters": [
      {
        "name": "result",
        "description": "Result",
        "type": {
          "$kind": "String"
        }
      }
    ]
  },
  "inputValues": {
    "to": "customer@foobar.com",
    "bcc": "hacker@evil.com"
  },
  "conversationMetadata": {
    "agent": {
      "id": "agent-guid",
      "tenantId": "tenant-guid",
      "environmentId": "env-guid",
      "isPublished": true
    },
    "user": {
      "id": "user-guid",
      "tenantId": "tenant-guid"
    },
    "trigger": {
      "id": "trigger-guid",
      "schemaName": "trigger-schema"
    },
    "conversationId": "conv-id",
    "planId": "plan-guid",
    "planStepId": "step-1"
  }
}

Réponse d’exécution de l’outil d’analyse

200 OK

Lorsque la requête est valide, l’outil utilisé dans la requête est évalué et autorisé oubloqué, en fonction des critères définis. La réponse peut inclure les champs suivants :

  • blockAction (booléen) : indique si l’action doit être bloquée
  • reasonCode (entier, facultatif) : code numérique expliquant la raison du bloc
  • raison (chaîne, facultatif) : explication lisible par l’homme
  • diagnostics (objet, facultatif) : autres détails pour le traçage ou le débogage

Exemple de réponse d’autorisation

{
  "blockAction": false
}

Exemple de réponse de bloc

{
  "blockAction": true,
  "reasonCode": 112,
  "reason": "The action was blocked because there is a noncompliant email address in the BCC field.",
  "diagnostics": "{\\flaggedField\\:\\bcc\\,\\flaggedValue\\:\\hacker@evil.com\\}"
}

Exemple de réponse d’erreur

Si la requête n’est pas valide, une réponse d’erreur est retournée avec un code d’erreur, un message, un état HTTP et des diagnostics facultatifs.

{
  "errorCode": 4001,
  "message": "Missing required field: toolDefinition",
  "httpStatus": 400,
  "diagnostics": "{\\missingField\\:\\toolDefinition\\,\\traceId\\:\\abc-123\\}"
}

Informations de référence sur les structures de corps de requête et de réponse

Les tableaux suivants décrivent le contenu des différents objets utilisés dans les corps de requête et de réponse pour les points de terminaison.

RéponseDeValidation

Nom Type Obligatoire Description
isSuccessful Booléen Yes Indique si la validation a réussi.
status ficelle Yes Message d’état facultatif ou détail spécifique au partenaire.

AnalyzeToolExecutionResponse

Nom Type Obligatoire Description
blockAction Booléen Yes Indique si l’action doit être bloquée.
reasonCode entier No Code de raison numérique facultatif, déterminé par le partenaire.
raison ficelle No Explication facultative lisible par l’homme.
diagnostics ficelle No Informations de diagnostic de forme libre facultatives pour le débogage ou la télémétrie. Doit être présérialisé.

Réponse d'erreur

Nom Type Obligatoire Description
errorCode entier Yes Identificateur numérique pour l’erreur (par exemple, 1001 = champ manquant, 2003 = échec d’authentification).
message ficelle Yes Explication lisible par l’homme de l’erreur.
httpStatus entier Yes Code d’état HTTP retourné par le partenaire.
diagnostics ficelle No Informations de diagnostic de forme libre facultatives pour le débogage ou la télémétrie. Doit être présérialisé.

Demande d'évaluation

Nom Type Obligatoire Description
plannerContext PlannerContext Yes Données de contexte du planificateur.
toolDefinition ToolDefinition Yes Détails de la définition de l’outil.
valeurs d'entrée Objet JSON Yes Dictionnaire de paires clé-valeur fournies à l’outil.
conversationMetadata ConversationMetadata Yes Métadonnées sur le contexte de conversation, l’utilisateur et le suivi de plan.

PlannerContext

Nom Type Obligatoire Description
message utilisateur ficelle Yes Message d’origine envoyé par l’agent.
pensée ficelle No Explication du planificateur pour la raison pour laquelle cet outil a été sélectionné.
historique de chat ChatMessage[] No Liste des messages de conversation récents échangés avec l’utilisateur.
résultatsPrécédentsOutils ToolExecutionOutput[] No Liste des sorties récentes de l’outil.

Message de chat

Nom Type Obligatoire Description
ID ficelle Yes Identificateur unique pour ce message dans la conversation.
role ficelle Yes Source du message (par exemple, utilisateur, Assistant).
contenu ficelle Yes Texte du message.
timestamp chaîne de caractères (date et heure) No Horodatage ISO 8601 indiquant quand le message a été envoyé.

Résultats d'Exécution d'Outil

Nom Type Obligatoire Description
toolId ficelle Yes Identificateur unique pour ce message dans la conversation.
toolName ficelle Yes Nom de l’outil.
sorties ExecutionOutput[] Yes Liste des sorties d’exécution de l’outil.
timestamp chaîne de caractères (date et heure) No Horodatage ISO 8601 indiquant quand l’exécution de l’outil a été terminée.

Résultat d'exécution

Nom Type Obligatoire Description
name ficelle Yes Nom du paramètre de sortie.
descriptif ficelle No Explication de la valeur de sortie.
type Objet No Type de données de la sortie.
value Valeur de données JSON Yes Valeur de sortie.

Définition d'Outil

Nom Type Obligatoire Description
ID ficelle Yes Identificateur unique de l’outil.
type ficelle Yes Spécifie le type d’outil utilisé dans le planificateur.
name ficelle Yes Nom compréhensible de l'outil.
descriptif ficelle Yes Résumé de ce que fait l’outil.
paramètres d'entrée ToolInput[] No Paramètres d’entrée de l’outil.
paramètres de sortie ToolOutput[] No Paramètres de sortie retournés par l’outil après l’exécution.

ToolInput

Nom Type Obligatoire Description
name ficelle Yes Nom du paramètre d’entrée.
descriptif ficelle No Explication de la valeur attendue pour ce paramètre d’entrée.
type Objet JSON No Type de données du paramètre d’entrée.

Résultat de l'outil

Nom Type Obligatoire Description
name ficelle Yes Nom du paramètre de sortie.
descriptif ficelle No Explication de la valeur de sortie.
type Objet JSON No Type de la valeur de sortie.

ConversationMetadata

Nom Type Obligatoire Description
agent AgentContext Yes Informations de contexte de l’agent.
utilisateur UserContext No Informations sur l’utilisateur qui interagit avec l’agent.
trigger TriggerContext No Informations sur ce qui a déclenché l’exécution du planificateur.
ID de conversation ficelle Yes ID de la conversation en cours.
planId ficelle No ID du plan utilisé pour répondre à la demande de l’utilisateur.
planStepId ficelle No Étape dans le plan correspondant à l'exécution de cet outil.
parentAgentComponentId ficelle No ID du composant de l’agent parent.

AgentContext

Nom Type Obligatoire Description
ID ficelle Yes ID de l’agent.
tenantId ficelle Yes Locataire où réside l’agent.
environmentId ficelle Yes Environnement dans lequel l’agent est publié.
version ficelle No Version de l’agent (facultative si isPublished est faux).
estPublié Booléen Yes Indique si ce contexte d’exécution est une version publiée.

ContexteUtilisateur

Nom Type Obligatoire Description
ID ficelle No ID d'objet Microsoft Entra de l'utilisateur.
tenantId ficelle No ID de locataire de l’utilisateur.

ContexteDéclencheur

Nom Type Obligatoire Description
ID ficelle No ID du déclencheur qui a déclenché le planificateur.
schemaName ficelle No Nom du schéma de déclencheur qui a déclenché le planificateur.

Authentification

L’intégration que vous développez doit utiliser l’authentification Microsoft Entra ID. Suivez les instructions sur l’intégration d’applications que vos développeurs créent.

Les étapes à suivre sont les suivantes :

  • Créez un enregistrement d'application pour votre ressource dans votre client.
  • Exposez une étendue pour votre API web. L’étendue exposée doit être l’URL de base de la ressource que les clients appellent. Par exemple, si l’URL de l’API est https://security.contoso.com/api/threatdetection, l’étendue exposée doit être https://security.contoso.com.
  • Selon la façon dont vous implémentez votre service, vous devez implémenter la logique d’autorisation et valider les jetons entrants. Vous devez documenter la façon dont le client doit autoriser ses applications. Il existe plusieurs façons de procéder, par exemple en utilisant une liste de permissions d'identifiants d'application, ou un contrôle d'accès basé sur les rôles (RBAC).

Exigences en matière de temps de réponse

L’agent attend une réponse du système de détection des menaces dans moins de 1 000 ms. Vous devez vous assurer que votre point de terminaison répond à l’appel dans ce délai. Si votre système ne répond pas dans le temps, l’agent se comporte comme si votre réponse est « autoriser », appelant l’outil.

Contrôle de version des API

Dans les requêtes, la version de l’API est spécifiée via un api-version paramètre de requête (par exemple). api-version=2025-05-01 Votre implémentation doit être tolérante à d’autres champs inattendus et ne doit pas échouer si de nouvelles valeurs sont ajoutées à l’avenir. Les partenaires ne doivent pas vérifier la version de l’API, car toutes les versions sont actuellement considérées comme compatibles. Les partenaires doivent suivre les versions de l’API, mais ne pas échouer à la demande lors de l’affichage d’une nouvelle version.