---
title: 도구 정의하기
url: https://platform.claude.com/docs/ko/agents-and-tools/tool-use/define-tools
description: 도구 스키마를 지정하고, 효과적인 설명을 작성하며, Claude가 도구를 호출하는 시점을 제어합니다.
---

## 사전 요구 사항

* ["tool use"(도구 사용) 개요](https://platform.claude.com/docs/ko/agents-and-tools/tool-use/overview)에 대한 이해
* Claude API 키와 작동하는 SDK 또는 cURL 설정

<Tip>
  도구 사용 및 "thinking"(사고)과 함께 Claude를 사용하는 경우, 자세한 내용은 [사고(Thinking)](https://platform.claude.com/docs/ko/build-with-claude/thinking)를 참조하세요.
</Tip>

## 클라이언트 도구 지정하기

"Client tools"(클라이언트 도구)는 API 요청의 최상위 매개변수인 `tools`에 지정됩니다. bash 및 텍스트 편집기 도구와 같은 Anthropic 스키마 클라이언트 도구는 날짜로 버전이 지정된 `type`으로 선언됩니다. 각 도구가 허용하는 필드는 [도구 참조](https://platform.claude.com/docs/ko/agents-and-tools/tool-use/tool-reference)에서 링크된 각 도구의 페이지를 참조하세요. 컴퓨터 사용 및 브라우저 사용 도구는 [클라이언트 도구 세트](https://platform.claude.com/docs/ko/agents-and-tools/tool-use/tool-reference#client-toolsets)로, 고정된 멤버 도구 집합을 선언하는 `name`이 없는 단일 항목입니다. 사용자 정의 도구 정의에는 다음이 포함됩니다:

| 매개변수             | 설명                                                                                                                                                                                       |
| ---------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `name`           | 도구의 이름입니다. 정규식 `^[a-zA-Z0-9_-]{1,128}$`와 일치해야 합니다.                                                                                                                                       |
| `description`    | 도구가 수행하는 작업, 사용해야 하는 시점, 동작 방식에 대한 상세한 일반 텍스트 설명입니다.                                                                                                                                     |
| `input_schema`   | 도구에 필요한 매개변수를 정의하는 [JSON Schema](https://json-schema.org/) 객체입니다.                                                                                                                        |
| `input_examples` | (선택 사항) Claude가 도구 사용 방법을 이해하는 데 도움이 되는 예시 입력 객체의 배열입니다. [도구 사용 예시 제공하기](https://platform.claude.com/docs/ko/agents-and-tools/tool-use/define-tools#providing-tool-use-examples)를 참조하세요. |

`cache_control`, `strict`, `defer_loading`, `allowed_callers`를 포함하여 단일 도구 정의에서 사용할 수 있는 선택적 속성의 전체 목록은 [도구 참조](https://platform.claude.com/docs/ko/agents-and-tools/tool-use/tool-reference#tool-definition-properties)를 참조하세요. 클라이언트 도구 세트 항목은 항목 자체에서 `cache_control`과 `allowed_callers`를 허용하며, `defer_loading`은 멤버별로 설정합니다. [클라이언트 도구 세트](https://platform.claude.com/docs/ko/agents-and-tools/tool-use/tool-reference#client-toolsets)를 참조하세요.

<Accordion title="간단한 도구 정의 예시">
  ```json JSON
  {
    "name": "get_weather",
    "description": "Get the current weather in a given location",
    "input_schema": {
      "type": "object",
      "properties": {
        "location": {
          "type": "string",
          "description": "The city and state, e.g. San Francisco, CA"
        },
        "unit": {
          "type": "string",
          "enum": ["celsius", "fahrenheit"],
          "description": "The unit of temperature, either 'celsius' or 'fahrenheit'"
        }
      },
      "required": ["location"]
    }
  }
  ```

  `get_weather`라는 이름의 이 도구는 필수 `location` 문자열과 "celsius" 또는 "fahrenheit" 중 하나여야 하는 선택적 `unit` 문자열을 포함하는 입력 객체를 기대합니다.
</Accordion>

### 도구 사용 시스템 프롬프트

`tools` 매개변수와 함께 Claude API를 호출하면, API는 도구 정의, 도구 구성 및 사용자가 지정한 "system prompt"(시스템 프롬프트)로부터 특별한 시스템 프롬프트를 구성합니다. 구성된 프롬프트는 모델이 지정된 도구를 사용하도록 지시하고 도구가 올바르게 작동하는 데 필요한 컨텍스트를 제공하도록 설계되었습니다:

```text wrap
In this environment you have access to a set of tools you can use to answer the user's question.
{{ FORMATTING INSTRUCTIONS }}
String and scalar parameters should be specified as is, while lists and objects should use JSON format. Note that spaces for string values are not stripped. The output is not expected to be valid XML and is parsed with regular expressions.
Here are the functions available in JSONSchema format:
{{ TOOL DEFINITIONS IN JSON SCHEMA }}
{{ USER SYSTEM PROMPT }}
{{ TOOL CONFIGURATION }}
```

### 도구 정의 모범 사례

도구를 사용할 때 Claude로부터 최상의 성능을 얻으려면 다음 지침을 따르세요:

* **매우 상세한 설명을 제공하세요.** 이는 도구 성능에서 단연 가장 중요한 요소입니다. 설명에는 다음을 포함하여 도구에 대한 모든 세부 사항을 설명해야 합니다:

  * 도구가 수행하는 작업
  * 도구를 사용해야 하는 시점(그리고 사용하지 말아야 하는 시점)
  * 각 매개변수의 의미와 도구 동작에 미치는 영향
  * 도구 이름이 명확하지 않은 경우 도구가 반환하지 않는 정보와 같은 중요한 주의 사항이나 제한 사항. 도구에 대해 Claude에게 더 많은 컨텍스트를 제공할수록 Claude가 도구를 언제 어떻게 사용할지 더 잘 판단할 수 있습니다. 각 도구 설명은 최소 3\~4문장을 목표로 하고, 도구가 복잡하다면 더 길게 작성하세요.

* **설명을 우선시하되, 복잡한 도구에는 `input_examples` 사용을 고려하세요.** 명확한 설명이 가장 중요하지만, 복잡한 입력, 중첩된 객체 또는 형식에 민감한 매개변수가 있는 도구의 경우 `input_examples` 필드를 사용하여 스키마 검증을 거친 예시를 제공할 수 있습니다. 자세한 내용은 [도구 사용 예시 제공하기](https://platform.claude.com/docs/ko/agents-and-tools/tool-use/define-tools#providing-tool-use-examples)를 참조하세요.

* **관련 작업을 더 적은 수의 도구로 통합하세요.** 모든 작업마다 별도의 도구(`create_pr`, `review_pr`, `merge_pr`)를 만드는 대신, `action` 매개변수를 가진 단일 도구로 묶으세요. 더 적지만 더 유능한 도구는 선택의 모호성을 줄이고 Claude가 도구 구성을 더 쉽게 탐색할 수 있게 합니다.

* **도구 이름에 의미 있는 네임스페이스를 사용하세요.** 도구가 여러 서비스나 리소스에 걸쳐 있는 경우, 이름 앞에 서비스 이름을 접두사로 붙이세요(예: `github_list_prs`, `slack_send_message`). 이렇게 하면 라이브러리가 커져도 도구 선택이 모호하지 않게 되며, 특히 [도구 검색](https://platform.claude.com/docs/ko/agents-and-tools/tool-use/tool-search-tool)을 사용할 때 중요합니다.

* **신호 가치가 높은 정보만 반환하도록 도구 응답을 설계하세요.** 불투명한 내부 참조 대신 의미 있고 안정적인 식별자(예: 슬러그 또는 UUID)를 반환하고, Claude가 다음 단계를 추론하는 데 필요한 필드만 포함하세요. 비대한 응답은 컨텍스트를 낭비하고 Claude가 중요한 정보를 추출하기 어렵게 만듭니다.

* **추론이 아닌 설명을 요청하세요.** 매개변수가 Claude에게 호출하는 이유를 묻는 경우, 짧은 설명이나 근거가 되는 증거를 요청하세요. 모델의 사고나 단계별 추론을 요청하는 매개변수는 `reasoning_extraction` 거부로 이어질 수 있습니다. [추론을 사고 블록에 유지하기](https://platform.claude.com/docs/ko/build-with-claude/refusals-and-fallback#keep-reasoning-in-thinking-blocks)를 참조하세요.

<AccordionGroup>
  <Accordion title="좋은 도구 설명 예시">
    ```json JSON
    {
      "name": "get_stock_price",
      "description": "Retrieves the current stock price for a given ticker symbol. The ticker symbol must be a valid symbol for a publicly traded company on a major US stock exchange like NYSE or NASDAQ. The tool will return the latest trade price in USD. It should be used when the user asks about the current or most recent price of a specific stock. It will not provide any other information about the stock or company.",
      "input_schema": {
        "type": "object",
        "properties": {
          "ticker": {
            "type": "string",
            "description": "The stock ticker symbol, e.g. AAPL for Apple Inc."
          }
        },
        "required": ["ticker"]
      }
    }
    ```
  </Accordion>

  <Accordion title="나쁜 도구 설명 예시">
    ```json JSON
    {
      "name": "get_stock_price",
      "description": "Gets the stock price for a ticker.",
      "input_schema": {
        "type": "object",
        "properties": {
          "ticker": {
            "type": "string"
          }
        },
        "required": ["ticker"]
      }
    }
    ```
  </Accordion>
</AccordionGroup>

좋은 설명은 도구가 수행하는 작업, 사용 시점, 반환하는 데이터, 그리고 `ticker` 매개변수의 의미를 명확하게 설명합니다. 나쁜 설명은 너무 짧아서 도구의 동작과 사용법에 대해 Claude에게 많은 의문을 남깁니다.

<Tip>
  도구 설계(통합, 이름 지정, 응답 구성)에 대한 더 깊은 지침은 [에이전트를 위한 도구 작성하기](https://www.anthropic.com/engineering/writing-tools-for-agents)를 참조하세요.
</Tip>

## 도구 사용 예시 제공하기

Claude가 도구를 더 효과적으로 사용하는 방법을 이해할 수 있도록 유효한 도구 입력의 구체적인 예시를 제공할 수 있습니다. 이는 중첩된 객체, 선택적 매개변수 또는 형식에 민감한 입력이 있는 복잡한 도구에 특히 유용합니다.

### 기본 사용법

도구 정의에 예시 입력 객체의 배열을 담은 선택적 `input_examples` 필드를 추가하세요. 각 예시는 도구의 `input_schema`에 따라 유효해야 합니다:

<CodeGroup>
  ```bash cURL
  curl -sS https://api.anthropic.com/v1/messages \
    -H "content-type: application/json" \
    -H "x-api-key: $ANTHROPIC_API_KEY" \
    -H "anthropic-version: 2023-06-01" \
    -d '{
      "model": "claude-opus-5-5",
      "max_tokens": 1024,
      "tools": [
        {
          "name": "get_weather",
          "description": "Get the current weather in a given location",
          "input_schema": {
            "type": "object",
            "properties": {
              "location": {
                "type": "string",
                "description": "The city and state, e.g. San Francisco, CA"
              },
              "unit": {
                "type": "string",
                "enum": ["celsius", "fahrenheit"],
                "description": "The unit of temperature"
              }
            },
            "required": ["location"]
          },
          "input_examples": [
            {"location": "San Francisco, CA", "unit": "fahrenheit"},
            {"location": "Tokyo, Japan", "unit": "celsius"},
            {"location": "New York, NY"}
          ]
        }
      ],
      "messages": [
        {"role": "user", "content": "What is the weather like in San Francisco?"}
      ]
    }'
  ```

  ```bash CLI
  ant messages create <<'YAML'
  model: claude-opus-5-5
  max_tokens: 1024
  tools:
    - name: get_weather
      description: Get the current weather in a given location
      input_schema:
        type: object
        properties:
          location:
            type: string
            description: The city and state, e.g. San Francisco, CA
          unit:
            type: string
            enum: [celsius, fahrenheit]
            description: The unit of temperature
        required: [location]
      input_examples:
        - location: San Francisco, CA
          unit: fahrenheit
        - location: Tokyo, Japan
          unit: celsius
        - location: New York, NY  # 'unit' is optional
  messages:
    - role: user
      content: What's the weather like in San Francisco?
  YAML
  ```

  ```python Python
  client = anthropic.Anthropic()

  response = client.messages.create(
      model="claude-opus-5-5",
      max_tokens=1024,
      tools=[
          {
              "name": "get_weather",
              "description": "Get the current weather in a given location",
              "input_schema": {
                  "type": "object",
                  "properties": {
                      "location": {
                          "type": "string",
                          "description": "The city and state, e.g. San Francisco, CA",
                      },
                      "unit": {
                          "type": "string",
                          "enum": ["celsius", "fahrenheit"],
                          "description": "The unit of temperature",
                      },
                  },
                  "required": ["location"],
              },
              "input_examples": [
                  {"location": "San Francisco, CA", "unit": "fahrenheit"},
                  {"location": "Tokyo, Japan", "unit": "celsius"},
                  {
                      "location": "New York, NY"  # 'unit' is optional
                  },
              ],
          }
      ],
      messages=[{"role": "user", "content": "What's the weather like in San Francisco?"}],
  )

  print(response)
  ```

  ```typescript TypeScript
  const client = new Anthropic();

  const response = await client.messages.create({
    model: "claude-opus-5-5",
    max_tokens: 1024,
    tools: [
      {
        name: "get_weather",
        description: "Get the current weather in a given location",
        input_schema: {
          type: "object",
          properties: {
            location: {
              type: "string",
              description: "The city and state, e.g. San Francisco, CA"
            },
            unit: {
              type: "string",
              enum: ["celsius", "fahrenheit"],
              description: "The unit of temperature"
            }
          },
          required: ["location"]
        },
        input_examples: [
          {
            location: "San Francisco, CA",
            unit: "fahrenheit"
          },
          {
            location: "Tokyo, Japan",
            unit: "celsius"
          },
          {
            location: "New York, NY"
            // 'unit'이 선택 사항임을 보여줍니다
          }
        ]
      }
    ],
    messages: [{ role: "user", content: "What's the weather like in San Francisco?" }]
  });

  console.log(response);
  ```

  ```csharp C#
  AnthropicClient client = new();

  var parameters = new MessageCreateParams
  {
      Model = Model.ClaudeOpus5_5,
      MaxTokens = 1024,
      Tools = [
          new ToolUnion(new Tool()
          {
              Name = "get_weather",
              Description = "Get the current weather in a given location",
              InputSchema = new InputSchema()
              {
                  Properties = new Dictionary<string, JsonElement>
                  {
                      ["location"] = JsonSerializer.SerializeToElement(new { type = "string", description = "The city and state, e.g. San Francisco, CA" }),
                      ["unit"] = JsonSerializer.SerializeToElement(new { type = "string", @enum = new[] { "celsius", "fahrenheit" }, description = "The unit of temperature" }),
                  },
                  Required = ["location"],
              },
              InputExamples =
              [
                  new Dictionary<string, JsonElement>()
                  {
                      { "location", JsonSerializer.SerializeToElement("San Francisco, CA") },
                      { "unit", JsonSerializer.SerializeToElement("fahrenheit") },
                  },
                  new Dictionary<string, JsonElement>()
                  {
                      { "location", JsonSerializer.SerializeToElement("Tokyo, Japan") },
                      { "unit", JsonSerializer.SerializeToElement("celsius") },
                  },
                  new Dictionary<string, JsonElement>()
                  {
                      { "location", JsonSerializer.SerializeToElement("New York, NY") },
                  },
              ],
          }),
      ],
      Messages = [
          new() { Role = Role.User, Content = "What's the weather like in San Francisco?" }
      ]
  };

  var message = await client.Messages.Create(parameters);
  Console.WriteLine(message);
  ```

  ```go Go
  client := anthropic.NewClient()

  response, err := client.Messages.New(context.TODO(), anthropic.MessageNewParams{
  	Model:     anthropic.ModelClaudeOpus5_5,
  	MaxTokens: 1024,
  	Tools: []anthropic.ToolUnionParam{
  		{OfTool: &anthropic.ToolParam{
  			Name:        "get_weather",
  			Description: anthropic.String("Get the current weather in a given location"),
  			InputSchema: anthropic.ToolInputSchemaParam{
  				Properties: map[string]any{
  					"location": map[string]any{
  						"type":        "string",
  						"description": "The city and state, e.g. San Francisco, CA",
  					},
  					"unit": map[string]any{
  						"type":        "string",
  						"enum":        []string{"celsius", "fahrenheit"},
  						"description": "The unit of temperature",
  					},
  				},
  				Required: []string{"location"},
  			},
  			InputExamples: []map[string]any{
  				{
  					"location": "San Francisco, CA",
  					"unit":     "fahrenheit",
  				},
  				{
  					"location": "Tokyo, Japan",
  					"unit":     "celsius",
  				},
  				{
  					"location": "New York, NY",
  					// 'unit'이 선택 사항임을 보여줍니다
  				},
  			},
  		}},
  	},
  	Messages: []anthropic.MessageParam{
  		anthropic.NewUserMessage(anthropic.NewTextBlock("What's the weather like in San Francisco?")),
  	},
  })
  if err != nil {
  	log.Fatal(err)
  }
  fmt.Println(response.RawJSON())
  ```

  ```java Java
  import com.anthropic.models.messages.Tool;
  import com.anthropic.models.messages.Tool.InputSchema;
  // ...
  void main() {
      AnthropicClient client = AnthropicOkHttpClient.fromEnv();

      MessageCreateParams params = MessageCreateParams.builder()
          .model(Model.CLAUDE_OPUS_5_5)
          .maxTokens(1024L)
          .addTool(Tool.builder()
              .name("get_weather")
              .description("Get the current weather in a given location")
              .inputSchema(InputSchema.builder()
                  .properties(JsonValue.from(Map.of(
                      "location", Map.of(
                          "type", "string",
                          "description", "The city and state, e.g. San Francisco, CA"
                      ),
                      "unit", Map.of(
                          "type", "string",
                          "enum", List.of("celsius", "fahrenheit"),
                          "description", "The unit of temperature"
                      )
                  )))
                  .required(List.of("location"))
                  .build())
              .putAdditionalProperty("input_examples", JsonValue.from(List.of(
                  Map.of(
                      "location", "San Francisco, CA",
                      "unit", "fahrenheit"
                  ),
                  Map.of(
                      "location", "Tokyo, Japan",
                      "unit", "celsius"
                  ),
                  Map.of(
                      "location", "New York, NY"
                  )
              )))
              .build())
          .addUserMessage("What's the weather like in San Francisco?")
          .build();

      Message response = client.messages().create(params);
      IO.println(response);
  }
  ```

  ```php PHP
  $client = new Client();

  $message = $client->messages->create(
      maxTokens: 1024,
      messages: [
          ['role' => 'user', 'content' => "What's the weather like in San Francisco?"]
      ],
      model: 'claude-opus-5-5',
      tools: [
          [
              'name' => 'get_weather',
              'description' => 'Get the current weather in a given location',
              'input_schema' => [
                  'type' => 'object',
                  'properties' => [
                      'location' => [
                          'type' => 'string',
                          'description' => 'The city and state, e.g. San Francisco, CA'
                      ],
                      'unit' => [
                          'type' => 'string',
                          'enum' => ['celsius', 'fahrenheit'],
                          'description' => 'The unit of temperature'
                      ]
                  ],
                  'required' => ['location']
              ],
              'input_examples' => [
                  [
                      'location' => 'San Francisco, CA',
                      'unit' => 'fahrenheit'
                  ],
                  [
                      'location' => 'Tokyo, Japan',
                      'unit' => 'celsius'
                  ],
                  [
                      'location' => 'New York, NY'
                  ]
              ]
          ]
      ],
  );
  ```

  ```ruby Ruby
  client = Anthropic::Client.new

  message = client.messages.create(
    model: "claude-opus-5-5",
    max_tokens: 1024,
    tools: [
      {
        name: "get_weather",
        description: "Get the current weather in a given location",
        input_schema: {
          type: "object",
          properties: {
            location: {
              type: "string",
              description: "The city and state, e.g. San Francisco, CA"
            },
            unit: {
              type: "string",
              enum: ["celsius", "fahrenheit"],
              description: "The unit of temperature"
            }
          },
          required: ["location"]
        },
        input_examples: [
          {
            location: "San Francisco, CA",
            unit: "fahrenheit"
          },
          {
            location: "Tokyo, Japan",
            unit: "celsius"
          },
          {
            location: "New York, NY"
          }
        ]
      }
    ],
    messages: [
      { role: "user", content: "What's the weather like in San Francisco?" }
    ]
  )
  puts message
  ```
</CodeGroup>

예시는 도구 스키마와 함께 프롬프트에 포함되어, 올바른 형식의 도구 호출에 대한 구체적인 패턴을 Claude에게 보여줍니다. 이는 Claude가 선택적 매개변수를 언제 포함해야 하는지, 어떤 형식을 사용해야 하는지, 복잡한 입력을 어떻게 구성해야 하는지 이해하는 데 도움이 됩니다.

### 요구 사항 및 제한 사항

* **스키마 검증** - 각 예시는 도구의 `input_schema`에 따라 유효해야 합니다. 유효하지 않은 예시는 400 오류를 반환합니다
* **서버 측 도구 또는 클라이언트 도구 세트에서는 지원되지 않음** - 입력 예시는 사용자 정의 도구와 [컴퓨터 사용](https://platform.claude.com/docs/ko/agents-and-tools/tool-use/computer-use-tool) 및 [브라우저 사용](https://platform.claude.com/docs/ko/agents-and-tools/tool-use/browser-use-tool) 도구 세트를 제외한 Anthropic 스키마 클라이언트 도구에서 작동하지만, 웹 검색이나 코드 실행과 같은 서버 도구에서는 작동하지 않습니다
* **토큰 비용** - 예시는 프롬프트 토큰을 증가시킵니다: 간단한 예시는 약 20\~50 토큰, 복잡한 중첩 객체는 약 100\~200 토큰

## Claude의 출력 제어하기

### 도구 사용 강제하기

경우에 따라 Claude가 도구를 호출하지 않고 직접 답변할 수 있는 상황에서도, 사용자의 질문에 답하기 위해 Claude가 특정 도구를 사용하도록 하고 싶을 수 있습니다. 요청의 `tool_choice` 필드에 도구를 지정하여 이를 수행할 수 있습니다.

모든 모델과 설정이 강제 도구 사용을 지원하는 것은 아닙니다. 지원되지 않는 경우 `tool_choice: {"type": "any"}`와 `tool_choice: {"type": "tool", "name": "..."}`는 실패하지만, `tool_choice: {"type": "auto"}`(기본값)와 `tool_choice: {"type": "none"}`은 여전히 작동합니다:

| 모델 또는 설정                                                                                                                                   | 제한 사항                                                                                                        | 대신 사용할 항목                                                                                                                                                                                                                                                                                                     |
| ------------------------------------------------------------------------------------------------------------------------------------------ | ------------------------------------------------------------------------------------------------------------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| 수동 [확장 사고](https://platform.claude.com/docs/ko/build-with-claude/extended-thinking) (`thinking: {type: "enabled"}`)                        | `any`와 `tool`은 지원되지 않으며 오류가 발생합니다                                                                            | `auto` 또는 `none`. [적응형 사고](https://platform.claude.com/docs/ko/build-with-claude/thinking) 자체는 강제 도구 사용을 막지 않습니다(Claude Opus 5 및 Claude Haiku 5.5와 같이 사고가 기본적으로 켜져 있는 모델은 이를 허용하지만, 강제 호출은 사고를 건너뜁니다. 응답은 도구 호출로 시작하며 `thinking` 블록이 없습니다). 다음 행의 모델은 사고 설정과 관계없이 강제 도구 사용을 거부합니다                             |
| Claude Opus 5.5, Claude Sonnet 5.5, Claude Fable 5.1 및 [Claude Mythos 5.1](https://platform.claude.com/docs/ko/models/mythos-5-1/overview) | `any`와 `tool`은 [400 오류](https://platform.claude.com/docs/ko/api/errors#forced-tool-use-not-supported)를 반환합니다 | 스키마에 유효한 도구 입력을 보장하려면 [엄격한 도구 사용](https://platform.claude.com/docs/ko/agents-and-tools/tool-use/strict-tool-use)과 함께 `auto`를 사용하거나, 고정된 JSON 형태의 응답이 필요한 경우 [구조화된 출력](https://platform.claude.com/docs/ko/build-with-claude/structured-outputs)을 사용하세요. 프롬프트는 여전히 `auto`가 어떤 도구를 선택할지에 영향을 줍니다. `none`도 지원됩니다 |

이를 지원하는 모델에서는 강조 표시된 줄만이 표준 도구 사용 요청과의 유일한 차이점입니다:

<CodeGroup>
  ```bash cURL
  curl -sS https://api.anthropic.com/v1/messages \
    -H "content-type: application/json" \
    -H "x-api-key: $ANTHROPIC_API_KEY" \
    -H "anthropic-version: 2023-06-01" \
    -d '{
      "model": "claude-opus-5",
      "max_tokens": 1024,
      "tools": [
        {
          "name": "get_weather",
          "description": "Get the current weather in a given location",
          "input_schema": {
            "type": "object",
            "properties": {
              "location": {
                "type": "string",
                "description": "The city and state, e.g. San Francisco, CA"
              }
            },
            "required": ["location"]
          }
        }
      ],
      "tool_choice": {"type": "tool", "name": "get_weather"},
      "messages": [
        {"role": "user", "content": "What is the weather like in San Francisco?"}
      ]
    }'
  ```

  ```bash CLI
  ant messages create <<'YAML'
  model: claude-opus-5
  max_tokens: 1024
  tools:
    - name: get_weather
      description: Get the current weather in a given location
      input_schema:
        type: object
        properties:
          location:
            type: string
            description: The city and state, e.g. San Francisco, CA
        required: [location]
  tool_choice:
    type: tool
    name: get_weather
  messages:
    - role: user
      content: What's the weather like in San Francisco?
  YAML
  ```

  ```python Python
  client = anthropic.Anthropic()

  tools = [
      {
          "name": "get_weather",
          "description": "Get the current weather in a given location",
          "input_schema": {
              "type": "object",
              "properties": {
                  "location": {
                      "type": "string",
                      "description": "The city and state, e.g. San Francisco, CA",
                  }
              },
              "required": ["location"],
          },
      }
  ]

  response = client.messages.create(
      model="claude-opus-5",
      max_tokens=1024,
      tools=tools,
      tool_choice={"type": "tool", "name": "get_weather"},
      messages=[{"role": "user", "content": "What's the weather like in San Francisco?"}],
  )

  print(response)
  ```

  ```typescript TypeScript
  const client = new Anthropic();

  const response = await client.messages.create({
    model: "claude-opus-5",
    max_tokens: 1024,
    tools: [
      {
        name: "get_weather",
        description: "Get the current weather in a given location",
        input_schema: {
          type: "object",
          properties: {
            location: {
              type: "string",
              description: "The city and state, e.g. San Francisco, CA"
            }
          },
          required: ["location"]
        }
      }
    ],
    tool_choice: { type: "tool", name: "get_weather" },
    messages: [{ role: "user", content: "What's the weather like in San Francisco?" }]
  });

  console.log(response);
  ```

  ```csharp C#
  AnthropicClient client = new();

  var parameters = new MessageCreateParams
  {
      Model = Model.ClaudeOpus5,
      MaxTokens = 1024,
      Tools = [
          new ToolUnion(new Tool()
          {
              Name = "get_weather",
              Description = "Get the current weather in a given location",
              InputSchema = new InputSchema()
              {
                  Properties = new Dictionary<string, JsonElement>
                  {
                      ["location"] = JsonSerializer.SerializeToElement(new { type = "string", description = "The city and state, e.g. San Francisco, CA" }),
                  },
                  Required = ["location"],
              },
          }),
      ],
      ToolChoice = new ToolChoiceTool { Name = "get_weather" },
      Messages = [
          new() { Role = Role.User, Content = "What's the weather like in San Francisco?" }
      ]
  };

  var message = await client.Messages.Create(parameters);
  Console.WriteLine(message);
  ```

  ```go Go
  client := anthropic.NewClient()

  response, err := client.Messages.New(context.TODO(), anthropic.MessageNewParams{
  	Model:     anthropic.ModelClaudeOpus5,
  	MaxTokens: 1024,
  	Tools: []anthropic.ToolUnionParam{
  		{OfTool: &anthropic.ToolParam{
  			Name:        "get_weather",
  			Description: anthropic.String("Get the current weather in a given location"),
  			InputSchema: anthropic.ToolInputSchemaParam{
  				Properties: map[string]any{
  					"location": map[string]any{
  						"type":        "string",
  						"description": "The city and state, e.g. San Francisco, CA",
  					},
  				},
  				Required: []string{"location"},
  			},
  		}},
  	},
  	ToolChoice: anthropic.ToolChoiceUnionParam{OfTool: &anthropic.ToolChoiceToolParam{Name: "get_weather"}},
  	Messages: []anthropic.MessageParam{
  		anthropic.NewUserMessage(anthropic.NewTextBlock("What's the weather like in San Francisco?")),
  	},
  })
  if err != nil {
  	log.Fatal(err)
  }
  fmt.Println(response.RawJSON())
  ```

  ```java Java
  import com.anthropic.models.messages.Tool;
  import com.anthropic.models.messages.Tool.InputSchema;
  import com.anthropic.models.messages.ToolChoice;
  import com.anthropic.models.messages.ToolChoiceTool;
  // ...
  void main() {
      AnthropicClient client = AnthropicOkHttpClient.fromEnv();

      MessageCreateParams params = MessageCreateParams.builder()
          .model(Model.CLAUDE_OPUS_5)
          .maxTokens(1024L)
          .addTool(Tool.builder()
              .name("get_weather")
              .description("Get the current weather in a given location")
              .inputSchema(InputSchema.builder()
                  .properties(JsonValue.from(Map.of(
                      "location", Map.of(
                          "type", "string",
                          "description", "The city and state, e.g. San Francisco, CA"
                      )
                  )))
                  .required(List.of("location"))
                  .build())
              .build())
          .toolChoice(ToolChoice.ofTool(ToolChoiceTool.builder()
              .name("get_weather")
              .build()))
          .addUserMessage("What's the weather like in San Francisco?")
          .build();

      Message response = client.messages().create(params);
      IO.println(response);
  }
  ```

  ```php PHP
  $client = new Client();

  $message = $client->messages->create(
      maxTokens: 1024,
      messages: [
          ['role' => 'user', 'content' => "What's the weather like in San Francisco?"]
      ],
      model: 'claude-opus-5',
      toolChoice: ['type' => 'tool', 'name' => 'get_weather'],
      tools: [
          [
              'name' => 'get_weather',
              'description' => 'Get the current weather in a given location',
              'input_schema' => [
                  'type' => 'object',
                  'properties' => [
                      'location' => [
                          'type' => 'string',
                          'description' => 'The city and state, e.g. San Francisco, CA'
                      ]
                  ],
                  'required' => ['location']
              ]
          ]
      ],
  );
  ```

  ```ruby Ruby
  client = Anthropic::Client.new

  message = client.messages.create(
    model: "claude-opus-5",
    max_tokens: 1024,
    tools: [
      {
        name: "get_weather",
        description: "Get the current weather in a given location",
        input_schema: {
          type: "object",
          properties: {
            location: {
              type: "string",
              description: "The city and state, e.g. San Francisco, CA"
            }
          },
          required: ["location"]
        }
      }
    ],
    tool_choice: { type: "tool", name: "get_weather" },
    messages: [
      { role: "user", content: "What's the weather like in San Francisco?" }
    ]
  )
  puts message
  ```
</CodeGroup>

`tool_choice` 매개변수를 사용할 때는 네 가지 옵션이 있습니다:

* `auto`는 Claude가 제공된 도구를 호출할지 여부를 결정하도록 허용합니다. `tools`가 제공된 경우의 기본값입니다.
* `any`는 Claude에게 제공된 도구 중 하나를 반드시 사용해야 한다고 알리지만, 특정 도구를 강제하지는 않습니다.
* `tool`은 Claude가 항상 특정 도구를 사용하도록 강제합니다.
* `none`은 Claude가 어떤 도구도 사용하지 못하도록 합니다. `tools`가 제공되지 않은 경우의 기본값입니다.

<Note>
  ["prompt caching"(프롬프트 캐싱)](https://platform.claude.com/docs/ko/build-with-claude/prompt-caching#what-invalidates-the-cache)을 사용할 때 `tool_choice` 매개변수를 변경하면 캐시된 메시지 블록이 무효화됩니다. 도구 정의와 시스템 프롬프트는 캐시된 상태로 유지되지만, 메시지 콘텐츠는 다시 처리되어야 합니다.
</Note>

다음 다이어그램은 각 옵션이 작동하는 방식을 보여줍니다:

<Frame>
  ![세 가지 tool\_choice 옵션의 다이어그램: auto(도구 또는 일반 응답), any(도구 중 하나), tool(지정된 도구)](https://platform.claude.com/docs/ko/images/tool_choice.svg)
</Frame>

`tool_choice`가 `any` 또는 `tool`인 경우, API는 도구 사용을 강제하기 위해 어시스턴트 메시지를 미리 채웁니다. 이는 명시적으로 요청하더라도 모델이 `tool_use` 콘텐츠 블록 앞에 자연어 응답이나 설명을 출력하지 않는다는 것을 의미합니다.

테스트 결과 이로 인해 성능이 저하되지는 않는 것으로 나타났습니다. 모델이 특정 도구를 사용하도록 요청하면서도 자연어 컨텍스트나 설명을 제공하기를 원한다면, `tool_choice`에 `{"type": "auto"}`(기본값)를 사용하고 `user` 메시지에 명시적인 지시를 추가할 수 있습니다. 예: `What's the weather like in London? Use the get_weather tool in your response.`

도구를 강제하면 강제 도구 사용을 허용하는 모든 모델에서 사고도 건너뜁니다. 응답은 `tool_use` 블록으로 시작하며 `thinking` 블록이 없습니다. 모델이 도구를 호출하기 전에 사고하도록 하려면, 같은 방식으로 프롬프트 지시와 함께 `auto`를 사용하세요.

<Tip>
  **엄격한 도구를 통한 보장된 도구 호출**

  강제 도구 사용을 지원하는 모델에서는 `tool_choice: {"type": "any"}`를 [엄격한 도구 사용](https://platform.claude.com/docs/ko/agents-and-tools/tool-use/strict-tool-use)과 결합하여 도구 중 하나가 반드시 호출되고 도구 입력이 스키마를 엄격하게 따르도록 보장할 수 있습니다. 스키마 검증을 활성화하려면 도구 정의에 `strict: true`를 설정하세요.
</Tip>

### 도구 사용 시 모델 응답

도구를 사용할 때 Claude는 도구를 호출하기 전에 자신이 수행하는 작업에 대해 설명하거나 사용자에게 자연스럽게 응답하는 경우가 많습니다.

예를 들어, "What's the weather like in San Francisco right now, and what time is it there?"라는 프롬프트가 주어지면 Claude는 다음과 같이 응답할 수 있습니다:

```json JSON
{
  "role": "assistant",
  "content": [
    {
      "type": "text",
      "text": "I'll help you check the current weather and time in San Francisco."
    },
    {
      "type": "tool_use",
      "id": "toolu_01A09q90qw90lq917835lq9",
      "name": "get_weather",
      "input": { "location": "San Francisco, CA" }
    }
  ]
}
```

이러한 자연스러운 응답 스타일은 사용자가 Claude가 무엇을 하고 있는지 이해하는 데 도움이 되며, 보다 대화적인 상호작용을 만들어 냅니다. 시스템 프롬프트를 통해, 그리고 프롬프트에 `<examples>`를 제공하여 이러한 응답의 스타일과 내용을 안내할 수 있습니다.

Claude는 자신의 행동을 설명할 때 다양한 표현과 접근 방식을 사용할 수 있다는 점에 유의해야 합니다. 코드에서는 이러한 응답을 다른 어시스턴트 생성 텍스트와 동일하게 취급해야 하며, 특정 형식 규칙에 의존해서는 안 됩니다.

## 다음 단계

<CardGroup>
  <Card href="https://platform.claude.com/docs/ko/agents-and-tools/tool-use/handle-tool-calls" title="도구 호출 처리하기">
    tool\_use 블록을 파싱하고 tool\_result 응답의 형식을 지정합니다.
  </Card>

  <Card href="https://platform.claude.com/docs/ko/agents-and-tools/tool-use/tool-runner" title="Tool Runner (SDK)">
    SDK가 에이전트 루프를 자동으로 처리하도록 합니다.
  </Card>

  <Card href="https://platform.claude.com/docs/ko/agents-and-tools/tool-use/tool-reference" title="도구 참조">
    Anthropic이 제공하는 도구 및 선택적 속성의 디렉터리입니다.
  </Card>
</CardGroup>
