Las herramientas ejecutadas en el servidor comparten estas mecánicas: el bloque server_tool_use, la continuación con pause_turn, los turnos que mezclan herramientas de servidor y de cliente, la elegibilidad para "Zero Data Retention" (retención cero de datos), o ZDR, y el filtrado de dominios. Para herramientas individuales, consulta la referencia de herramientas.
El bloque server_tool_use aparece en la respuesta de Claude cuando se ejecuta una herramienta ejecutada en el servidor. Su campo id usa el prefijo srvtoolu_ para distinguirlo de las llamadas a herramientas de cliente:
{
"type": "server_tool_use",
"id": "srvtoolu_01A2B3C4D5E6F7G8H9",
"name": "web_search",
"input": { "query": "latest quantum computing breakthroughs" }
}La API ejecuta la herramienta internamente. Ves la llamada y su resultado en la respuesta, pero no te encargas de la ejecución. A diferencia de los bloques tool_use de cliente, no necesitas responder con un tool_result. El bloque de resultado de la herramienta (por ejemplo, web_search_tool_result para la búsqueda web) sigue al bloque server_tool_use en el mismo turno del asistente, emparejado por tool_use_id. Si Claude llama a una de tus herramientas de cliente al mismo tiempo, el bloque server_tool_use aparece sin su resultado, y la respuesta termina con stop_reason: "tool_use". La API ejecuta la herramienta cuando devuelves los bloques tool_result de cliente en tu siguiente solicitud.
Al usar herramientas de servidor como la búsqueda web, la API ejecuta las llamadas a herramientas en un bucle agéntico del lado del servidor. En un turno de larga duración, la API podría pausar ese bucle y devolver un motivo de detención pause_turn.
Así es como se maneja el motivo de detención pause_turn:
client = anthropic.Anthropic()
# Solicitud inicial con búsqueda web
response = client.messages.create(
model="claude-opus-5",
max_tokens=1024,
messages=[
{
"role": "user",
"content": "Search for comprehensive information about quantum computing breakthroughs in 2025",
}
],
tools=[{"type": "web_search_20250305", "name": "web_search", "max_uses": 10}],
)
# Verifica si la respuesta tiene el stop_reason pause_turn
if response.stop_reason == "pause_turn":
# Continúa la conversación con el contenido pausado
messages = [
{
"role": "user",
"content": "Search for comprehensive information about quantum computing breakthroughs in 2025",
},
{"role": "assistant", "content": response.content},
]
# Envía la solicitud de continuación
continuation = client.messages.create(
model="claude-opus-5",
max_tokens=1024,
messages=messages,
tools=[{"type": "web_search_20250305", "name": "web_search", "max_uses": 10}],
)
print(continuation)
else:
print(response)Al manejar pause_turn:
server_tool_use cuya herramienta aún no se ha ejecutado, y la API devuelve un error de validación si esa herramienta falta en la continuación.stop_reason en cada respuesta y continúa hasta que obtengas un motivo de detención diferente, limitando el número de continuaciones como lo harías con cualquier bucle de reintentos.Para los demás valores de stop_reason y los patrones generales de manejo, consulta Motivos de detención y respaldo.
Claude puede llamar a una herramienta de servidor y a una herramienta de cliente en el mismo grupo de llamadas a herramientas en paralelo, por ejemplo, web_fetch junto con una herramienta definida por el usuario. Una herramienta de cliente es cualquier herramienta que tu código ejecuta y que produce un bloque tool_use, ya sea definida por el usuario o una herramienta de cliente con esquema de Anthropic como la herramienta Bash. Cuando eso sucede, la API no ejecuta la herramienta de servidor. Devuelve la respuesta de inmediato para que puedas ejecutar primero la herramienta de cliente:
stop_reason es "tool_use", no "pause_turn".content contiene el bloque server_tool_use y el bloque tool_use de cliente, pero ningún bloque de resultado para la herramienta de servidor: esa llamada no ha terminado.server_tool_use cuyo id no tenga un bloque de resultado correspondiente en la respuesta. Un bloque mcp_tool_use del conector MCP se comporta de la misma manera. Las llamadas a herramientas de servidor que ya tienen su bloque de resultado en la misma respuesta están completas y no necesitan nada de tu parte.{
"stop_reason": "tool_use",
"content": [
{
"type": "text",
"text": "I'll fetch the article and check your system at the same time."
},
{
"type": "server_tool_use",
"id": "srvtoolu_01HxbWnMRmbWyMfUtJKC45rA",
"name": "web_fetch",
"input": { "url": "https://example.com/article" }
},
{
"type": "tool_use",
"id": "toolu_01PjgRJLbXrXEMZwDNYLnBqk",
"name": "run_command",
"input": { "command": "uname -a" }
}
]
}Para continuar el turno, ejecuta las herramientas de cliente y envía un mensaje de usuario cuyo contenido sea únicamente los bloques tool_result, uno por cada bloque tool_use en esa respuesta. Mantén el mismo array tools: una solicitud de reanudación que ya no define la herramienta de servidor en espera falla con un 400 cuyo mensaje termina en but no `web_fetch` tool was provided.
{
"role": "user",
"content": [
{
"type": "tool_result",
"tool_use_id": "toolu_01PjgRJLbXrXEMZwDNYLnBqk",
"content": "Linux demo-host 6.8.0-52-generic x86_64 GNU/Linux"
}
]
}La API adjunta tus resultados al turno del asistente aún abierto, ejecuta la herramienta de servidor diferida (en el caso de una ejecución de código pausada, la reanuda) y luego permite que Claude continúe. Para una herramienta de servidor que Claude llamó directamente, la siguiente respuesta comienza con el bloque de resultado que responde al id del server_tool_use de la respuesta anterior, seguido del contenido recién generado y un nuevo stop_reason:
{
"stop_reason": "end_turn",
"content": [
{
"type": "web_fetch_tool_result",
"tool_use_id": "srvtoolu_01HxbWnMRmbWyMfUtJKC45rA",
"content": {
"type": "web_fetch_result",
"url": "https://example.com/article",
"content": {
"type": "document",
"source": {
"type": "text",
"media_type": "text/plain",
"data": "Full text content of the article..."
}
}
}
},
{
"type": "text",
"text": "The article argues that... and your machine is running Linux..."
}
]
}Un bloque server_tool_use y su bloque de resultado se emparejan por tool_use_id, no por posición: en este flujo llegan en dos respuestas diferentes, y el bloque server_tool_use no se repite en la segunda. En solicitudes posteriores, mantén todo el intercambio en tu array messages en orden: la primera respuesta como un mensaje assistant, el mensaje de usuario con tool_result y luego la siguiente respuesta como otro mensaje assistant, de la misma manera en que acumulas cualquier otro intercambio de uso de herramientas.
En qué se diferencia esto de pause_turn: Una respuesta pause_turn también puede terminar con un bloque server_tool_use que no se ha ejecutado, pero nunca deja un bloque tool_use de cliente esperándote, por lo que la continúas reenviando el contenido del asistente tal cual. Una respuesta que deja un bloque tool_use de cliente esperándote nunca tiene un stop_reason de pause_turn: cuando Claude se detiene para llamar a tus herramientas, stop_reason es tool_use, y la continúas enviando los bloques tool_result de cliente en lugar de reenviar la respuesta. En ambos casos, la API ejecuta la herramienta de servidor pendiente al inicio de la siguiente solicitud.
El siguiente ejemplo habilita web fetch junto con una herramienta run_command definida por el usuario y maneja la respuesta mixta:
client = anthropic.Anthropic()
tools = [
{"type": "web_fetch_20250910", "name": "web_fetch", "max_uses": 5},
{
"name": "run_command",
"description": "Run a shell command on this computer and return its output.",
"input_schema": {
"type": "object",
"properties": {
"command": {"type": "string", "description": "The command to run"}
},
"required": ["command"],
},
},
]
messages = [
{
"role": "user",
"content": "Summarize https://example.com/article and run uname -a to tell me what system this is on.",
}
]
response = client.messages.create(
model="claude-opus-4-8", max_tokens=1024, tools=tools, messages=messages
)
tool_results = [
{
"type": "tool_result",
"tool_use_id": block.id,
# Ejecuta tu herramienta aquí. Este ejemplo devuelve una cadena fija.
"content": "Linux demo-host 6.8.0-52-generic x86_64 GNU/Linux",
}
for block in response.content
if block.type == "tool_use"
]
if response.stop_reason == "tool_use" and tool_results:
# Un bloque server_tool_use sin bloque de resultado en esta respuesta no ha terminado; su resultado llega en una respuesta posterior.
# Envía de vuelta solo los bloques tool_result del cliente, con las mismas herramientas.
continuation = client.messages.create(
model="claude-opus-4-8",
max_tokens=1024,
tools=tools,
messages=[
*messages,
{"role": "assistant", "content": response.content},
{"role": "user", "content": tool_results},
],
)
# Si un web_fetch fue diferido, se ejecuta en esta solicitud y su
# web_fetch_tool_result es el primer bloque de continuation.content.
print(continuation)
else:
print(response)Este código también es correcto cuando Claude no mezcla los dos tipos de llamada. Un turno con solo bloques tool_use de cliente sigue la misma ruta de continuación, y un turno con solo llamadas a herramientas de servidor no necesita bloques tool_result de cliente de tu parte: sus bloques de resultado normalmente ya están presentes, y uno que regresa suspendido, como una respuesta pause_turn, se reenvía tal cual en su lugar.
Las versiones básicas de búsqueda web (web_search_20250305) y web fetch (web_fetch_20250910) son elegibles para Zero Data Retention (ZDR).
Las versiones _20260209 y posteriores con filtrado dinámico no son elegibles para ZDR de forma predeterminada porque el filtrado dinámico depende internamente de la ejecución de código.
Para usar una herramienta de servidor _20260209 o posterior con ZDR, desactiva el filtrado dinámico estableciendo "allowed_callers": ["direct"] en la herramienta:
{
"type": "web_search_20260209",
"name": "web_search",
"allowed_callers": ["direct"]
}Esto restringe la herramienta únicamente a la invocación directa, omitiendo el paso interno de ejecución de código.
allowed_callers controla cómo se puede invocar una herramienta: directamente por Claude ("direct"), desde dentro de un contenedor de ejecución de código (por ejemplo, "code_execution_20260120") o ambos. Las versiones _20260209 de las herramientas web usan de forma predeterminada solo el llamador de ejecución de código; las versiones anteriores usan de forma predeterminada ["direct"]. En modelos que no admiten la llamada programática de herramientas, estas versiones requieren allowed_callers: ["direct"]; sin ello, la API devuelve un error de validación que indica que debes establecerlo.
Las herramientas de servidor que acceden a la web aceptan los parámetros allowed_domains y blocked_domains para controlar a qué dominios puede acceder Claude. Ambos son campos del objeto de la herramienta:
{
"type": "web_search_20250305",
"name": "web_search",
"allowed_domains": ["example.com", "docs.python.org"]
}Al usar filtros de dominio:
example.com en lugar de https://example.com).example.com cubre docs.example.com).docs.example.com devuelve solo resultados de ese subdominio, no de example.com ni de api.example.com).example.com/blog coincide con example.com/blog/post-1).allowed_domains o blocked_domains, pero no ambos en la misma solicitud.Compatibilidad con comodines:
*) no están permitidos en el dominio en sí, solo en la ruta que le sigue.example.com/*, example.com/*/articles*.example.com, ex*.comLos formatos de dominio inválidos se rechazan en el momento de la solicitud con un 400 invalid_request_error.
Las versiones _20260209 y posteriores de búsqueda web y web fetch usan la ejecución de código internamente para aplicar filtros dinámicos a los resultados de búsqueda.
Los eventos de herramientas de servidor se transmiten por streaming como parte del flujo normal de "server-sent events" (eventos enviados por el servidor), o SSE. Un bloque server_tool_use que Claude llama directamente se transmite como un bloque tool_use de cliente: un evento content_block_start seguido de eventos input_json_delta. El bloque de resultado llega completo en un único evento content_block_start, sin deltas.
Consulta Streaming para ver la referencia completa de eventos. Las páginas de herramientas individuales documentan los nombres de eventos específicos de cada herramienta cuando difieren.
Todas las herramientas de servidor admiten el procesamiento por lotes. En un lote, el bucle agéntico se ejecuta igual que para las solicitudes síncronas, con un límite de iteraciones por turno más alto. Si el bucle alcanza ese límite, la respuesta termina con stop_reason: "pause_turn"; puedes continuarla enviando una solicitud de seguimiento con el contenido devuelto. Consulta Herramientas de servidor y el bucle agéntico para más detalles.
Las cargas de trabajo por lotes comunes incluyen enriquecer un conjunto de datos con información de la web, verificar un gran conjunto de documentos contra fuentes actuales y ejecutar código de análisis sobre muchos archivos.
Corrige los errores más comunes del uso de herramientas con tablas de diagnóstico de síntoma a solución.
Busca en la web y cita los resultados.
Obtén y lee contenido de URLs específicas para ampliar el contexto de Claude con contenido web en vivo.
Ejecuta código Python y bash en un contenedor aislado para analizar datos, generar archivos e iterar sobre soluciones.
Descubre y carga herramientas bajo demanda.
Was this page helpful?