Практические разборы инструментов выходят в наших каналах.
Что понадобится
Эта инструкция для прямого вызова API из программы, а не для установки навыка в Claude Code. Нужны API-ключ Claude, доступ к выбранной модели и Python 3. Код ниже использует стандартную библиотеку Python и HTTP, поэтому не зависит от того, какую версию SDK ты установил. Ключ передаётся через переменную окружения ANTHROPIC_API_KEY; не вставляй его в текст программы или переписку.
В API есть готовые навыки Anthropic: pptx для презентаций, xlsx для таблиц, docx для документов Word и pdf для PDF. Они подключаются через type: "anthropic". Эта инструкция использует готовый навык, без загрузки своего.
В официальном quickstart, открытом при подготовке материала, использована пара claude-opus-5-5 и code_execution_20260521. Она и взята ниже. Это документально сверенный пример, не отчёт о нашем платном запуске API.
Какие beta-заголовки нужны
Пример следует текущему HTTP-контракту quickstart: заголовки x-api-key, anthropic-version: 2023-06-01, content-type: application/json; anthropic-beta в нём не передаётся. Нельзя брать модель, способ вызова и формат ответа из разных поколений документации.
В документации Files API также указано, что API вышел из beta. Старый files-api-2025-04-14 сохраняет старые форматы ответа; удаление заголовка переключает их на текущие. Поэтому старый пример с client.beta.files нельзя механически объединять с новым.
Здесь мы не мигрируем существующий сервис со старого beta-контракта. Если у тебя уже есть такой сервис, сначала сверь его заголовки и форматы ответа. Самого слова beta в имени SDK-метода недостаточно: документация Files API отдельно оговаривает поведение разных версий SDK.
Если хочешь применять такие инструменты в своём проекте, посмотри описание практикума.
Создай презентацию и скачай файл
Пример отправляет задачу создать пять слайдов о возобновляемой энергии, сохраняет весь ответ в skill-response.json, затем извлекает идентификаторы созданных файлов. Он не берёт путь сохранения из ответа модели: файлы окажутся в новой локальной папке skill-output. Если папка уже существует, программа остановится, чтобы не перезаписать прежний результат.
import json
import os
from pathlib import Path
from urllib.error import HTTPError
from urllib.request import Request, urlopen
API = "https://api.anthropic.com/v1"
KEY = os.environ["ANTHROPIC_API_KEY"]
HEADERS = {
"x-api-key": KEY,
"anthropic-version": "2023-06-01",
"content-type": "application/json",
}
def request(path, payload=None, binary=False):
data = None if payload is None else json.dumps(payload).encode("utf-8")
req = Request(API + path, data=data, headers=HEADERS)
try:
with urlopen(req, timeout=600) as result:
body = result.read()
except HTTPError as error:
raise RuntimeError(f"Claude API HTTP {error.code}; check access and request") from None
return body if binary else json.loads(body)
out = Path("skill-output")
out.mkdir(exist_ok=False)
response = request("/messages", {
"model": "claude-opus-5-5",
"max_tokens": 16000,
"container": {
"skills": [{"type": "anthropic", "skill_id": "pptx", "version": "latest"}]
},
"messages": [{
"role": "user",
"content": "Create a presentation about renewable energy with 5 slides",
}],
"tools": [{"type": "code_execution_20260521", "name": "code_execution"}],
})
(out / "skill-response.json").write_text(
json.dumps(response, ensure_ascii=False, indent=2), encoding="utf-8"
)
print("stop_reason:", response.get("stop_reason"))
file_ids = []
for block in response["content"]:
if block["type"] == "bash_code_execution_tool_result":
result = block["content"]
if result["type"] == "bash_code_execution_result":
for item in result["content"]:
file_id = item.get("file_id")
if file_id and file_id not in file_ids:
file_ids.append(file_id)
if not file_ids:
raise RuntimeError("No generated file_id; inspect skill-response.json")
for index, file_id in enumerate(file_ids, start=1):
from urllib.parse import quote
file_path = "/files/" + quote(file_id, safe="")
metadata = request(file_path)
if metadata.get("downloadable") is not True:
raise RuntimeError("This file cannot be downloaded through Files API")
target = out / f"result-{index}.pptx"
target.write_bytes(request(file_path + "/content", binary=True))
print("Saved:", target)Имена result-1.pptx и далее выбраны для этой задачи с презентацией. Расширение файла не доказывает его содержимое: открой скачанный документ и проверь формат, число слайдов и текст. Не считай успешным результатом один только HTTP 200 или наличие file_id.
Программа выводит stop_reason, причину остановки ответа, и сохраняет полный ответ для проверки. Она не продолжает диалог и не повторяет платный запрос автоматически. Наличие скачанного файла не означает, что вся задача завершена: проверь сохранённый ответ и сам документ, прежде чем решать, нужен ли следующий запрос.
Какие права нужны для файлов
Files API привязывает файлы к workspace, рабочему пространству, а не к отдельному пользователю твоего приложения или переписке. По документации любой API-ключ с доступом к этому workspace может получить доступ к загруженным туда файлам. Для скачивания в примере используется тот же ключ, что и для генерации. Никогда не принимай file_id от конечных пользователей или других недоверенных источников. Храни эти идентификаторы на сервере, а соответствие между пользователями и их файлами веди в своём приложении.
Отдельно проверь метаданные файла: они должны содержать downloadable: true. Документация разрешает скачивать созданные навыками или инструментом выполнения кода файлы; для файлов, загруженных тобой, downloadable: false, а попытка скачивания вернёт 400. Право доступа к workspace и возможность скачать конкретный файл не заменяют друг друга.
Для многопользовательского приложения документация Files API рекомендует отдельный workspace на каждого клиента как границу изоляции файлов. Это рекомендация именно о файлах; не стоит переносить её на все сущности и права без проверки соответствующего API.
Готовый навык и собственный навык
У готовых навыков идентификаторы pptx, xlsx, docx, pdf. В справочнике списка навыков источник custom обозначен как частный для workspace, а anthropic как общий и доступный только для чтения.
version: "latest" в первом примере означает последнюю опубликованную версию навыка. Для воспроизводимой интеграции учитывай, что этот выбор может измениться; переход к фиксированной версии требует выбрать существующую версию используемого навыка, а не выдуманный идентификатор из примера.
Ограничения и следующий шаг
Пример охватывает только создание презентации готовым навыком и скачивание. Загрузка своих навыков, их удаление и доступ к сторонним сервисам здесь не проверялись. Для этих задач нужна отдельная проверка соответствующего API.
Если задача связана с файлами в интерфейсе Claude, есть отдельный разбор как загрузить файл в Claude. Для прямых вызовов пригодится как посчитать расход токенов на API. А для работы в терминальном агенте читай как выбирать навыки Claude Code: это другой способ подключения.
Для первой проверки достаточно одного готового pptx: проверить ответ, скачать разрешённый к скачиванию файл и открыть его. Свои навыки и разграничение доступа между клиентами добавляй после этой проверки.
Новые материалы - дайджестом, без спама
Гайды выходят регулярно. Подпишись, чтобы не пропускать: пришлю подборку в Telegram или на email. Раз в неделю или каждый день - выбираешь сам.

