# `Alloy.Context.Compactor`
[🔗](https://github.com/alloy-ex/alloy/blob/v0.10.1/lib/alloy/context/compactor.ex#L1)

Summary-based context compaction.

When the conversation approaches the configured reserve threshold, Alloy
preserves the first message, keeps a recent verbatim token window, and
replaces older context with a structured handoff summary. If summary
generation fails, Alloy falls back to deterministic truncation.

# `compact_messages`

```elixir
@spec compact_messages(
  [Alloy.Message.t()],
  keyword()
) :: [Alloy.Message.t()]
```

Compacts messages, preserving the first message and the most recent N messages.

This helper intentionally stays deterministic and provider-free so it can serve
as the fallback truncation strategy.

## Options
  * `:keep_recent` - number of recent messages to preserve (default 10)

# `force_compact`

```elixir
@spec force_compact(Alloy.Agent.State.t()) :: Alloy.Agent.State.t()
```

Forces compaction regardless of reserve budget.
Used when the provider rejects the prompt as too long.

# `maybe_compact`

```elixir
@spec maybe_compact(Alloy.Agent.State.t()) ::
  {:compacted | :unchanged, Alloy.Agent.State.t()}
```

Compacts state messages when they exceed `max_tokens - reserve_tokens`.

Returns `{:compacted, state}` when compaction occurred, or
`{:unchanged, state}` when already within budget.

# `summary_prefix`

```elixir
@spec summary_prefix() :: String.t()
```

Prefix used for synthetic handoff summary messages inserted by the compactor.

---

*Consult [api-reference.md](api-reference.md) for complete listing*
