If you build agents on OpenAI or LangGraph, the sharpest recent writing on keeping a long-running agent inside its window is Anthropic's — and it names three levers: clear, compact, remember. The good news is those aren't Anthropic-only ideas. The same three primitives exist on the OpenAI Agents SDK and in LangGraph, under different names. This is the decision framework, plus where each vendor's version actually differs.
The one-screen answer: a long-running agent fails when its window fills with stale output, not because the model weakened. You have exactly three fixes, sorted by what you can afford to lose. Clear evicts re-fetchable tool results (cheapest, no inference). Compact summarizes the transcript (one inference pass, loses verbatim detail). Remember writes durable state outside the window (the only one that survives a reset). Don't pick one — assign each loss to the mechanism whose loss is cheapest, and save specifics to memory before compaction summarizes them away. We made this case for Anthropic's three levers; here it is across vendors.
Why the window fills faster than you think#
The reason to manage context at all is that a bigger window doesn't buy you proportionally more usable context. Output quality measurably degrades as input grows — Chroma's 2025 "context rot" research across 18 frontier models found accuracy can fall well before the documented limit, and, counter-intuitively, coherent well-structured input can degrade attention more than shuffled input (Anthropic Engineering). We unpacked why a bigger window doesn't mean better recall. The practical upshot: "just use the 1M window" is not a context strategy. You still have to keep the window clean.
1. Clear — evict re-fetchable tool results#
What it does: deletes old tool-call results (and optionally the tool inputs) from the window, leaving a placeholder so the model still knows a call happened. Because the results are re-fetchable, this is the cheapest possible loss — a mechanical edit with no inference cost.
Anthropic makes this a first-class, server-side feature: clear_tool_uses_20250919 (beta header context-management-2025-06-27). It runs before the prompt reaches the model, so your client keeps the full unmodified history — no sync. Defaults: trigger at {input_tokens: 100000}, keep the 3 most recent tool uses, plus clear_at_least (free enough tokens to justify the cache re-write) and exclude_tools (never clear, e.g. ["memory"]) (Claude docs).
OpenAI and LangGraph have no first-class equivalent — you do the same job with manual message trimming (LangGraph exposes trim_messages; on the OpenAI Agents SDK you manage it through the session). That means you own the logic for what to drop, which is more control and more rope.
Watch the cache: clearing changes the cached prompt prefix, so it invalidates the cache at the clearing point and forces a re-write. That's exactly why clear_at_least exists — don't clear unless you'll free enough to be worth it.
Reach for it when the bloat is re-fetchable tool output — file reads, search results, API responses. Suggested start: trigger 30K–50K input tokens, keep 4–6 recent tool uses, and always exclude your memory tool.
2. Compact — summarize the transcript#
What it does: replaces the older transcript with an LLM-generated summary. It's the only lever that lets a single run continue past the point where it would otherwise hit the wall — but it costs one summarizer inference pass and it loses verbatim detail.
Anthropic: compact_20260112 (beta header compact-2026-01-12). Default trigger at 150,000 input tokens (minimum 50,000); a custom instructions string completely replaces the default summary prompt; pause_after_compaction lets you inspect the summary before continuing. A billing gotcha worth knowing: the top-level token counts don't include the compaction pass — sum usage.iterations[] for the true cost (Claude docs). Note the documented default differs between the raw API (150K) and the Agent SDK wrapper (100K), so confirm which layer you're calling.
OpenAI Agents SDK: a Compaction() capability with a policy threshold, and OpenAIResponsesCompactionSession to wrap a session and force checkpoints at phase boundaries. Its design line is the clearest one-sentence summary of the whole space: "Compaction helps the current run continue; memory helps future runs improve" (OpenAI Cookbook).
LangGraph: SummarizationMiddleware (via create_agent) monitors token counts and summarizes older messages at a threshold; langmem offers a SummarizationNode for use inside a graph (LangChain docs). Confirm the exact class signatures against the live docs before you copy code — the LangChain 1.x memory surface is mid-migration.
What it loses, and how to limit it: in Anthropic's own cookbook trace, a compaction summary kept 3 of 3 high-level facts but 0 of 3 obscure specifics. The mitigations are the same everywhere: write a custom summary prompt that names your must-keep specifics (IDs, numbers, open questions, unread items) — Anthropic's rule is "maximize recall first, then improve precision" — and offload critical detail to memory before the summarizer runs.
Reach for it when the transcript itself — accumulated reasoning and dialogue, not tool output — is what's growing, and the agent stalls before finishing.
3. Remember — write durable state outside the window#
What it does: the agent writes state to files or a database it reads back later. No token trigger; it's model-driven. This is the only mechanism whose data survives a context reset, because it never lived in the window.
Anthropic: the memory tool (memory_20250818) is generally available — no beta header — on all Claude 4+ models. It's fully client-side: the model only requests file ops (view, create, str_replace, etc.) and your handler executes them, confined to a /memories prefix. The API auto-injects an instruction telling Claude to check memory first "because your context window might be reset at any moment" — which makes memory a crash-recovery mechanism, not just a note-taker (Claude docs).
OpenAI: a Memory() capability plus the Sessions system (SQLiteSession), with a sharp opinion — the cookbook says memory should store reusable workflow lessons, not case-specific facts (it explicitly forbids writing evidence citations or document facts to memory). OpenAI's Responses API is stateless server-side, so cross-session identity is left to your app (OpenAI Agents SDK).
LangGraph: short-term memory is the graph state persisted by a thread-scoped checkpointer; long-term, cross-thread memory is a separate store (LangChain docs).
One non-negotiable: if the model can write file paths, you must implement path-traversal protection (reject ../, resolve canonical paths, watch for %2e%2e%2f) and cap file sizes. /memories/../../secrets.env is the attack. We covered building a memory-tool handler safely.
Reach for it when work spans sessions, or a fact must outlive a reset. Memory is what you save the specifics to before compaction can lose them.
The decision, in order#
Cheapest to most involved — and they compose:
- Default on clearing if re-fetchable tool output is your bloat. No inference, lowest fidelity risk.
- Add compaction when the transcript grows and the agent stops mid-task. It's the only lever that continues a single run — pay the summarizer, and protect your specifics with a custom prompt.
- Add memory when work crosses sessions. Durable state goes to files, not the transcript.
Anthropic's combined config took a research agent from "335K-token peak, failed on a 200K window" to "~200K peak, multi-session, task completed." The vendors differ most on clearing (first-class only at Anthropic) and least on the framework itself: clear what's re-fetchable, compact what's narratable, remember what's irreplaceable. That decision is portable even when the API isn't.



