도구가 실패할 때 AI 에이전트가 수행하는 작업을 테스트하는 방법

AI 에이전트는 HTTP API, MCP 서버 및 기타 서비스를 호출합니다. 이러한 도구는 시간 초과가 발생하고, 속도 제한에 걸리거나, 오류를 반환하거나, 예상하지 못한 형식의 데이터를 보냅니다. 모델은 코드가 모델에 반환하는 내용에 따라 다음에 수행할 작업을 결정합니다. 코드가 오랫동안 기다린 끝에 예외, 빈 문자열 또는 아무 값도 반환하지 않으면, 에이전트는 명확한 오류를 받았을 때와 다르게 동작합니다.

도구 장애가 발생하는 방식

  • 에이전트가 멈춥니다. 시간 제한이 없는 도구 호출은 사용자를 계속 기다리게 합니다.
  • 에이전트가 반복됩니다. 모델은 토큰과 도구의 호출 한도를 소진하면서 실패한 도구를 몇 번이고 호출합니다.
  • 에이전트가 이를 숨깁니다. 코드는 오류를 무시하며 모델은 도구가 성공한 것처럼 응답합니다.
  • 에이전트가 충돌합니다. 처리되지 않은 예외는 전체 대화를 종료합니다.

도구 오류를 처리하는 방법

  1. 모든 도구 호출에 시간 제한을 설정하고 전체 턴에 대한 예산을 설정합니다. MCP 사양에 따르면 클라이언트는 도구 호출에 대한 시간 제한을 구현해야 합니다.
  2. 코드에서 발생한 일시적 오류를 다시 시도합니다. 도구 코드에서 429 및 503 응답을 처리하고, Retry-After를 유지하고 시도 횟수를 제한하여 모델이 재시도 시기를 결정할 필요가 없도록 하세요.
  3. 명확한 결과로 모델에 실패를 반환합니다. MCP는 알 수 없는 도구 또는 잘못된 인수와 같은 프로토콜 오류를 API 호출 실패와 같은 도구 실행 오류와 구분합니다. isError: true를 사용해 도구 결과의 실행 오류를 보고하므로 모델이 무엇이 잘못되었는지 확인할 수 있습니다. 무엇이 실패했는지와 다시 시도하는 것이 의미가 있는지 말하세요.
  4. 턴당 도구 호출 수를 제한합니다. 설정된 실패 횟수가 지나면 중지하고 사용자에게 알리십시오.
  5. 도구 결과를 모델에 전달하기 전에 유효성을 검사합니다. MCP 사양에 따르면 클라이언트는 이 작업을 수행하는 것이 좋다고 하며, 도구의 출력 스키마가 있는 경우 구조화된 결과를 해당 스키마에 따라 검증하는 것이 좋습니다.
  6. 무엇이 작동하지 않았는지 사용자에게 알리세요. 실패한 도구 호출을 기반으로 작성된 응답은 실패한 도구 호출에 기반했음을 명시해야 합니다.

에이전트에서 도구 오류 처리를 테스트하는 방법

Approach 찾은 내용 당신이 놓친 것
스텁 클라이언트를 사용하여 도구 래퍼를 단위 테스트하세요 작성한 오류를 코드가 매핑하는 방법 모델이 그것으로 무엇을 하는지, 그리고 실제 도구가 실패하는 방식
실제 도구를 망가뜨리기(예: 서버 중지 또는 키 해지) 그런 종류의 진정한 실패 속도 제한, 느린 응답 및 잘못된 형식의 데이터처럼 원할 때 의도적으로 유발할 수 없는 문제들
가짜 API 또는 MCP 서버 작성 직접 작성한 모든 응답 에이전트가 가짜를 가리키게 해야 하며, 그러면 실제 도구와 점점 어긋납니다
에이전트의 실제 도구 트래픽을 가로채고 실패를 삽입합니다. 실행 중인 에이전트 및 모델이 실제 도구의 오류, 지연 시간 및 잘못된 데이터를 어떻게 처리하는지 격리된 상태의 코드입니다. 그건 단위 테스트로 처리하세요.

