DEV Community

Sangmin Lee
Sangmin Lee

Posted on • Originally published at claudeguide.io

Claude API tool_use_error (invalid_request_error): 원인과 해결법

Originally published at claudeguide.io/claude-api-error-tool-use-error

Claude API tool_use_error (invalid_request_error): 원인과 해결법

Claude API tool_use_error invalid_request_error는 tool_choice / tool_result / tool_use 형식이 schema와 불일치에 발생합니다 (2026 기준). Tool use 형식 오류이며, 재시도하지 말고 요청 자체를 수정해야 합니다. 이 글은 5가지 흔한 원인과 Python/TypeScript 코드 예시를 다룹니다.

전반적인 Claude API 에러 처리 패턴은 Claude API Error Handling 가이드를 참고하세요.


무엇을 의미하는가?

tool_use_error 에러 서브타입는 tool_choice / tool_result / tool_use 형식이 schema와 불일치을 의미합니다. Anthropic API의 에러 응답 본문에는 error.type"invalid_request_error"로 명시되며, error.message에 구체적 사유가 옵니다.

응답 예시:

{
  "type": "error",
  "error": {
    "type": "invalid_request_error",
    "message": "..."
  }
}
Enter fullscreen mode Exit fullscreen mode

흔한 원인 5가지

  1. tool_use_id가 tool_result와 매칭 안 됨
  2. tool_choice를 specific tool로 했지만 해당 tool 미정의
  3. input_schema가 JSON Schema draft 2020-12 위반
  4. messages에 tool_use는 있는데 다음 turn에 tool_result 없음

해결 코드 (Python)

# Validate tool_use → tool_result pairing before sending
def validate_tool_pairing(messages):
    pending_tool_uses = []
    for msg in messages:
        if msg["role"] == "assistant":
            for block in msg.get("content", []):
                if isinstance(block, dict) and block.get("type") == "tool_use":
                    pending_tool_uses.append(block["id"])
        elif msg["role"] == "user":
            for block in msg.get("content", []):
                if isinstance(block, dict) and block.get("type") == "tool_result":
                    if block["tool_use_id"] in pending_tool_uses:
                        pending_tool_uses.remove(block["tool_use_id"])
    if pending_tool_uses:
        raise ValueError(f"Unmatched tool_use IDs: {pending_tool_uses}")
Enter fullscreen mode Exit fullscreen mode

해결 코드 (TypeScript)


typescript
function validateToolPairing(messages) {
  const pending: string[] = [];
  for (const msg of messages) {
    if (msg.role === "assistant") {
      for (const b of msg.content ?? []) {
        if (b.type === "tool_use") pending.push(b.id);
      }
    } else if (msg.role === "user") {
      for (const b of msg.content ?? []) {
        if (b.type === "tool_result") {
          const idx = pending.indexOf(b.tool_use_id);
          if (idx
Enter fullscreen mode Exit fullscreen mode

Top comments (0)