Skip to Content
InternalsHistory and Scrollback

History and Scrollback

As soon as a terminal application has:

  • multiple conversation turns
  • completed content
  • a live viewport
  • a sticky footer or composer

history can no longer be treated as “just text that was printed earlier”.

In Ansiq, history and scrollback are explicit surface semantics.

The current model

Ansiq commits completed history into terminal scrollback at commit time.

That means:

  • completed content leaves the live viewport
  • the live viewport retains only the active shell
  • scrollback becomes the primary place for reviewing committed history

This model fits especially well for:

  • long-running session UIs
  • agent shells
  • transcript and log-oriented interfaces
From live viewport to scrollback
1the current turn grows inside the live viewport
2the app decides that the turn is complete
3the history entry normalizes into a block
4the surface commits that block into scrollback
5the live viewport keeps only the active shell

Current behavior

  • history wraps at commit width
  • committed history does not reflow on later resize
  • Text and Block entries now share the same commit-time wrap path

These are not incidental implementation details. They are explicit current tradeoffs.

Why commit-time wrap is a tradeoff

At first glance, the ideal behavior might seem to be:

  • history should also reflow whenever the terminal width changes

But once content has been committed into scrollback, it is no longer part of the live viewport under runtime control.

To reflow that history after resize, the runtime would effectively need to:

  • regain control over previously emitted scrollback
  • recompute all wrapped lines
  • rewrite terminal history in place

That is not realistic in most terminal modes, and it introduces a large amount of complexity.

So Ansiq currently chooses the simpler and more terminal-native behavior:

  • wrap at commit time
  • do not reflow once content has entered scrollback

Why this must be documented

If this is left undocumented, users naturally interpret it as a bug:

Why does the live viewport reflow on resize, but committed history does not?

The answer is architectural:

  • the live viewport is still owned by the runtime
  • committed scrollback is already owned by the terminal

Those are different layers with different capabilities.

Why Text and Block had to be unified

Earlier, HistoryEntry::Text and HistoryBlock did not follow the same path, which meant:

  • one kind of history entry wrapped one way
  • another kind of history entry wrapped another way

That breaks the visual meaning of “history”.

The current behavior is now cleaner:

  • history first normalizes into a common block model
  • then it follows one scrollback rendering path

This guarantees that the same class of historical content behaves consistently at the same terminal width.

When content should be committed and when it should not

This is a product-semantic question, not merely a rendering detail.

You should decide:

  • what counts as completed
  • what belongs to the live viewport
  • what should move into scrollback

Examples:

  • in a conversation UI, completed turns can be committed
  • in an activity monitor, the main shell usually should not be committed
  • in a structured explorer, the left/middle/right panes also should not be treated as history

In other words, not every application needs a history model.

The real point of this page

In Ansiq, history / scrollback is not just “printing some strings”.

It is a clear architectural boundary:

  • runtime manages the live viewport
  • the terminal takes ownership of committed scrollback
  • commit-time wrapping is an explicit tradeoff

Once that boundary is documented, resize behavior, history behavior, and viewport behavior become much easier to explain.

Last updated on