Skip to content

view: stay responsive and fast over HTTP - #747

Merged
dfa1 merged 3 commits into
mainfrom
view-nonblocking-744
Nov 13, 2026
Merged

dfa1 merged 3 commits into
mainfrom
view-nonblocking-744

Conversation

@dfa1

@dfa1 dfa1 commented Nov 13, 2026 •

Copy link
Copy Markdown
Owner

The viewer froze on vortex view <https url> and took one sequential range request per column. A JFR showed 270 requests at ~150 ms each, one at a time, 226 starting within 1 KB of the previous one's end, 72 re-reading a range already read.

  • Render loop never waits on the IoWorker: LazyGridSource.peekRows returns cached rows plus … placeholders; the loop polls keys on a 50 ms tick while loading, so q quits at once. Title leads with a spinner.
  • Only the visible columns (+2 margin) are formatted.
  • Chunk.prefetch / VortexHandle.prefetch: concurrent range requests (max 8 in flight, virtual threads), neighboring segments merged (1 MiB distance, 16 MiB max, Rust's CoalesceConfig::object_storage).
  • VortexHttpReader keeps every segment it read: scrolling back makes no request. No TTL/eviction: immutable file, bytes live in the arena anyway.

Not included: jumping straight to a chunk instead of rescanning from chunk 0 (item 3), so the issue stays open. No vortex-jni cross-check test: prefetch changes when bytes are fetched, not what is decoded.

Refs #744

🤖 Generated with Claude Code

@dfa1
dfa1 force-pushed the view-nonblocking-744 branch from 58d382f to 10bedb0 Compare November 13, 2026 15:26
@dfa1 dfa1 changed the title view: never block the render loop on I/O view: stay responsive and fast over HTTP Nov 13, 2026
`vortex view <https url>` froze while it fetched data, and each window
took one sequential range request per column. A JFR of the viewer showed
270 requests at ~150 ms each, one at a time, 226 of them starting within
1 KB of the previous one's end, and 72 re-reading a range already read.

- The render loop never waits on the IoWorker: LazyGridSource.peekRows
  returns cached rows plus placeholders and posts a latest-wins request;
  the loop polls keys on a 50 ms tick while loading. A load superseded
  or queued before close is skipped, and teardown waits at most 250 ms
  for the worker, so q quits even with a request stalled. A failed load
  is tied to its window instead of poisoning the session.
- Only the visible columns, plus a margin of two, are formatted.
- Chunk.prefetch / VortexHandle.prefetch start the range requests of
  those columns together on virtual threads, at most 8 in flight, merging
  segments up to 1 MiB apart (16 MiB per request, Rust's
  CoalesceConfig::object_storage). A call queues at most 64 MiB on the
  heap, responses are sliced into the arena without a second copy, and a
  chunked layout's stats child is not fetched.
- VortexHttpReader keeps every segment it has read, so scrolling back
  makes no request. No eviction or TTL: the file is immutable for the
  life of the handle and the bytes stay in the arena anyway.

Not done from #744: jumping straight to a chunk instead of rescanning
from chunk 0.

Refs #744

Co-Authored-By: Claude Sonnet 5 <[email protected]>
@dfa1
dfa1 force-pushed the view-nonblocking-744 branch from 10bedb0 to 3abc812 Compare November 13, 2026 16:34
dfa1 and others added 2 commits November 13, 2026 17:37
The render loop reads through peekRows; the blocking readRows and its
row wrapper had no production caller left, only tests, which now read
through peekRows after the worker has loaded the window.

Co-Authored-By: Claude Sonnet 5 <[email protected]>
The viewer reaches a far chunk by stepping over the ones in between.
Chunks decode a column when it is read, so that costs no request; this
test fails if a change makes the decode eager. Refs #744 (item 3).

Co-Authored-By: Claude Sonnet 5 <[email protected]>
@dfa1
dfa1 merged commit 2f3843f into main Nov 13, 2026
5 of 6 checks passed
@dfa1
dfa1 deleted the view-nonblocking-744 branch November 13, 2026 18:12
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant