Skip to content

Electric resume check puts a lagging tab in error when a peer deleted the row it updates #2267

Open

Description

@KyleAMathews

Summary

Electric's resume check can put a persisted Collection in error when several tabs share one persisted database. A resumed tab that lags behind a peer receives an update for a row that the peer's commit already deleted from the shared durable rows. Electric treats the update as a row it never sent and fails with Electric resume state referenced an unseen row; a full snapshot is required.

The resume check assumes that the local rows came from this tab's own stream. With shared persistence, the local rows also reflect peers' commits, which can be ahead of this tab's stream.

main has the same behavior (checked at b8d8ee07c).

Reproduction

The generated multi-tab oracle in #2265 found this history and shrank it:

  1. Two eager tabs share one database. Both deliver the initial snapshot (rows 1 and 2).
  2. Tab B reloads. Its new stream resumes from the persisted position.
  3. The server updates row 2, deletes row 1, deletes row 2, and inserts row 1 again.
  4. Tab A's stream delivers all four changes and up-to-date. A commits them, so the durable rows hold only row 1.
  5. Tab B applies A's commit, so it no longer holds row 2.
  6. Tab B's stream delivers the same changes. The first message updates row 2. B fails with the error above.

The history is pinned as an it.fails replay in packages/browser-db-sqlite-persistence/tests/multi-tab-electric-oracle.test.ts:

cd packages/browser-db-sqlite-persistence
npx vitest run tests/multi-tab-electric-oracle.test.ts -t "keeps a resumed lagging tab out of error"

Expected

A tab whose own stream is legal does not enter error. After every stream catches up, every tab shows the server's rows.

Notes

  • The generated campaigns leave this history out until a fix lands. The coverage map records the exclusion.
  • A fix probably needs the resume check to use evidence from this stream only, not rows that peers' commits supplied. Persisted multi-tab: order source transactions by server position #2209 (ordering source writes by server position) is related, because both come from tabs sharing durable rows at different stream positions.

This issue was written by Isaac.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions