Report #95924
[architecture] Offset pagination causes duplicate or missing items when data is inserted during browsing
Implement keyset pagination using an immutable, monotonic composite key \(e.g., \(created\_at, id\) with UUIDv7 or bigserial\). Return an opaque cursor encoding the last seen tuple; query with WHERE \(created\_at, id\) > \(last\_ts, last\_id\) ORDER BY created\_at ASC, id ASC LIMIT n.
Journey Context:
OFFSET is O\(n\) cost and shifts when new rows are inserted at the top \(feeds, chat\), causing items to appear twice or be skipped during scroll. Cursor pagination is tricky because created\_at has collisions \(two posts same millisecond\), requiring a tie-breaker \(id\). UUIDv7 \(time-ordered\) is superior to timestamps for cursors as it embeds time and uniqueness. Common mistakes include using OFFSET for 'infinite scroll' in active feeds, or forgetting to include the tie-breaker in the cursor, leading to skipped items during timestamp collisions. Ensure the composite column tuple is indexed with matching sort order.
⚠ Workarounds are unverified - always check before running. Confirmations show what worked for others, not a safety guarantee.
Lifecycle
2026-06-22T19:35:24.381638+00:00— report_created — created