Session Boundary Design
The longer a conversation runs, the less the instructions and constraints given at the start still hold. Compression is unavoidable — if we don't draw the line, the tool draws it for us at a capacity threshold. The choice isn't whether to cut, but when and what to keep when cutting. What disappears is the conversation's process, not its output.
Problem
As dialogue piles up, the constraints stated at the start quietly stop holding. The cause isn't only running out of capacity — length itself degrades performance (Research, an 18-model benchmark; see in Practice).
And not designing a boundary doesn't mean there is no boundary. One simply gets drawn without you. As capacity nears its limit, the tool automatically summarizes and compresses the conversation to fit (Official, see in Practice). Summarization is irreversible, and what got dropped was never your choice.
The direction decided last week, the constraint just read a moment ago — all of it gets folded away together, at a point that has nothing to do with any natural break in the work.
Context
Applies when (these three correspond to what the official docs state as judgment criteria; see in Practice):
- Moving to an unrelated task — the next piece of work doesn't need the prior conversation
- Wanting a do-over — when direction went wrong, starting from a blank slate is faster than making the model reconcile new decisions with old ones
- Summarization has piled up too many times — when it's been folded away repeatedly and something that should still matter already feels lost. That conversation is now carrying nothing but cost
Does not apply when:
- A single short task. The cost of building a boundary — re-handing context, rebuilding the preamble — outweighs the benefit
- The accumulated understanding itself is the asset. For iterative work where you want to retain what was tried and what didn't work, cutting destroys the asset along with the rest (Official, see in Practice)
- The phase changes, but the dependency doesn't break. Work that moves a single feature through scaffolding, implementation, testing, and a PR keeps changing phase, yet a later phase still needs the content of an earlier one (Official, see in Practice)
Boundary with neighboring patterns:
- Read-and-Discard Isolation — if the unit discarded is the conversation itself, this pattern; if it's one section within a conversation, that pattern
- Resident Context Inventory — this pattern cuts the side that piles up (the conversation); that pattern reduces the side that loads every turn (resident content). Different parts of the same context window
- Keeping the Prefix Stable — that pattern says "cutting means rebuilding"; this pattern says "not cutting means breaking." A direct tension
Solution
Boundaries get drawn in two ways.
| Aspect | A boundary drawn by capacity | A boundary drawn by dependency |
|---|---|---|
| Trigger | A capacity threshold, unrelated to any break in the work | The moment dependency thins out |
| What's dropped | Everything gets folded away, mid-implementation and all | Only what nothing depends on |
| Who chooses what carries over | The tool | You, specifying what to hand over |
Draw the boundary at the moment dependency thins out, and only the investigation process gets folded away, while what carries forward can be specified and handed off. Why this works can be explained from the boundary's own nature. A boundary is irreversible compression by summarization, and that compression happens whether you choose it or not.
This isn't a flaw in the tool. Without folding, old messages that no longer fit simply get dropped, with no summary and no record (Official, see in Practice). Automatic compression is a safety net, and far better than having none.
But a safety net doesn't choose where things fall. The threshold is set by capacity, and capacity has nothing to do with any natural break in the work. So the choice isn't whether to draw a boundary — only when, and what to keep, when you do.
When to draw it. The cue is a phase change — once an investigation ends, almost none of its process is needed anymore. But phase isn't the condition itself. What matters is dependency.
The only question is whether the next piece of work needs the prior conversation, and sometimes the phase changes while the dependency doesn't break. Work that moves a single feature through scaffolding, implementation, testing, and a PR keeps changing phase, yet a later phase still needs the content of an earlier one. The official docs list exactly this as the leading case for "when a long session is the right call" (see in Practice). The rule "cut once the investigation ends" runs straight into a counterexample here.
Phase is only a clue to where dependency is likely to thin, and cutting at a seam where dependency hasn't thinned just discards something you needed. There's a flip side too — when the prior conversation has become a liability for the next task, that is, direction went wrong and reconciling old decisions with a new approach is about to begin, dependency stops being an asset worth keeping and becomes exactly what should be severed (the official docs cite "a clean slate" as a reason for a new session; see in Practice).
What to keep. This is where this pattern earns its keep. It's not "discard or keep" — it's deciding what carries forward.
In a boundary the tool draws, the tool chooses what carries over. In a boundary you draw yourself, you can specify it. Because summarization is irreversible, this specification happens once, and only once.
⚠ What disappears is the conversation's process, not its output. Drawing a boundary doesn't mean erasing the code you wrote or the commits you made. What disappears is only the conversation that led there.
Turn it around: if something you want to carry forward exists only inside the conversation, it should have been taken out before the boundary, not left in. Designing a boundary also means finishing that sorting before an accident happens.
Trade-offs
Advantages
- You choose what drops. Compression itself is unavoidable, but you can choose its timing and what the summary keeps. A boundary left to the tool gets drawn on a criterion — capacity — that has nothing to do with the work.
- Input length stays short. Where length itself degrades performance (Research, see in Practice), keeping it short has value in itself. But the evidence shows a trend, not a threshold — "cut at N tokens" doesn't follow from this research (see in Practice).
Costs
- Summarization is irreversible. The official docs state plainly that "fine-grained details … may not be included" (see in Practice). Details don't come back. This holds even for a boundary you draw yourself — what this pattern changes is what drops, not whether something drops.
- It invites rebuilding the preamble. The official docs describe redrawing a boundary as "rebuild from a short summary instead of the full history" (see in Practice), taking rebuilding itself as a given. But the official docs push a new session specifically for the case where a pause has already invalidated the cache. The cost of cutting while the cache is still alive doesn't follow from this text. The tension with Keeping the Prefix Stable only resolves in the invalidated case.
GitHub Copilot in Practice
Copilot isn't a single product. New sessions and /compact both appear in the official docs for Copilot CLI and VS Code, but how far the text goes differs by surface.
Copilot CLI — the judgment criteria for a boundary are written in the official docs
Source: Context management in Copilot CLI (retrieved 2026-07-16).
What happens if you leave it alone Official:
When your conversation reaches approximately 80% of the context window's capacity, Copilot CLI automatically starts compacting the context in the background. This leaves a buffer of approximately 20% so that tool calls can continue to run while compaction is in progress. If the context fills to approximately 95% before compaction finishes, Copilot CLI pauses briefly to wait for compaction to complete before continuing.
The boundary is drawn by capacity. Roughly 80%, 20%, 95% — none of them a number tied to the shape of the work. But this shouldn't be read as a flaw. The same page states the alternative Official:
Without compaction, once the context window filled up, Copilot would have to fall back to simply dropping old messages from the conversation history—removing them without any summary or record.
Old messages dropped with no summary and no record — automatic compaction is a safety net against exactly that. This pattern isn't about removing the safety net; it's about not using the safety net in place of design.
What's lost, and what the surviving side is called Official:
Compaction is a summarization process, so some detail is inevitably lost. The summary captures the key points, but fine-grained details—such as the exact wording of every message, the full output of every command, or minor decisions made early in a long conversation—may not be included.
Every time compaction happens—whether automatically or manually—a checkpoint is created. A checkpoint is a saved copy of the compaction summary, stored as a numbered, titled file in your session's workspace.
And the same page states something rarely found elsewhere in this catalogue — the actual judgment criteria for when to cut Official:
Starting a new session is better when:
- You're switching to an unrelated task. Copilot doesn't need the context of your previous work, and a clean context window means more space for the new task.
- The conversation has gone through many compactions, and you feel that important context is being lost in the summarization process.
- You want a clean slate—for example, if work went in a wrong direction and you'd rather start over than have Copilot try to reconcile earlier decisions with a new approach.
The other side is stated too Official:
- You're working on a multi-phase task, such as building a feature that requires scaffolding, implementation, testing, and then creating a pull request.
- You're iterating on a problem and want Copilot to retain the context of what's been tried and what hasn't worked.
Put the two side by side and the axis becomes readable. None of the five conditions is about phase. Unrelated task means dependency is absent. Clean slate means dependency has turned into a liability. Many compactions means the thing depended on is already lost. Multi-phase task and iterating, conversely, are cases where dependency doesn't break even as phase changes. This is exactly why a phase-based rule like "cut once investigation ends into implementation" collides with the official docs' own multi-phase example — and why Solution says to look at dependency rather than phase.
Operations (source: Copilot CLI command reference, retrieved 2026-07-16) Official:
|
/clear [PROMPT],/new [PROMPT],/reset [PROMPT]| Start a new conversation. |
|
/compact [FOCUS-INSTRUCTIONS]| Summarize the conversation history to reduce context window usage. Optionally provide focus instructions to steer the summary—for example,/compact focus on the auth module. … |
|
/context| Show the context window token usage and visualization. … |
That /compact takes an argument is this pattern's whole point. "What carries forward" isn't a metaphor — it can be specified, as in focus on the auth module. The difference between a summary folded automatically and one folded with focus instructions attached is the difference between an undesigned boundary and a designed one. /context gives you material to make that call ahead of time — knowing the threshold is near lets you draw the boundary before the tool does.
⚠ Don't drop the original text's qualifier — an early draft note in this catalogue cited /fork with no qualification Official:
|
/fork [NAME],/branch [NAME]| Fork the current session into a new session, optionally with a name. Only available in experimental mode. |
/fork is limited to experimental mode. It's an attractive way to draw a boundary, but if it isn't introduced together with that limitation, it isn't introduced at all.
VS Code — arriving at the boundary from the cache side
Source: Cache Explorer (retrieved 2026-07-16). A page for optimizing prompt caching lists a new session as one of five recommendations Official:
- Start fresh after a break: Caches expire after inactivity. Start a new session or run
/compactto rebuild from a short summary instead of the full history.
This is where the tension with Keeping the Prefix Stable resolves. Drawing a boundary means rebuilding the preamble, so from the cache's point of view a boundary is a cost. But once a break intervenes, the cache expires anyway. After it's invalidated, rebuilding happens regardless. At that point, rebuilding from a short summary is cheaper than rebuilding from the full history. The caching page's push toward a boundary is specific to this situation — and conversely, the cost of cutting while the cache is still alive doesn't follow from this original text.
This is as far as the cross-surface comparison goes. What's common to the Official docs on both surfaces is starting a new session and /compact; the threshold numbers, the judgment criteria for when to cut, and focus instructions were confirmed only in the Copilot CLI text. This doesn't mean "VS Code lacks it" — what's confirmed is only "the Copilot CLI text has it." This is correctly read as a difference in text, not a difference in product, across surfaces.
Beyond any surface — research that measured input length itself
The source for Problem's "length itself degrades performance" isn't a vendor. Source: Context Rot: How Increasing Input Tokens Impacts LLM Performance (Chroma Research, retrieved 2026-07-16) Research.
What was measured is the crux:
our experiments hold task complexity constant while varying only the input length—allowing us to directly measure the effect of input length alone.
Task difficulty was held constant, and only input length was varied. So what this shows isn't "long tasks are hard" — it's "even the same task degrades once it's buried in a long input."
An evaluation across 18 LLMs, including leading closed-source and open-weights models, revealing nonuniform performance with increasing input length.
We demonstrate that even under these minimal conditions, model performance degrades as input length increases, often in surprising and non-uniform ways. Real-world applications typically involve much greater complexity, implying that the influence of input length may be even more pronounced in practice.
⚠ What can't be drawn from this research: the claim goes only as far as "performance degrades as input grows, and not uniformly." Results measured nonuniform across 18 models also mean no threshold can be drawn — if it's neither a smooth slope nor a clean cliff, a rule like "cut at N tokens" doesn't follow from this evidence. Don't convert it into a specific threshold for a specific tool. The final sentence too (may be even more pronounced in practice) is the authors' own speculation, not a measured result.
For this pattern, the real point is that no threshold can be drawn. If it can't be decided by a number, a boundary can only be decided by the structure of the work itself — whether dependency breaks. That isn't visible to the tool; only a human can see it.
Also Known As
| Name | Source |
|---|---|
| Compaction | Primary — the name Copilot CLI's official docs give to the process of summarizing and compressing a conversation (source: in Practice section above) |
| Checkpoint | Primary — the name the same official docs give to the saved copy of that summary (source: in Practice section above) |
| Session Boundary Design | Descriptive — this catalogue's descriptive name; no primary source uses it |
The official docs give a name only as far as the mechanism (compaction, checkpoint, /clear). For the judgment of "when to cut," no established name could be found, as far as this catalogue could confirm.
Repurposing the mechanism's name for the practice invites the misreading "compaction exists, therefore this practice is being done." In reality it's nearly the reverse. Automatic compaction happens on its own, with no judgment on your part (see in Practice). The mechanism running says nothing about whether the boundary was designed — if anything, the mechanism is what kicks in instead, when no one designed one. So the name was given to the judgment, not the mechanism.
Related
- Read-and-Discard Isolation — if the unit discarded is the conversation itself, this pattern; if it's one section within a conversation, that pattern. Having a ballooning piece of work read in a separate context from the start can eliminate the need for this pattern's boundary altogether
- Resident Context Inventory — this pattern cuts the side that piles up (the conversation); that pattern reduces the side that loads every turn (resident content). They handle different parts of the same context window, so either alone falls short
- Keeping the Prefix Stable — that pattern says "cutting means rebuilding"; this pattern says "not cutting means breaking." A direct tension. The official docs resolve it only for "a pause has already invalidated the cache" (see in Practice)
- The Break-Even Point of Delegation — neither drawing a boundary nor standing up isolation is free. Which price tag you're looking at is that pattern
- If reading just one more next: Read-and-Discard Isolation — once you want to discard at finer grain than a whole conversation, read this next