Skip to content

fix(electric-db-collection): preserve persisted rows on progressive resume#1493

Merged
KyleAMathews merged 5 commits into
TanStack:mainfrom
pkudinov:codex/fix-progressive-persisted-resume
Jul 13, 2026
Merged

fix(electric-db-collection): preserve persisted rows on progressive resume#1493
KyleAMathews merged 5 commits into
TanStack:mainfrom
pkudinov:codex/fix-progressive-persisted-resume

Conversation

@pkudinov

@pkudinov pkudinov commented Apr 24, 2026

Copy link
Copy Markdown
Contributor

Summary

Fixes #1478.

Progressive Electric collections wrapped with SQLite persistence can hydrate rows from the persisted store, then wipe them when the resumed Electric stream sends an up-to-date control message without replaying snapshot rows.

This changes progressive startup so a valid persisted Electric resume point is treated as already past the initial atomic-swap phase. That preserves hydrated persisted rows while still allowing normal progressive initial sync to use the existing buffer/truncate/apply behavior.

Root cause

Progressive mode uses the first up-to-date message to finish initial sync by truncating the collection and replaying buffered stream rows. With persisted resume metadata, the stream starts from a saved handle/offset, so it may legitimately send up-to-date with no old rows. The collection had already hydrated those rows from persistence, but the initial atomic swap ran anyway and truncated them.

Changes

  • Initialize progressive hasReceivedUpToDate when using a compatible persisted Electric resume point.
  • Add a regression test that hydrates persisted rows, resumes with saved Electric metadata, receives up-to-date without snapshot rows, and verifies rows remain in memory and persistence.
  • Add a patch changeset for @tanstack/electric-db-collection.

Validation

pnpm --filter @tanstack/electric-db-collection test -- --coverage.enabled false
pnpm --filter @tanstack/electric-db-collection build
pnpm exec eslint packages/electric-db-collection/src/electric.ts packages/electric-db-collection/tests/electric.test.ts --max-warnings=0

I also verified this patch in a real Next.js app using browser OPFS SQLite persistence: after resetting local SQLite, loading a persisted progressive Electric collection, and refreshing/warm-loading twice, the collection stayed populated instead of dropping to zero rows.

Summary by CodeRabbit

  • Bug Fixes

    • Fixed progressive resume behavior to prevent saved collection data from being truncated, ensuring persisted rows remain intact when resuming from previously stored Electric shape metadata.
  • Tests

    • Added an integration test covering persisted progressive resume, verifying hydrated persisted rows stay visible through the initial progressive phase and update correctly after resumed change and up-to-date control messages.
  • Chores

    • Published a patch release entry for the collection package to deliver the fix.

@pkudinov pkudinov marked this pull request as ready for review April 24, 2026 06:49
@coderabbitai

coderabbitai Bot commented May 21, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: 6e626445-8d4d-421e-8971-4d3e35e67643

📥 Commits

Reviewing files that changed from the base of the PR and between eec58b0 and d7ca8eb.

📒 Files selected for processing (1)
  • packages/electric-db-collection/tests/electric.test.ts
🚧 Files skipped from review as they are similar to previous changes (1)
  • packages/electric-db-collection/tests/electric.test.ts

📝 Walkthrough

Walkthrough

Progressive resume state now reuses valid persisted resumes without initial atomic-swap buffering. The test adapter supports seeded persisted rows and committed mutations, and an integration test verifies hydrated rows survive resume and subsequent updates.

Changes

Progressive Persisted Resume

Layer / File(s) Summary
Progressive resume state handling
packages/electric-db-collection/src/electric.ts, .changeset/progressive-persisted-resume.md
Initializes hasReceivedUpToDate from progressive mode and persisted-resume validity, with a patch changeset documenting the fix.
Persisted resume validation
packages/electric-db-collection/tests/electric.test.ts
Seeds persisted rows, applies metadata and row mutations in the test adapter, and verifies hydrated rows remain visible through resume, resumed inserts, and up-to-date.

Estimated code review effort: 2 (Simple) | ~12 minutes

Sequence Diagram(s)

