Anthropic выделяет отдельные правила для входных данных от 20 тысяч токенов и больше. По грубой оценке 20k токенов — это примерно 8–10 страниц документации, или 3–5 средних Kotlin-файлов с тестами рядом, или большой кусок React-компонента с дочерними компонентами. То есть это про реальный сценарий: вы открыли в Claude Code сразу OrderService.kt, OrderCalculationService.kt, MaterialService.kt и попросили разобраться, почему расчёт markupMaterialsPct едет в одной из веток.
Когда в промпт уезжает столько текста, важно не просто «закинуть всё подряд», а разложить по правилам. Anthropic формулирует это так:
When working with large documents or data-rich inputs (20k+ tokens), structure your prompt carefully to get the best results.
Дальше — три конкретных приёма из их документации, плюс в конце пример, как это выглядит в вашем стеке.
Первое правило кажется неочевидным. Подсознательно хочется написать «вот инструкция: проанализируй такие-то файлы», а потом приклеить файлы. Anthropic советует наоборот:
Place your long documents and inputs near the top of your prompt, above your query, instructions, and examples. This can significantly improve performance across all models.
То есть структура такая: сначала большие документы (файлы кода, спецификации, выгрузки данных), и только в самом конце — ваш запрос: «найди баг в расчёте наценки», «объясни, почему интеграционный тест падает», «составь чеклист рефакторинга».
Второе правило — про разметку. Если вы подаёте Claude несколько файлов одновременно, оборачивайте каждый в отдельный тег. Anthropic рекомендует такую структуру: внешний контейнер <documents>, внутри — много <document index="N">, и в каждом документе — <source> с именем файла и <document_content> с самим текстом.
Зачем это: Claude визуально различает, где кончается один файл и начинается другой, и не путает их между собой. И когда он будет ссылаться в ответе на конкретный кусок, он сможет назвать его по source.
Канонический пример из документации Anthropic — он на английском, специально оставлен дословно:
<documents>
<document index="1">
<source>annual_report_2023.pdf</source>
<document_content>
{{ANNUAL_REPORT}}
</document_content>
</document>
<document index="2">
<source>competitor_analysis_q2.xlsx</source>
<document_content>
{{COMPETITOR_ANALYSIS}}
</document_content>
</document>
</documents>
Analyze the annual report and competitor analysis. Identify strategic advantages and recommend Q3 focus areas.
Двойные фигурные скобки {{ANNUAL_REPORT}} — это плейсхолдер. На их место подставляется реальное содержимое файла. И обратите внимание на порядок: сначала весь блок <documents> с данными, и только потом — одна строка с задачей в конце. Это и есть приём 1 в действии.
Третье правило — про то, как заставить Claude быть внимательным к деталям длинного документа. Anthropic называет это «ground responses in quotes»:
For long document tasks, ask Claude to quote relevant parts of the documents first before carrying out its task. This helps Claude cut through the noise of the rest of the document's contents.
Логика простая: вместо «проанализируй вот это» — «сначала выпиши релевантные цитаты в тег <quotes>, потом на их основе сделай выводы». Когда модель сначала вытаскивает важные куски в явный список, она перестаёт реагировать на шум остального текста и опирает (grounds) свой финальный ответ на конкретные строки исходника.
Канонический пример Anthropic — дословно:
You are an AI physician's assistant. Your task is to help doctors diagnose possible patient illnesses.
<documents>
<document index="1">
<source>patient_symptoms.txt</source>
<document_content>
{{PATIENT_SYMPTOMS}}
</document_content>
</document>
<document index="2">
<source>patient_records.txt</source>
<document_content>
{{PATIENT_RECORDS}}
</document_content>
</document>
<document index="3">
<source>patient01_appt_history.txt</source>
<document_content>
{{PATIENT01_APPOINTMENT_HISTORY}}
</document_content>
</document>
</documents>
Find quotes from the patient records and appointment history that are relevant to diagnosing the patient's reported symptoms. Place these in <quotes> tags. Then, based on these quotes, list all information that would help the doctor diagnose the patient's symptoms. Place your diagnostic information in <info> tags.
Этот пример выбран Anthropic не случайно: медицинская карта — длинный шумный текст, и без шага «сначала цитаты» Claude может запросто потерять важное. У вас задачи похожего класса: длинный лог сборки, большой schema.sql, или PR на 2000 строк.
Допустим, у вас падает интеграционный тест JWT-фильтра, и вы хотите, чтобы Claude нашёл причину. У вас на руках: сам тест, фильтр, базовый класс интеграционных тестов и фрагмент Ktor-конфигурации. Это уже четыре куска — типичная зона «длинного контекста».
Промпт по правилам Anthropic будет выглядеть так:
<documents>
<document index="1">
<source>JwtFilterTest.kt</source>
<document_content>
{{JwtFilterTest.kt}}
</document_content>
</document>
<document index="2">
<source>JwtFilter.kt</source>
<document_content>
{{JwtFilter.kt}}
</document_content>
</document>
<document index="3">
<source>IntegrationTestBase.kt</source>
<document_content>
{{IntegrationTestBase.kt}}
</document_content>
</document>
<document index="4">
<source>Application.kt (фрагмент конфигурации Ktor)</source>
<document_content>
{{Application.kt}}
</document_content>
</document>
</documents>
Сначала в теге <quotes> выпиши строки из этих файлов, которые относятся к проверке токена и порядку установки фильтров.
Затем в теге <analysis> объясни, почему JwtFilterTest падает, и предложи минимальную правку.
Что здесь сделано из трёх приёмов сразу:
<document> с понятным <source>. Claude в ответе сможет сослаться: «в JwtFilter.kt, строка такая-то…».<quotes>, потом <analysis>. Модель не начнёт фантазировать про токен, не выписав сначала, что в коде реально написано.В Claude Code вам не обязательно набирать всё это руками: подсунуть файлы можно через интерфейс прикрепления, а текст инструкции написать обычной фразой. Но если вы делаете промпт «программистcки» — копированием в чат — структура выше работает лучше всего.
<pre> подряд без разделителей. Claude будет вынужден угадывать, где заканчивается один файл и начинается другой, особенно если оба на Kotlin и оба содержат класс OrderRepository.<source>. Без имени файла Claude в ответе будет писать «в первом документе…», и вам придётся обратно сопоставлять «первый» с реальным OrderCalculationService.kt.Если хотите глубже понять, почему вообще «положение в промпте» влияет на ответ — отдельная история про то, как языковая модель «читает» длинный вход, разобрана в гайде «Как работают LLM». Здесь — только конкретные приёмы.