---
title: Сжатие и сохранённые размышления
url: https://platform.claude.com/docs/ru/build-with-claude/compaction-thinking-blocks
description: Когда блоки размышлений в ходах, сохранённых после сжатия по запросу, остаются действительными на моделях с сохраняемыми размышлениями, и как это проверить.
featureMetadata:
  status: beta
  betaHeader: compact-2026-09-04
  supportedModels:
    - claude-fable-5-1
    - claude-mythos-5-1
    - claude-fable-5
    - claude-mythos-5
    - claude-mythos-preview
    - claude-opus-5-5
    - claude-opus-5
    - claude-opus-4-8
    - claude-opus-4-7
    - claude-opus-4-6
    - claude-sonnet-5-5
    - claude-sonnet-5
    - claude-sonnet-4-6
    - claude-haiku-5-5
  supportedPlatforms:
    Claude API: beta
    Claude Platform on AWS: beta
    Google Cloud: beta
    Microsoft Foundry: beta
---

Пропустите эту страницу, если только вы не отправляете «thinking blocks» (блоки размышлений) обратно модели с «preserved thinking» ([сохранёнными размышлениями](https://platform.claude.com/docs/ru/build-with-claude/preserved-thinking)) и не сохраняете ходы после блока «compaction» (сжатия). «Kept turns» (сохранённые ходы) — это ходы, следующие за блоком: недавние ходы, которые вы не включили в запрос на сжатие, как в разделе [Сжатие с сохранением последних ходов](https://platform.claude.com/docs/ru/build-with-claude/compaction-keep-recent-turns), или ходы, поступившие во время написания сводки, как в разделе [Сжатие в фоновом режиме](https://platform.claude.com/docs/ru/build-with-claude/compaction-background).

Модели с сохранёнными размышлениями сверяют более ранние блоки размышлений с диалогом, в котором они были созданы. Сводка заменяет часть этого диалога, но проверка принимает такую замену, если сводку написал API, поэтому размышления в сохранённых ходах могут оставаться действительными.

## Условия, при которых сохранённые размышления остаются действительными

Блоки размышлений в сохранённых ходах остаются действительными, пока выполняются все следующие условия:

* **Запрос на сжатие выполняется на модели с сохранёнными размышлениями.** Это условие распространяется на каждый запрос на сжатие с момента создания блока размышлений, а не только на самый последний. Один из способов его выполнить — отправлять каждый запрос на сжатие той модели, которую использует диалог.
* **Сохранённые ходы непосредственно следуют за суммированными сообщениями, и вы отправляете их без изменений.** Отправляйте каждое сохранённое сообщение точно в том виде, в каком оно есть в вашей истории. Не пропускайте и не добавляйте сообщения между последним суммированным сообщением и первым сохранённым. Первое сохранённое сообщение также должно иметь роль, отличную от роли последнего суммированного сообщения, и оно не может быть сообщением `role: "system"` в середине диалога. В противном случае API объединит его с последним суммированным сообщением. Один из способов правильно сформировать первое сохранённое сообщение — сжать ровно `messages` запроса, который вы уже отправили. Тогда сохранённые ходы начнутся с ответа Claude на него.
* **`system` и те `tools`, которые не помечены `defer_loading: true`, не меняются.** Они одинаковы в запросе на сжатие и в запросах, в которых были созданы сохранённые размышления, и остаются такими же в последующих запросах. В разделе [Изменение системной подсказки или инструментов](https://platform.claude.com/docs/ru/build-with-claude/compaction-thinking-blocks#change-the-system-prompt-or-tools) описано, как безопасно их изменить.

Если какое-либо условие не выполняется, при сжатии ничего не завершается ошибкой, и API в любом случае принимает блок в последующих запросах. Сбой происходит при первом последующем запросе, который отправляет сохранённые размышления туда, где API применяет проверку: по умолчанию это ошибка 400, а если в запросе для `thinking.block_binding.prefix_mismatch_behavior` задано значение `"drop_block"`, — отброшенные блоки размышлений. В Message Batches API элемент, в котором это поле не задано, не завершается ошибкой. Там, где проверка применяется по умолчанию, API вместо этого отбрасывает блоки. В разделе [Что API делает с недействительным блоком](https://platform.claude.com/docs/ru/build-with-claude/preserved-thinking#mismatch-behavior) описаны оба исхода, а в разделе [Когда API применяет проверку](https://platform.claude.com/docs/ru/build-with-claude/preserved-thinking#enforcement) указано, какие запросы проверяются.

## Повторное сжатие без нарушения более ранних размышлений

Вы можете [выполнить сжатие повторно](https://platform.claude.com/docs/ru/build-with-claude/compaction-on-demand#compact-again) и сохранить ходы: новый блок охватывает старую сводку и каждое следующее за ней сообщение в запросе на сжатие, а любые ходы, которые вы не включили в этот запрос, становятся сохранёнными ходами нового блока.

Первое из [условий для сохранённых размышлений](https://platform.claude.com/docs/ru/build-with-claude/compaction-thinking-blocks#conditions-for-kept-thinking-to-stay-valid) учитывает каждое сжатие с момента создания блока размышлений, поэтому для хода, который вы сохраняете на протяжении двух сжатий, оба сжатия должны быть выполнены на модели с сохранёнными размышлениями.

Сжатия, выполненные до создания блока размышлений, на него не влияют. Размышления, созданные после появления блока, привязаны к этому блоку и остаются действительными при последующих сжатиях, удовлетворяющих условиям.

## Изменение системной подсказки или инструментов

В последующем запросе можно использовать другой `system`, другие `tools` или другую модель, чем в запросе на сжатие, и API всё равно примет блок. Такое изменение может сделать недействительными размышления в сохранённых ходах, но других последствий у него нет.

Чтобы изменить `system` или `tools`, не делая недействительными сохранённые размышления, сначала сожмите весь диалог, чтобы не осталось сохранённых ходов. Затем измените их в следующем запросе.

Чтобы добавить инструкцию или изменить доступные инструменты, не затрагивая `system` или `tools`, добавьте изменение в `messages`, как описано в разделе [Внесение изменений без редактирования префикса](https://platform.claude.com/docs/ru/build-with-claude/preserved-thinking#replace-prefix-edits).

Системные сообщения в середине разговора внутри суммированных ходов тоже попадают в сводку, поэтому их текстовые инструкции перестают действовать после замены. Уровень [усилий для отдельного сообщения](https://platform.claude.com/docs/ru/build-with-claude/effort#change-effort-mid-conversation-beta), который они задают, также не переносится: пока более позднее сообщение не задаст уровень, ходы выполняются с `output_config.effort` верхнего уровня запроса или со значением модели по умолчанию, если вы его не задали. Чтобы инструкция или уровень усилий продолжали действовать, повторите их в сообщении `role: "system"` сразу после первого нового хода `user`, следующего за сохранёнными ходами. Изменения инструментов внутри этих ходов переносятся сами, если запрос на сжатие также содержит `inline-tools-2026-09-15`: возвращённый блок записывает их итоговый эффект в своё поле `tool_changes`, поэтому отправляйте блок обратно без изменений. Если у блока нет поля `tool_changes`, повторите эти изменения инструментов тем же способом. Системное сообщение, размещённое между блоком и сохранёнными ходами, нарушает их размышления.

## Проверка того, что сохранённые размышления остались действительными

Ответ на запрос сжатия не сообщает, остаются ли сохранённые размышления действительными. Это показывает первый запрос после замены. Чтобы проверить это в своих тестах:

1. Проведите короткий диалог с включёнными размышлениями. Используйте модель, на которой API выполняет проверку (см. [Когда API применяет проверку](https://platform.claude.com/docs/ru/build-with-claude/preserved-thinking#enforcement)), и используйте её на каждом шаге, поскольку модель, которая не может прочитать блок размышлений, отбрасывает его без ошибки.
2. Сожмите более ранние ходы и сохраните как минимум один ход, содержащий блок размышлений.
3. Отправьте следующий запрос: сначала блок, затем сохранённый ход, затем новое сообщение `user`, а для `thinking.block_binding.prefix_mismatch_behavior` задайте значение `"error"`.
4. Прочитайте результат. Ответ 200 с пустым массивом `input_transformations` означает, что ни один блок размышлений не провалил проверку и не был отброшен. Ошибка 400 с сообщением о том, что блок привязан к другому диалогу, означает, что такой блок есть. Сообщение начинается с пути к первому блоку, не прошедшему проверку, а в разделе [Что API делает с недействительным блоком](https://platform.claude.com/docs/ru/build-with-claude/preserved-thinking#mismatch-behavior) оно приведено полностью.

Для поля `prefix_mismatch_behavior` требуется бета-заголовок `thinking-binding-controls-2026-08-01` в дополнение к [бета-заголовку `compact-2026-09-04`](https://platform.claude.com/docs/ru/build-with-claude/compaction-on-demand#request-a-summary). Установка этого поля также включает проверку для запроса в аккаунтах, где проверка не включена по умолчанию.

Следующая программа выполняет эти четыре шага. Она выводит, сколько блоков размышлений содержит сохранённый ход и сколько записей содержит `input_transformations`; отсутствие записей означает, что сохранённые размышления остались действительными:

<CodeGroup exclude="shell">
  ```python Python
  from anthropic.types.beta import BetaMessageParam, BetaThinkingConfigParam

  client = anthropic.Anthropic()

  # Claude Fable 5.1 — первая модель, которая сверяет возвращённые ей блоки размышлений с ходом диалога.
  MODEL = "claude-fable-5-1"
  BETAS = ["compact-2026-09-04", "thinking-binding-controls-2026-08-01"]
  SYSTEM = "You help plan a recipe app's release. Keep answers short."
  # При значении "error" блок размышлений, не прошедший проверку, приводит к ошибке запроса с кодом 400.
  THINKING: BetaThinkingConfigParam = {
      "type": "adaptive",
      "block_binding": {"prefix_mismatch_behavior": "error"},
  }

  # 1. Проведите короткий диалог с включёнными размышлениями.
  history: list[BetaMessageParam] = [
      {"role": "user", "content": "What are the main entities in the app's data model?"}
  ]
  first = client.beta.messages.create(
      model=MODEL,
      max_tokens=8192,
      system=SYSTEM,
      betas=BETAS,
      thinking=THINKING,
      messages=history,
  )
  history += [
      {"role": "assistant", "content": first.content},
      {
          "role": "user",
          "content": "Testing starts on Tuesday, March 3, 2026, takes 10 weekdays, and pauses on March 9 and March 16. On which date does it end?",
      },
  ]
  second = client.beta.messages.create(
      model=MODEL,
      max_tokens=8192,
      system=SYSTEM,
      betas=BETAS,
      thinking=THINKING,
      messages=history,
  )
  history.append({"role": "assistant", "content": second.content})
  thinking_blocks = sum(block.type == "thinking" for block in second.content)
  print(f"Thinking blocks in the kept turn: {thinking_blocks}")

  # 2. Кратко изложите первый ход. Второй ход в запрос не включается.
  summary = client.beta.messages.create(
      model=MODEL,
      max_tokens=4096,
      system=SYSTEM,
      betas=BETAS,
      thinking=THINKING,
      messages=history[:2],
      compaction={"type": "summarize"},
  )
  if summary.stop_reason != "compaction":
      raise SystemExit(f"No summary: {summary.stop_reason}")

  # 3. Поместите блок перед сохранённым ходом и задайте следующий вопрос.
  history = [
      {"role": "assistant", "content": summary.content},
      *history[2:],
      {"role": "user", "content": "Which day should the release go out?"},
  ]
  third = client.beta.messages.create(
      model=MODEL,
      max_tokens=8192,
      system=SYSTEM,
      betas=BETAS,
      thinking=THINKING,
      messages=history,
  )

  # 4. Ответ 200 без отброшенных блоков означает, что сохранённые размышления прошли проверку.
  print(f"Dropped thinking blocks: {len(third.input_transformations)}")
  ```

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

  // Claude Fable 5.1 — первая модель, которая сверяет возвращённые блоки размышлений с ходом диалога.
  const model: Anthropic.Model = "claude-fable-5-1";
  const betas: Anthropic.Beta.AnthropicBeta[] = [
    "compact-2026-09-04",
    "thinking-binding-controls-2026-08-01"
  ];
  const systemPrompt = "You help plan a recipe app's release. Keep answers short.";
  // При значении "error" блок размышлений, не прошедший проверку, приводит к ошибке запроса с кодом 400.
  const thinking: Anthropic.Beta.Messages.BetaThinkingConfigParam = {
    type: "adaptive",
    block_binding: { prefix_mismatch_behavior: "error" }
  };

  // 1. Проведите короткий диалог с включёнными размышлениями.
  let history: Anthropic.Beta.Messages.BetaMessageParam[] = [
    { role: "user", content: "What are the main entities in the app's data model?" }
  ];
  const first = await client.beta.messages.create({
    model,
    max_tokens: 8192,
    system: systemPrompt,
    betas,
    thinking,
    messages: history
  });
  history.push(
    { role: "assistant", content: first.content },
    {
      role: "user",
      content:
        "Testing starts on Tuesday, March 3, 2026, takes 10 weekdays, and pauses on March 9 and March 16. On which date does it end?"
    }
  );
  const second = await client.beta.messages.create({
    model,
    max_tokens: 8192,
    system: systemPrompt,
    betas,
    thinking,
    messages: history
  });
  history.push({ role: "assistant", content: second.content });
  const thinkingBlocks = second.content.filter((block) => block.type === "thinking").length;
  console.log(`Thinking blocks in the kept turn: ${thinkingBlocks}`);

  // 2. Составьте сводку первого хода. Второй ход в запрос не включается.
  const summary = await client.beta.messages.create({
    model,
    max_tokens: 4096,
    system: systemPrompt,
    betas,
    thinking,
    messages: history.slice(0, 2),
    compaction: { type: "summarize" }
  });
  if (summary.stop_reason !== "compaction") {
    throw new Error(`No summary: ${summary.stop_reason}`);
  }

  // 3. Поместите блок перед сохранённым ходом и задайте следующий вопрос.
  history = [
    { role: "assistant", content: summary.content },
    ...history.slice(2),
    { role: "user", content: "Which day should the release go out?" }
  ];
  const third = await client.beta.messages.create({
    model,
    max_tokens: 8192,
    system: systemPrompt,
    betas,
    thinking,
    messages: history
  });

  // 4. Ответ 200 без отброшенных блоков означает, что сохранённые размышления прошли проверку.
  console.log(`Dropped thinking blocks: ${third.input_transformations?.length ?? 0}`);
  ```

  ```csharp C#
  using Anthropic.Models.Beta;
  using Anthropic.Models.Beta.Messages;
  using Model = Anthropic.Models.Messages.Model;

  AnthropicClient client = new();

  // Claude Fable 5.1 — первая модель, которая сверяет возвращённые блоки размышлений с ходом диалога.
  const Model ModelId = Model.ClaudeFable5_1;
  AnthropicBeta[] betas = [AnthropicBeta.Compact2026_09_04, AnthropicBeta.ThinkingBindingControls2026_08_01];
  const string SystemPrompt = "You help plan a recipe app's release. Keep answers short.";
  // При значении "error" блок размышлений, не прошедший проверку, приводит к ошибке запроса с кодом 400.
  BetaThinkingConfigAdaptive thinking = new()
  {
      BlockBinding = new() { PrefixMismatchBehavior = BetaThinkingPrefixMismatchBehavior.Error },
  };

  // 1. Проведите короткий диалог с включёнными размышлениями.
  List<BetaMessageParam> history =
  [
      new() { Role = Role.User, Content = "What are the main entities in the app's data model?" },
  ];
  var first = await client.Beta.Messages.Create(new MessageCreateParams
  {
      Model = ModelId,
      MaxTokens = 8192,
      System = SystemPrompt,
      Betas = [.. betas],
      Thinking = thinking,
      Messages = history,
  });
  history.AddRange(
  [
      new()
      {
          Role = Role.Assistant,
          Content = first.Content.Select(block => new BetaContentBlockParam(block.Json)).ToList(),
      },
      new()
      {
          Role = Role.User,
          Content = "Testing starts on Tuesday, March 3, 2026, takes 10 weekdays, and pauses on March 9 and March 16. On which date does it end?",
      },
  ]);
  var second = await client.Beta.Messages.Create(new MessageCreateParams
  {
      Model = ModelId,
      MaxTokens = 8192,
      System = SystemPrompt,
      Betas = [.. betas],
      Thinking = thinking,
      Messages = history,
  });
  history.Add(new()
  {
      Role = Role.Assistant,
      Content = second.Content.Select(block => new BetaContentBlockParam(block.Json)).ToList(),
  });
  var thinkingBlocks = second.Content.Count(block => block.TryPickThinking(out _));
  Console.WriteLine($"Thinking blocks in the kept turn: {thinkingBlocks}");

  // 2. Кратко изложите первый ход. Второй ход в запрос не включается.
  var summary = await client.Beta.Messages.Create(new MessageCreateParams
  {
      Model = ModelId,
      MaxTokens = 4096,
      System = SystemPrompt,
      Betas = [.. betas],
      Thinking = thinking,
      Messages = history[..2],
      Compaction = new BetaCompactionConfig(), // type defaults to "summarize"
  });
  if (summary.StopReason != BetaStopReason.Compaction)
  {
      throw new InvalidOperationException($"No summary: {summary.StopReason?.Raw()}");
  }

  // 3. Поместите блок перед сохранённым ходом и задайте следующий вопрос.
  history =
  [
      new()
      {
          Role = Role.Assistant,
          Content = summary.Content.Select(block => new BetaContentBlockParam(block.Json)).ToList(),
      },
      .. history[2..],
      new() { Role = Role.User, Content = "Which day should the release go out?" },
  ];
  var third = await client.Beta.Messages.Create(new MessageCreateParams
  {
      Model = ModelId,
      MaxTokens = 8192,
      System = SystemPrompt,
      Betas = [.. betas],
      Thinking = thinking,
      Messages = history,
  });

  // 4. Ответ 200 без отброшенных блоков означает, что сохранённые размышления прошли проверку.
  Console.WriteLine($"Dropped thinking blocks: {third.InputTransformations?.Count ?? 0}");
  ```

  ```go Go
  ctx := context.Background()
  client := anthropic.NewClient()

  // Claude Fable 5.1 — первая модель, которая сверяет возвращённые ей блоки размышлений с ходом диалога.
  const model = anthropic.ModelClaudeFable5_1
  betas := []anthropic.AnthropicBeta{
  	anthropic.AnthropicBetaCompact2026_09_04,
  	anthropic.AnthropicBetaThinkingBindingControls2026_08_01,
  }
  system := []anthropic.BetaTextBlockParam{{Text: "You help plan a recipe app's release. Keep answers short."}}
  // При значении "error" блок размышлений, не прошедший проверку, приводит к ошибке запроса с кодом 400.
  thinking := anthropic.BetaThinkingConfigParamUnion{
  	OfAdaptive: &anthropic.BetaThinkingConfigAdaptiveParam{
  		BlockBinding: anthropic.BetaThinkingBlockBindingParam{
  			PrefixMismatchBehavior: anthropic.BetaThinkingPrefixMismatchBehaviorError,
  		},
  	},
  }

  // 1. Проведите короткий диалог с включёнными размышлениями.
  history := []anthropic.BetaMessageParam{
  	anthropic.NewBetaUserMessage(anthropic.NewBetaTextBlock("What are the main entities in the app's data model?")),
  }
  first, err := client.Beta.Messages.New(ctx, anthropic.BetaMessageNewParams{
  	Model:     model,
  	MaxTokens: 8192,
  	System:    system,
  	Betas:     betas,
  	Thinking:  thinking,
  	Messages:  history,
  })
  if err != nil {
  	log.Fatal(err)
  }
  history = append(history,
  	first.ToParam(),
  	anthropic.NewBetaUserMessage(anthropic.NewBetaTextBlock("Testing starts on Tuesday, March 3, 2026, takes 10 weekdays, and pauses on March 9 and March 16. On which date does it end?")),
  )
  second, err := client.Beta.Messages.New(ctx, anthropic.BetaMessageNewParams{
  	Model:     model,
  	MaxTokens: 8192,
  	System:    system,
  	Betas:     betas,
  	Thinking:  thinking,
  	Messages:  history,
  })
  if err != nil {
  	log.Fatal(err)
  }
  history = append(history, second.ToParam())
  thinkingBlocks := 0
  for _, block := range second.Content {
  	if _, ok := block.AsAny().(anthropic.BetaThinkingBlock); ok {
  		thinkingBlocks++
  	}
  }
  fmt.Printf("Thinking blocks in the kept turn: %d\n", thinkingBlocks)

  // 2. Сделайте сводку первого хода. Второй ход не включается в запрос.
  summary, err := client.Beta.Messages.New(ctx, anthropic.BetaMessageNewParams{
  	Model:     model,
  	MaxTokens: 4096,
  	System:    system,
  	Betas:     betas,
  	Thinking:  thinking,
  	Messages:  history[:2],
  	Compaction: anthropic.BetaCompactionConfigUnionParam{
  		OfSummarize: &anthropic.BetaSummarizeCompactionParam{},
  	},
  })
  if err != nil {
  	log.Fatal(err)
  }
  if summary.StopReason != anthropic.BetaStopReasonCompaction {
  	log.Fatalf("No summary: %s", summary.StopReason)
  }

  // 3. Поместите блок перед сохранённым ходом и задайте следующий вопрос.
  history = slices.Concat(
  	[]anthropic.BetaMessageParam{summary.ToParam()},
  	history[2:],
  	[]anthropic.BetaMessageParam{anthropic.NewBetaUserMessage(anthropic.NewBetaTextBlock("Which day should the release go out?"))},
  )
  third, err := client.Beta.Messages.New(ctx, anthropic.BetaMessageNewParams{
  	Model:     model,
  	MaxTokens: 8192,
  	System:    system,
  	Betas:     betas,
  	Thinking:  thinking,
  	Messages:  history,
  })
  if err != nil {
  	log.Fatal(err)
  }

  // 4. Ответ 200 без отброшенных блоков означает, что сохранённые размышления прошли проверку.
  fmt.Printf("Dropped thinking blocks: %d\n", len(third.InputTransformations))
  ```

  ```java Java
  import com.anthropic.models.beta.AnthropicBeta;
  import com.anthropic.models.beta.messages.BetaCompactionConfig;
  import com.anthropic.models.beta.messages.BetaContentBlock;
  import com.anthropic.models.beta.messages.BetaMessageParam;
  import com.anthropic.models.beta.messages.BetaStopReason;
  import com.anthropic.models.beta.messages.BetaThinkingBlockBinding;
  import com.anthropic.models.beta.messages.BetaThinkingConfigAdaptive;
  import com.anthropic.models.beta.messages.BetaThinkingPrefixMismatchBehavior;
  import com.anthropic.models.beta.messages.MessageCreateParams;

  // Claude Fable 5.1 — первая модель, которая сверяет возвращённые ей блоки размышлений с ходом диалога.
  static final Model MODEL = Model.CLAUDE_FABLE_5_1;
  static final List<AnthropicBeta> BETAS = List.of(
      AnthropicBeta.COMPACT_2026_09_04,
      AnthropicBeta.THINKING_BINDING_CONTROLS_2026_08_01
  );
  static final String SYSTEM = "You help plan a recipe app's release. Keep answers short.";
  // При значении "error" блок размышлений, не прошедший проверку, приводит к ошибке запроса с кодом 400.
  static final BetaThinkingConfigAdaptive THINKING = BetaThinkingConfigAdaptive.builder()
      .blockBinding(BetaThinkingBlockBinding.builder()
          .prefixMismatchBehavior(BetaThinkingPrefixMismatchBehavior.ERROR)
          .build())
      .build();

  void main() {
      var client = AnthropicOkHttpClient.fromEnv();

      // 1. Проведите короткий диалог с включёнными размышлениями.
      var history = new ArrayList<BetaMessageParam>();
      history.add(BetaMessageParam.builder()
          .role(BetaMessageParam.Role.USER)
          .content("What are the main entities in the app's data model?")
          .build());
      var firstParams = MessageCreateParams.builder()
          .model(MODEL)
          .maxTokens(8192)
          .system(SYSTEM)
          .betas(BETAS)
          .thinking(THINKING)
          .messages(history)
          .build();
      var first = client.beta().messages().create(firstParams);
      history.add(first.toParam());
      history.add(BetaMessageParam.builder()
          .role(BetaMessageParam.Role.USER)
          .content("Testing starts on Tuesday, March 3, 2026, takes 10 weekdays, and pauses on March 9 and March 16. On which date does it end?")
          .build());
      var secondParams = MessageCreateParams.builder()
          .model(MODEL)
          .maxTokens(8192)
          .system(SYSTEM)
          .betas(BETAS)
          .thinking(THINKING)
          .messages(history)
          .build();
      var second = client.beta().messages().create(secondParams);
      history.add(second.toParam());
      long thinkingBlocks = second.content().stream().filter(BetaContentBlock::isThinking).count();
      IO.println("Thinking blocks in the kept turn: " + thinkingBlocks);

      // 2. Сделайте сводку первого хода. Второй ход в запрос не включается.
      var firstTurn = history.subList(0, 2);
      var summaryParams = MessageCreateParams.builder()
          .model(MODEL)
          .maxTokens(4096)
          .system(SYSTEM)
          .betas(BETAS)
          .thinking(THINKING)
          .messages(firstTurn)
          .compaction(BetaCompactionConfig.builder().build()) // type defaults to "summarize"
          .build();
      var summary = client.beta().messages().create(summaryParams);
      if (!summary.stopReason().map(BetaStopReason.COMPACTION::equals).orElse(false)) {
          throw new IllegalStateException("No summary: " + summary.stopReason().orElseThrow());
      }

      // 3. Поместите блок перед сохранённым ходом и задайте следующий вопрос.
      firstTurn.clear();
      history.addFirst(summary.toParam());
      history.add(BetaMessageParam.builder()
          .role(BetaMessageParam.Role.USER)
          .content("Which day should the release go out?")
          .build());
      var thirdParams = MessageCreateParams.builder()
          .model(MODEL)
          .maxTokens(8192)
          .system(SYSTEM)
          .betas(BETAS)
          .thinking(THINKING)
          .messages(history)
          .build();
      var third = client.beta().messages().create(thirdParams);

      // 4. Ответ 200 без отброшенных блоков означает, что сохранённые размышления прошли проверку.
      IO.println("Dropped thinking blocks: " + third.inputTransformations().map(List::size).orElse(0));
  }
  ```

  ```php PHP
  use Anthropic\Beta\AnthropicBeta;
  use Anthropic\Beta\Messages\BetaCompactionConfig;
  use Anthropic\Beta\Messages\BetaMessageParam;
  use Anthropic\Beta\Messages\BetaMessageParam\Role;
  use Anthropic\Beta\Messages\BetaStopReason;
  use Anthropic\Beta\Messages\BetaThinkingBlock;
  use Anthropic\Beta\Messages\BetaThinkingBlockBinding;
  use Anthropic\Beta\Messages\BetaThinkingConfigAdaptive;
  use Anthropic\Beta\Messages\BetaThinkingPrefixMismatchBehavior;

  $client = new Client();

  // Claude Fable 5.1 — первая модель, которая сверяет возвращённые блоки размышлений с ходом диалога.
  const MODEL = Model::CLAUDE_FABLE_5_1;
  const BETAS = [AnthropicBeta::COMPACT_2026_09_04, AnthropicBeta::THINKING_BINDING_CONTROLS_2026_08_01];
  const SYSTEM = "You help plan a recipe app's release. Keep answers short.";
  // При значении "error" блок размышлений, не прошедший проверку, приводит к ошибке запроса с кодом 400.
  $thinking = BetaThinkingConfigAdaptive::with(
      blockBinding: BetaThinkingBlockBinding::with(
          prefixMismatchBehavior: BetaThinkingPrefixMismatchBehavior::ERROR,
      ),
  );

  // 1. Проведите короткий диалог с включёнными размышлениями.
  $history = [
      BetaMessageParam::with(role: Role::USER, content: "What are the main entities in the app's data model?"),
  ];
  $first = $client->beta->messages->create(
      model: MODEL,
      maxTokens: 8192,
      system: SYSTEM,
      betas: BETAS,
      thinking: $thinking,
      messages: $history,
  );
  $history[] = BetaMessageParam::with(role: Role::ASSISTANT, content: $first->content);
  $history[] = BetaMessageParam::with(
      role: Role::USER,
      content: 'Testing starts on Tuesday, March 3, 2026, takes 10 weekdays, and pauses on March 9 and March 16. On which date does it end?',
  );
  $second = $client->beta->messages->create(
      model: MODEL,
      maxTokens: 8192,
      system: SYSTEM,
      betas: BETAS,
      thinking: $thinking,
      messages: $history,
  );
  $history[] = BetaMessageParam::with(role: Role::ASSISTANT, content: $second->content);
  $thinkingBlocks = count(array_filter($second->content, fn ($block) => $block instanceof BetaThinkingBlock));
  printf("Thinking blocks in the kept turn: %d\n", $thinkingBlocks);

  // 2. Сделайте сводку первого хода. Второй ход в запрос не включается.
  $summary = $client->beta->messages->create(
      model: MODEL,
      maxTokens: 4096,
      system: SYSTEM,
      betas: BETAS,
      thinking: $thinking,
      messages: array_slice($history, 0, 2),
      compaction: new BetaCompactionConfig(), // type defaults to 'summarize'
  );
  if ($summary->stopReason !== BetaStopReason::COMPACTION->value) {
      throw new \RuntimeException("No summary: {$summary->stopReason}");
  }

  // 3. Поместите блок перед сохранённым ходом и задайте следующий вопрос.
  $history = [
      BetaMessageParam::with(role: Role::ASSISTANT, content: $summary->content),
      ...array_slice($history, 2),
      BetaMessageParam::with(role: Role::USER, content: 'Which day should the release go out?'),
  ];
  $third = $client->beta->messages->create(
      model: MODEL,
      maxTokens: 8192,
      system: SYSTEM,
      betas: BETAS,
      thinking: $thinking,
      messages: $history,
  );

  // 4. Ответ 200 без отброшенных блоков означает, что сохранённые размышления прошли проверку.
  printf("Dropped thinking blocks: %d\n", count($third->inputTransformations));
  ```

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

  # Claude Fable 5.1 — первая модель, которая сверяет возвращённые блоки размышлений с ходом диалога.
  MODEL = Anthropic::Model::CLAUDE_FABLE_5_1
  BETAS = [
    Anthropic::AnthropicBeta::COMPACT_2026_09_04,
    Anthropic::AnthropicBeta::THINKING_BINDING_CONTROLS_2026_08_01
  ]
  SYSTEM = "You help plan a recipe app's release. Keep answers short."
  # При значении "error" блок размышлений, не прошедший проверку, приводит к ошибке запроса с кодом 400.
  THINKING = Anthropic::Beta::BetaThinkingConfigAdaptive.new(
    block_binding: Anthropic::Beta::BetaThinkingBlockBinding.new(
      prefix_mismatch_behavior: Anthropic::Beta::BetaThinkingPrefixMismatchBehavior::ERROR
    )
  )

  # 1. Проведите короткий диалог с включёнными размышлениями.
  history = [{ role: "user", content: "What are the main entities in the app's data model?" }]
  first = client.beta.messages.create(
    model: MODEL,
    max_tokens: 8192,
    system_: SYSTEM,
    betas: BETAS,
    thinking: THINKING,
    messages: history
  )
  history += [
    { role: "assistant", content: first.content },
    {
      role: "user",
      content: "Testing starts on Tuesday, March 3, 2026, takes 10 weekdays, and pauses on March 9 and March 16. On which date does it end?"
    }
  ]
  second = client.beta.messages.create(
    model: MODEL,
    max_tokens: 8192,
    system_: SYSTEM,
    betas: BETAS,
    thinking: THINKING,
    messages: history
  )
  history << { role: "assistant", content: second.content }
  thinking_blocks = second.content.count { it.is_a?(Anthropic::Beta::BetaThinkingBlock) }
  puts "Thinking blocks in the kept turn: #{thinking_blocks}"

  # 2. Кратко изложите первый ход. Второй ход в запрос не включается.
  summary = client.beta.messages.create(
    model: MODEL,
    max_tokens: 4096,
    system_: SYSTEM,
    betas: BETAS,
    thinking: THINKING,
    messages: history.first(2),
    compaction: { type: "summarize" }
  )
  abort "No summary: #{summary.stop_reason}" unless summary.stop_reason == :compaction

  # 3. Поставьте блок перед сохранённым ходом и задайте следующий вопрос.
  history = [
    { role: "assistant", content: summary.content },
    *history.drop(2),
    { role: "user", content: "Which day should the release go out?" }
  ]
  third = client.beta.messages.create(
    model: MODEL,
    max_tokens: 8192,
    system_: SYSTEM,
    betas: BETAS,
    thinking: THINKING,
    messages: history
  )

  # 4. Ответ 200 без отброшенных блоков означает, что сохранённые размышления прошли проверку.
  puts "Dropped thinking blocks: #{third.input_transformations.length}"
  ```
</CodeGroup>

```text Output wrap
Thinking blocks in the kept turn: 1
Dropped thinking blocks: 0
```

В рабочей среде `"drop_block"` обеспечивает успешное выполнение запросов, когда какое-либо условие не выполняется, и сообщает о каждом отброшенном блоке в `input_transformations` с `reason: "prefix_binding_mismatch"`. Запись, чей `path` попадает в сохранённый ход, означает, что размышления этого хода не остались действительными. В разделе [Что API делает с недействительным блоком](https://platform.claude.com/docs/ru/build-with-claude/preserved-thinking#mismatch-behavior) описано, что отбрасывается, и объясняется, как настроить оповещения об этом. На Claude Sonnet 5.5 и Claude Haiku 5.5 `block_binding` работает только с `thinking: {"type": "adaptive"}`. Запрос, который устанавливает его с `thinking: {"type": "between_tools"}` на Claude Sonnet 5.5 или с `thinking: {"type": "disabled"}` на Claude Haiku 5.5, возвращает ошибку 400. В таких запросах убедитесь, что выполняется каждое условие, или удалите блоки `thinking` и `redacted_thinking` из сохранённых ходов.