sequenceDiagram
  participant PersistedAdapter
  participant ElectricCollection
  participant ShapeStream
  PersistedAdapter->>ElectricCollection: hydrate persisted rows and resume metadata
  ElectricCollection->>ShapeStream: resume with persisted offset and handle
  ShapeStream->>ElectricCollection: resumed insert and up-to-date message
  ElectricCollection->>PersistedAdapter: persist final row state
Loading

Possibly related issues

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Title check ✅ Passed The title clearly matches the main fix: preserving persisted rows during progressive resume.
Description check ✅ Passed The description covers summary, root cause, changes, and validation, though the template's checklist and release-impact sections are missing.
Linked Issues check ✅ Passed The code and regression test address #1478 by preserving hydrated rows while resuming from persisted Electric metadata.
Out of Scope Changes check ✅ Passed The changes appear scoped to the bug fix, regression test, and changeset, with no unrelated additions evident.
Docstring Coverage ✅ Passed Docstring coverage is 100.00% which is sufficient. The required threshold is 80.00%.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@KyleAMathews KyleAMathews left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

thanks!

@pkg-pr-new

pkg-pr-new Bot commented Jul 13, 2026

Copy link
Copy Markdown
More templates

@tanstack/angular-db

npm i https://pkg.pr.new/@tanstack/angular-db@1493

@tanstack/browser-db-sqlite-persistence

npm i https://pkg.pr.new/@tanstack/browser-db-sqlite-persistence@1493

@tanstack/capacitor-db-sqlite-persistence

npm i https://pkg.pr.new/@tanstack/capacitor-db-sqlite-persistence@1493

@tanstack/cloudflare-durable-objects-db-sqlite-persistence

npm i https://pkg.pr.new/@tanstack/cloudflare-durable-objects-db-sqlite-persistence@1493

@tanstack/db

npm i https://pkg.pr.new/@tanstack/db@1493

@tanstack/db-ivm

npm i https://pkg.pr.new/@tanstack/db-ivm@1493

@tanstack/db-sqlite-persistence-core

npm i https://pkg.pr.new/@tanstack/db-sqlite-persistence-core@1493

@tanstack/electric-db-collection

npm i https://pkg.pr.new/@tanstack/electric-db-collection@1493

@tanstack/electron-db-sqlite-persistence

npm i https://pkg.pr.new/@tanstack/electron-db-sqlite-persistence@1493

@tanstack/expo-db-sqlite-persistence

npm i https://pkg.pr.new/@tanstack/expo-db-sqlite-persistence@1493

@tanstack/node-db-sqlite-persistence

npm i https://pkg.pr.new/@tanstack/node-db-sqlite-persistence@1493

@tanstack/offline-transactions

npm i https://pkg.pr.new/@tanstack/offline-transactions@1493

@tanstack/powersync-db-collection

npm i https://pkg.pr.new/@tanstack/powersync-db-collection@1493

@tanstack/query-db-collection

npm i https://pkg.pr.new/@tanstack/query-db-collection@1493

@tanstack/react-db

npm i https://pkg.pr.new/@tanstack/react-db@1493

@tanstack/react-native-db-sqlite-persistence

npm i https://pkg.pr.new/@tanstack/react-native-db-sqlite-persistence@1493

@tanstack/rxdb-db-collection

npm i https://pkg.pr.new/@tanstack/rxdb-db-collection@1493

@tanstack/solid-db

npm i https://pkg.pr.new/@tanstack/solid-db@1493

@tanstack/svelte-db

npm i https://pkg.pr.new/@tanstack/svelte-db@1493

@tanstack/tauri-db-sqlite-persistence

npm i https://pkg.pr.new/@tanstack/tauri-db-sqlite-persistence@1493

@tanstack/trailbase-db-collection

npm i https://pkg.pr.new/@tanstack/trailbase-db-collection@1493

@tanstack/vue-db

npm i https://pkg.pr.new/@tanstack/vue-db@1493

commit: d7ca8eb

@KyleAMathews KyleAMathews merged commit 6ed8b15 into TanStack:main Jul 13, 2026
11 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.

Persisted collection with progressive sync mode wiped on reconnect

2 participants