Skip to content

Hand each result over as soon as it arrives - #614

Merged
jmtts merged 1 commit into
mainfrom
claude/bold-noether-hyg4ov
Oct 12, 2026
Merged

jmtts merged 1 commit into
mainfrom
claude/bold-noether-hyg4ov

Conversation

@werk24

@werk24 werk24 commented Oct 12, 2026

Copy link
Copy Markdown
Contributor

The read stream (Werk24Client.read_drawing) held every message back until the server sent the next one. The hold-back was there so a payload download could overlap the wait for the next message. Its side effect: a result reached the caller only when the result after it arrived.

The server sends results as soon as each one is ready, and the gap between two can be long. A sheet image (AskSheetImages) is typically ready a few seconds into a read, while the first extracted values come many seconds later. The image sat in the client, fully downloaded, for that whole gap.

What changed (_send_command_read in werk24/techread.py)

  • The receive for the next message now runs as a task.
  • While it waits, every message already received is handed over as soon as its own payload has downloaded.
  • Order is unchanged, and every message still carries its payload_bytes.
  • Downloads still overlap the receive.
  • If the stream is abandoned or fails, the outstanding receive is cancelled along with any downloads. Cancelling a websockets recv() loses no data.
  • recv() is called inside the task, so a receive cancelled before its first tick leaves no "coroutine was never awaited" warning.

One semantic shift: read_idle_timeout now starts when the previous message arrives, not when the caller next asks for one. It now measures server silence only, which is what its docstring says it bounds. Before, time the caller spent on a message was added to the window.

Effect, replaying one real read's message schedule against a stubbed socket (seconds; the payload download is stubbed at 0.2s):

message sent by server handed over before handed over after
STARTED 0.0 3.2 0.0
document profile 3.2 3.5 3.2
sheet image 3.5 20.9 3.8
first values 20.9 26.3 20.9
remaining results 26.3 26.3 26.3

Tests

  • Three new tests in tests/test_shared_https_session.py. Two check that a message, with or without a payload, is handed over before the server sends the next one. The third checks that abandoning the stream cancels the outstanding receive.
  • All three fail on main and pass here. The existing overlap, ordering, failure and normal-termination tests pass unchanged.
  • .venv/bin/python -m pytest -m "not callback_e2e" -p no:cacheprovider on CPython 3.13.16: 1025 passed, 4 skipped, 1 deselected, 4 warnings. On main: 1023 passed, with the same 4 warnings.

Questions for the owner

One question. It does not block the merge.

  1. Release this as a patch version to PyPI right after the merge?
    • Applications that install from PyPI or pin a commit keep the delay until they upgrade.
    • The change only affects when a message reaches the caller; the API and the message content are unchanged.
    • Recommendation: yes.

Not questions, for after the merge:

  • Bump every consumer that pins a commit of this repository, so the faster hand-over reaches them.

🤖 Generated with Claude Code

https://claude.ai/code/session_01HdXy5tRa4VgmTRHFLbygBx


Generated by Claude Code

The read stream held every message back until the server sent the next
one. That let a payload download overlap the wait for the next message,
but it also meant a result reached the caller only when its successor
arrived. The server sends results as they become ready and the gap
between two of them can be long: a sheet image that is ready a few
seconds into a read sat in the client, fully downloaded, until the first
extracted values arrived many seconds later.

The receive for the next message now runs as a task, and while it waits
every message already received is handed over as soon as its own payload
is downloaded. Order is unchanged, downloads still overlap the receive,
and a stream that is abandoned or fails cancels the outstanding receive
along with any downloads.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01HdXy5tRa4VgmTRHFLbygBx
@jmtts
jmtts merged commit c65b2b6 into main Oct 12, 2026
7 checks passed
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.

3 participants