ConnectOnionAll Posts

Design Journal · August 15, 2026 · ConnectOnion 1.6.8

A Page Should Not Become a Wall

A finite page protects a service. It must not pretend the rest of a mailbox does not exist.

Received and sent mail exposed the same last idea but enforced different limits. Asking for 101 received messages failed while asking for 1,000 sent messages worked. The only way to learn the hidden boundary was to cross it.

The decision

Keep a finite page size, align the two mailboxes, and make every page reachable.

The wrong repairs

Silently clamp the request

Turning 1,000 into 100 would make the HTTP request green while making its meaning false. A reconciliation agent would believe it had asked for—and received—a thousand messages. Silent incompleteness is worse than a loud limit.

Document the 100-row ceiling

An explicit error is honest, but it preserves the wrong product behaviour. Users still cannot reconcile a mailbox larger than one page. The page boundary has become a mailbox boundary.

A traversable boundary

ConnectOnion 1.6.8 aligns received and sent page sizes at 1,000 and adds an offset to the SDK, CLI, skill, and backend. Equal timestamps use message ID as a deterministic tie-breaker, so rows do not exchange pages between calls.

get_emails(last=1000, offset=2000)
co email inbox --last 1000 --offset 2000

# A full CLI page prints the exact next-page command.

The tradeoff

Offset pagination is simple and inspectable, but inserts can shift later pages during a long traversal. Stable ordering prevents arbitrary swaps; callers that need a transactionally frozen snapshot still need a future cursor or snapshot API.

Evidence

Tests cover limit and offset validation, request forwarding, unsupported-backend detection, deterministic backend ordering, CLI forwarding, and the next-page tip. The production backend and the public 1.6.8 wheel were verified together before these docs were published.

What would make us revisit this

If high-volume reconciliation commonly spans concurrent writes, an opaque cursor tied to a stable snapshot would be worth its extra state. The current contract remains intentionally plain: a caller can see the limit, move past it, and know when traversal is complete.

See the email CLI guide for commands and The Owner Needs a Door for the other shortest-path lesson in 1.6.8.

Star us on GitHub

If ConnectOnion saves you time, a ⭐ goes a long way — and earns you a coffee chat with our founder.