모델 출력은 실행마다 다를 수 있으므로 각 실패 시나리오를 두 번 이상 실행하세요.

앱에서 직접 써 보기

Dev Proxy는 에이전트와 해당 도구 사이에 위치하며 에이전트 코드를 변경하지 않고 오류를 삽입합니다.

HTTP API를 호출하는 도구의 경우 임의 오류, 대기 시간 및 API가 요청한 만큼 오래 에이전트가 대기하는지 확인을 결합하세요.

{
  "$schema": "https://raw.githubusercontent.com/dotnet/dev-proxy/main/schemas/v3.3.1/rc.schema.json",
  "plugins": [
    {
      "name": "RetryAfterPlugin",
      "enabled": true,
      "pluginPath": "~appFolder/plugins/DevProxy.Plugins.dll"
    },
    {
      "name": "LatencyPlugin",
      "enabled": true,
      "pluginPath": "~appFolder/plugins/DevProxy.Plugins.dll",
      "configSection": "latencyPlugin"
    },
    {
      "name": "GenericRandomErrorPlugin",
      "enabled": true,
      "pluginPath": "~appFolder/plugins/DevProxy.Plugins.dll",
      "configSection": "errorsContosoApi"
    }
  ],
  "urlsToWatch": [
    "https://api.contoso.com/*"
  ],
  "latencyPlugin": {
    "$schema": "https://raw.githubusercontent.com/dotnet/dev-proxy/main/schemas/v3.3.1/latencyplugin.schema.json",
    "minMs": 2000,
    "maxMs": 10000
  },
  "errorsContosoApi": {
    "$schema": "https://raw.githubusercontent.com/dotnet/dev-proxy/main/schemas/v3.3.1/genericrandomerrorplugin.schema.json",
    "errorsFile": "errors-contoso-api.json",
    "rate": 50
  }
}

임의 오류로 내 앱 테스트에 설명된 대로 errors-contoso-api.json에서 오류를 정의합니다. Retry-After 응답에서 429을(를) @dynamic(으)로 설정합니다. RetryAfterPlugin은 그것들만 확인합니다.

STDIO를 사용하는 MCP 서버의 경우 stdio를 통해 서버를 시작하되, devproxy stdio와 같이 MockStdioResponsePlugin을 활성화하는 구성을 사용합니다. 로 devproxyrc-stdio.json저장합니다. 그런 다음, 모든 stdio-mocks.json 요청에 대한 도구 실행 오류를 반환하려면 이것을 tools/call에 넣습니다:

{
  "$schema": "https://raw.githubusercontent.com/dotnet/dev-proxy/main/schemas/v3.3.1/mockstdioresponseplugin.mocksfile.schema.json",
  "mocks": [
    {
      "request": {
        "bodyFragment": "tools/call"
      },
      "response": {
        "stdout": "{\"jsonrpc\":\"2.0\",\"id\":@stdin.body.id,\"result\":{\"content\":[{\"type\":\"text\",\"text\":\"Failed to fetch weather data: API rate limit exceeded\"}],\"isError\":true}}\n"
      }
    }
  ]
}
devproxy stdio --config-file devproxyrc-stdio.json npx -y @modelcontextprotocol/server-filesystem

에이전트에서 이를 사용하려면 에이전트의 MCP 서버 구성에서 명령을 변경하여 서버를 devproxy stdio를 통해 시작하도록 합니다. 모의 개체의 nth 속성을 사용하여 특정 호출만 실패하고 LatencyPlugin을 추가하여 서버의 응답을 느리게 합니다.

모델 자체가 실패할 때 에이전트가 수행하는 작업을 테스트하기 위해 LanguageModelFailurePlugin은 모델이 환각하도록, 명령을 무시하거나 잘못된 형식으로 답변하도록 합니다. 언어 모델 오류로 내 앱 테스트를 참조하세요.

개발 프록시를 설치하려면 개발 프록시 설정을 참조하세요.

다음 단계

또한, 다음을 참조하세요.