Skip to content

Add framework DB adapter package#1699

Open
jherr wants to merge 4 commits into
mainfrom
feat/framework-db-adapter
Open

Add framework DB adapter package#1699
jherr wants to merge 4 commits into
mainfrom
feat/framework-db-adapter

Conversation

@jherr

@jherr jherr commented Jul 26, 2026

Copy link
Copy Markdown

Summary

  • Add a new framework integration package for TanStack DB with live query hooks (useLiveQuery, useLiveSuspenseQuery, useLiveInfiniteQuery, usePacedMutations, useLiveQueryEffect)
  • Port test coverage and shared conformance driver from the React adapter
  • Register docs, installation, skill tree, and doc generation for the new package

Test plan

  • pnpm --filter @tanstack/octane-db build
  • pnpm --filter @tanstack/octane-db test

Made with Cursor

Summary by CodeRabbit

  • New Features
    • Released the Octane framework adapter for TanStack DB as a new package.
    • Added live query hooks, Suspense-enabled live queries, infinite live queries, live query effects, and paced mutations for Octane.
    • Enabled Octane compiler integration and supports incremental adoption alongside React.
  • Documentation
    • Added Octane installation guidance, expanded overview and API reference pages, and created detailed hook/skill documentation for the new adapter.
  • Tests
    • Added conformance coverage and comprehensive unit/type tests for all new hooks, including pagination, Suspense behavior, effects, and mutation pacing.

jherr and others added 2 commits July 26, 2026 11:16
Add a new framework integration package with live query hooks, tests,
docs, and monorepo registration aligned with existing react-db patterns.

Co-authored-by: Cursor <cursoragent@cursor.com>
@coderabbitai

coderabbitai Bot commented Jul 26, 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 Plus

Run ID: bb3d8e36-9b09-4d58-9051-57e72e65c0e9

📥 Commits

Reviewing files that changed from the base of the PR and between f2d1096 and f212053.

📒 Files selected for processing (1)
  • docs/framework/octane/overview.md
🚧 Files skipped from review as they are similar to previous changes (1)
  • docs/framework/octane/overview.md

📝 Walkthrough

Walkthrough

Adds @tanstack/octane-db with Octane-compatible live-query, Suspense, infinite-query, effect, and paced-mutation hooks, compiler slot support, package tooling, tests, generated references, installation guidance, and skill metadata.

Changes

Octane DB adapter

Layer / File(s) Summary
Package contracts and integration
.changeset/*, packages/octane-db/package.json, packages/octane-db/src/index.ts, packages/octane-db/tsconfig*.json, packages/octane-db/vite.config.ts, docs/framework/octane/*, docs/installation.md, scripts/generate-docs.ts, domain_map.yaml, _artifacts/skill_tree.yaml
Defines package metadata, exports, compiler hook-slot configuration, build and test tooling, release metadata, documentation, and skill registration.
Live query subscription core
packages/octane-db/src/slot.ts, packages/octane-db/src/useLiveQuery.ts, packages/db/src/live-query-adapter.ts
Adds typed query inputs and results, conditional disabling, collection creation and reuse, external-store subscriptions, stable snapshots, and compiler slot helpers.
Suspense, effects, and paced mutations
packages/octane-db/src/useLiveSuspenseQuery.ts, packages/octane-db/src/useLiveQueryEffect.ts, packages/octane-db/src/usePacedMutations.ts
Adds Suspense/ErrorBoundary behavior, lifecycle-managed effects, stable mutation callbacks, and strategy-aware paced mutation instances.
Infinite query pagination
packages/octane-db/src/useLiveInfiniteQuery.ts
Adds windowed page loading, peek-ahead hasNextPage detection, dependency and collection resets, and flattened pagination results.
Behavioral and type validation
packages/octane-db/tests/*
Adds conformance, hook behavior, lifecycle, pagination, Suspense, mutation, setup, and TypeScript inference coverage.

Estimated code review effort: 5 (Critical) | ~120 minutes

Sequence Diagram(s)

sequenceDiagram
  participant OctaneComponent
  participant useLiveQuery
  participant Collection
  participant ReactStore
  OctaneComponent->>useLiveQuery: invoke query hook
  useLiveQuery->>Collection: create or reuse live query
  useLiveQuery->>ReactStore: subscribe and read snapshot
  Collection-->>ReactStore: publish live changes
  ReactStore-->>OctaneComponent: render updated data
Loading
🚥 Pre-merge checks | ✅ 3 | ❌ 2

❌ Failed checks (2 warnings)

Check name Status Explanation Resolution
Description check ⚠️ Warning The description is missing the required template sections and checklist/release impact details. Rewrite it with the required ## 🎯 Changes, ## ✅ Checklist, and ## 🚀 Release Impact sections, including the release-status checkbox items.
Docstring Coverage ⚠️ Warning Docstring coverage is 41.67% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (3 passed)
Check name Status Explanation
Title check ✅ Passed The title clearly summarizes the main change: adding a new framework DB adapter package.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feat/framework-db-adapter

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.

@socket-security

socket-security Bot commented Jul 26, 2026

Copy link
Copy Markdown

Review the following changes in direct dependencies. Learn more about Socket for GitHub.

Diff Package Supply Chain
Security
Vulnerability Quality Maintenance License
Addednpm/​@​octanejs/​vite-plugin@​0.1.13761007096100
Addednpm/​@​octanejs/​testing-library@​0.1.107410010095100
Addednpm/​octane@​0.1.13751008296100

View full report

@socket-security

socket-security Bot commented Jul 26, 2026

Copy link
Copy Markdown

Warning

Review the following alerts detected in dependencies.

According to your organization's Security Policy, it is recommended to resolve "Warn" alerts. Learn more about Socket for GitHub.

Action Severity Alert  (click "▶" to expand/collapse)
Warn Medium
Low adoption: npm octane

Location: Package overview

From: packages/octane-db/package.jsonnpm/octane@0.1.13

ℹ Read more on: This package | This alert | What are unpopular packages?

Next steps: Take a moment to review the security alert above. Review the linked package source code to understand the potential risk. Ensure the package is not malicious before proceeding. If you're unsure how to proceed, reach out to your security team or ask the Socket team for help at support@socket.dev.

Suggestion: Unpopular packages may have less maintenance and contain other problems.

Mark the package as acceptable risk. To ignore this alert only in this pull request, reply with the comment @SocketSecurity ignore npm/octane@0.1.13. You can also ignore all packages with @SocketSecurity ignore-all. To ignore an alert for all future pull requests, use Socket's Dashboard to change the triage state of this alert.

View full report

@pkg-pr-new

pkg-pr-new Bot commented Jul 26, 2026

Copy link
Copy Markdown
More templates

@tanstack/angular-db

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

@tanstack/browser-db-sqlite-persistence

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

@tanstack/capacitor-db-sqlite-persistence

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

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

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

@tanstack/db

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

@tanstack/db-ivm

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

@tanstack/db-sqlite-persistence-core

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

@tanstack/electric-db-collection

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

@tanstack/electron-db-sqlite-persistence

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

@tanstack/expo-db-sqlite-persistence

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

@tanstack/node-db-sqlite-persistence

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

@tanstack/octane-db

npm i https://pkg.pr.new/TanStack/db/@tanstack/octane-db@1699

@tanstack/offline-transactions

npm i https://pkg.pr.new/TanStack/db/@tanstack/offline-transactions@1699

@tanstack/powersync-db-collection

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

@tanstack/query-db-collection

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

@tanstack/react-db

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

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

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

@tanstack/rxdb-db-collection

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

@tanstack/solid-db

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

@tanstack/svelte-db

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

@tanstack/tauri-db-sqlite-persistence

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

@tanstack/trailbase-db-collection

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

@tanstack/vue-db

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

commit: f212053

@github-actions

Copy link
Copy Markdown
Contributor

Size Change: 0 B

Total Size: 125 kB

ℹ️ View Unchanged
Filename Size
packages/db/dist/esm/collection/change-events.js 1.43 kB
packages/db/dist/esm/collection/changes.js 1.38 kB
packages/db/dist/esm/collection/cleanup-queue.js 810 B
packages/db/dist/esm/collection/events.js 434 B
packages/db/dist/esm/collection/index.js 3.62 kB
packages/db/dist/esm/collection/indexes.js 1.99 kB
packages/db/dist/esm/collection/lifecycle.js 1.69 kB
packages/db/dist/esm/collection/mutations.js 2.47 kB
packages/db/dist/esm/collection/state.js 5.48 kB
packages/db/dist/esm/collection/subscription.js 3.74 kB
packages/db/dist/esm/collection/sync.js 2.88 kB
packages/db/dist/esm/collection/transaction-metadata.js 144 B
packages/db/dist/esm/deferred.js 207 B
packages/db/dist/esm/errors.js 5.1 kB
packages/db/dist/esm/event-emitter.js 748 B
packages/db/dist/esm/index.js 3.16 kB
packages/db/dist/esm/indexes/auto-index.js 829 B
packages/db/dist/esm/indexes/base-index.js 784 B
packages/db/dist/esm/indexes/basic-index.js 2.17 kB
packages/db/dist/esm/indexes/btree-index.js 2.29 kB
packages/db/dist/esm/indexes/index-registry.js 820 B
packages/db/dist/esm/indexes/reverse-index.js 557 B
packages/db/dist/esm/live-query-adapter.js 318 B
packages/db/dist/esm/local-only.js 916 B
packages/db/dist/esm/local-storage.js 2.12 kB
packages/db/dist/esm/optimistic-action.js 359 B
packages/db/dist/esm/paced-mutations.js 496 B
packages/db/dist/esm/proxy.js 3.75 kB
packages/db/dist/esm/query/builder/functions.js 1.47 kB
packages/db/dist/esm/query/builder/index.js 5.84 kB
packages/db/dist/esm/query/builder/ref-proxy.js 1.24 kB
packages/db/dist/esm/query/compiler/evaluators.js 1.89 kB
packages/db/dist/esm/query/compiler/expressions.js 430 B
packages/db/dist/esm/query/compiler/group-by.js 3.56 kB
packages/db/dist/esm/query/compiler/index.js 6.67 kB
packages/db/dist/esm/query/compiler/joins.js 2.5 kB
packages/db/dist/esm/query/compiler/lazy-targets.js 923 B
packages/db/dist/esm/query/compiler/order-by.js 1.74 kB
packages/db/dist/esm/query/compiler/select.js 1.53 kB
packages/db/dist/esm/query/effect.js 4.77 kB
packages/db/dist/esm/query/expression-helpers.js 1.43 kB
packages/db/dist/esm/query/ir.js 1.25 kB
packages/db/dist/esm/query/live-query-collection.js 360 B
packages/db/dist/esm/query/live/collection-config-builder.js 9.1 kB
packages/db/dist/esm/query/live/collection-registry.js 264 B
packages/db/dist/esm/query/live/collection-subscriber.js 1.93 kB
packages/db/dist/esm/query/live/internal.js 145 B
packages/db/dist/esm/query/live/utils.js 1.81 kB
packages/db/dist/esm/query/optimizer.js 2.92 kB
packages/db/dist/esm/query/predicate-utils.js 2.97 kB
packages/db/dist/esm/query/query-once.js 359 B
packages/db/dist/esm/query/subset-dedupe.js 960 B
packages/db/dist/esm/scheduler.js 1.3 kB
packages/db/dist/esm/SortedMap.js 1.3 kB
packages/db/dist/esm/strategies/debounceStrategy.js 247 B
packages/db/dist/esm/strategies/queueStrategy.js 428 B
packages/db/dist/esm/strategies/throttleStrategy.js 246 B
packages/db/dist/esm/transactions.js 3.04 kB
packages/db/dist/esm/utils.js 927 B
packages/db/dist/esm/utils/array-utils.js 273 B
packages/db/dist/esm/utils/browser-polyfills.js 304 B
packages/db/dist/esm/utils/btree.js 5.61 kB
packages/db/dist/esm/utils/comparison.js 1.15 kB
packages/db/dist/esm/utils/cursor.js 457 B
packages/db/dist/esm/utils/index-optimization.js 2.39 kB
packages/db/dist/esm/utils/type-guards.js 157 B
packages/db/dist/esm/utils/uuid.js 449 B
packages/db/dist/esm/virtual-props.js 360 B

compressed-size-action::db-package-size

@github-actions

Copy link
Copy Markdown
Contributor

Size Change: 0 B

Total Size: 4.22 kB

ℹ️ View Unchanged
Filename Size
packages/react-db/dist/esm/index.js 249 B
packages/react-db/dist/esm/useLiveInfiniteQuery.js 1.32 kB
packages/react-db/dist/esm/useLiveQuery.js 1.33 kB
packages/react-db/dist/esm/useLiveQueryEffect.js 355 B
packages/react-db/dist/esm/useLiveSuspenseQuery.js 567 B
packages/react-db/dist/esm/usePacedMutations.js 401 B

compressed-size-action::react-db-package-size

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Actionable comments posted: 8

🧹 Nitpick comments (11)
packages/octane-db/src/useLiveInfiniteQuery.ts (1)

182-191: 🎯 Functional Correctness | 🔵 Trivial | ⚡ Quick win

JSON.stringify for dep comparison rejects deps that useLiveQuery accepts.

useLiveQuery compares deps by element identity, so a collection, a Date, a function, or any non-serializable value is a valid dep there. Here the same array throws. Beyond the divergence, stringifying on every render is O(size of deps) and treats {a:1,b:2} and {b:2,a:1} as different.

Element-wise identity comparison (as useLiveQuery already does) removes the whole failure mode.

As per coding guidelines: "Be mindful of time complexity in algorithms".

♻️ Proposed refactor
-  // Track deps for query functions (stringify for comparison)
-  let depsKey: string
-  try {
-    depsKey = JSON.stringify(deps)
-  } catch {
-    throw new Error(
-      `useLiveInfiniteQuery: dependency array contains values that cannot be serialized (e.g. circular references). ` +
-        `Ensure all dependency values are JSON-serializable.`,
-    )
-  }
-  const prevDepsKeyRef = useRef(depsKey, subSlot(slot, `deps-key-ref`))
+  // Track deps for query functions (identity comparison, matching useLiveQuery)
+  const prevDepsRef = useRef<Array<unknown>>(deps, subSlot(slot, `deps-ref`))
+  const depsChanged =
+    prevDepsRef.current.length !== deps.length ||
+    prevDepsRef.current.some((dep, i) => dep !== deps[i])

The effect at lines 204-213 then keys off depsChanged and assigns prevDepsRef.current = deps. Note this also makes the throws a descriptive error when deps contain non-serializable values test at packages/octane-db/tests/useLiveInfiniteQuery.test.tsx lines 1876-1906 obsolete.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/octane-db/src/useLiveInfiniteQuery.ts` around lines 182 - 191,
Replace the JSON.stringify-based dependency key logic in useLiveInfiniteQuery
with element-wise identity comparison matching useLiveQuery, using the existing
previous-dependencies ref and deriving depsChanged from that comparison.
Preserve the effect’s update behavior by assigning the current deps to
prevDepsRef.current after processing, and remove the obsolete
serialization-error path and test.

Source: Coding guidelines

packages/octane-db/tests/useLiveInfiniteQuery.test.tsx (2)

1640-1670: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Skipped test leaves the orderBy validation error path uncovered.

The throw at packages/octane-db/src/useLiveInfiniteQuery.ts lines 240-244 now has no coverage. Since Octane surfaces it from a passive effect rather than during render, assert on it via the effect instead of expect(renderHook).toThrow — e.g. spy on the error channel after flushing effects, or expose the validation as a synchronous check during render so it behaves like the other input validation at lines 154-159.

Want me to write the effect-based version of this test, or open an issue to track it?

As per coding guidelines: "Always add unit tests that reproduce a bug before fixing it to ensure the bug is fixed and prevent regression".

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/octane-db/tests/useLiveInfiniteQuery.test.tsx` around lines 1640 -
1670, Replace the skipped test around useLiveInfiniteQuery with an active
regression test for the missing-orderBy validation. Because the error is emitted
from a passive effect rather than render, flush effects and assert through the
established error channel instead of using expect(renderHook).toThrow; preserve
the existing collection setup and ORDER BY/setWindow() validation expectation.

Source: Coding guidelines


10-11: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Use a shared test entry instead of importing @tanstack/db internals.

mockSyncCollectionOptions is only exported from packages/db/tests/utils.js, and createFilterFunctionFromExpression comes from packages/db/src/collection/change-events.js, so this adapter test is coupled to another package’s internal path instead of using the package’s public API or a shared test-utils entry.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/octane-db/tests/useLiveInfiniteQuery.test.tsx` around lines 10 - 11,
Update useLiveInfiniteQuery.test.tsx to stop importing mockSyncCollectionOptions
and createFilterFunctionFromExpression through packages/db test or source
internals; use the shared test entry or public `@tanstack/db` API that exposes
these helpers instead, while preserving the test behavior.
packages/octane-db/tests/useLiveSuspenseQuery.test.tsx (2)

13-13: 📐 Maintainability & Code Quality | 🔵 Trivial | 💤 Low value

children: unknown is looser than needed. Use Octane's node type (e.g. JSX.Element / the framework's Node type) so the wrappers get real type checking on what they render.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/octane-db/tests/useLiveSuspenseQuery.test.tsx` at line 13, Update
the ChildrenProps type used by the test wrappers to replace children: unknown
with Octane’s node type, such as JSX.Element or the framework’s established Node
type, so rendered children receive proper type checking.

Source: Coding guidelines


662-668: 📐 Maintainability & Code Quality | 🔵 Trivial | 💤 Low value

Test reaches into collection._sync internals. Underscore-prefixed access couples this suite to private plumbing; if @tanstack/db exposes (or can expose) a public helper for tracking a load promise, prefer that.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/octane-db/tests/useLiveSuspenseQuery.test.tsx` around lines 662 -
668, Update the test around the live query collection’s load-promise setup to
use a public API for tracking the promise instead of reaching through
collection._sync.trackLoadPromise. Reuse an existing exposed helper if
available, or add the smallest public helper needed, while preserving the
assertions that isLoadingSubset is true and status remains ready.

Source: Coding guidelines

packages/octane-db/tests/usePacedMutations.test.tsx (2)

44-47: 📐 Maintainability & Code Quality | 🔵 Trivial | 💤 Low value

let tx is implicitly any. Annotate as Transaction<Item> (or Transaction<Item> | undefined) so tx!.state and tx!.isPersisted are actually type-checked.

Also applies to: 83-86, 121-124

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/octane-db/tests/usePacedMutations.test.tsx` around lines 44 - 47,
Annotate the transaction variables assigned from result.current in the affected
usePacedMutations test cases as Transaction<Item> (or Transaction<Item> |
undefined), including the cases around lines 44, 83, and 121, so subsequent
tx!.state and tx!.isPersisted accesses are type-checked.

Source: Coding guidelines


21-32: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Extract the identical "create + ready a collection" setup. The same six lines (create with mockSyncCollectionOptionsNoInitialState, preload, begin/commit/markReady, await) appear verbatim in all three smoke tests, and all three reuse the id test. A small helper taking a unique id removes the duplication and the id collision.

♻️ Suggested helper
+async function createReadyCollection(id: string) {
+  const collection = createCollection(
+    mockSyncCollectionOptionsNoInitialState<Item>({
+      id,
+      getKey: (item) => item.id,
+    }),
+  )
+  const preloadPromise = collection.preload()
+  collection.utils.begin()
+  collection.utils.commit()
+  collection.utils.markReady()
+  await preloadPromise
+  return collection
+}
-    const collection = createCollection(
-      mockSyncCollectionOptionsNoInitialState<Item>({
-        id: `test`,
-        getKey: (item) => item.id,
-      }),
-    )
-
-    const preloadPromise = collection.preload()
-    collection.utils.begin()
-    collection.utils.commit()
-    collection.utils.markReady()
-    await preloadPromise
+    const collection = await createReadyCollection(`paced-debounce`)

Also applies to: 60-71, 98-109

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/octane-db/tests/usePacedMutations.test.tsx` around lines 21 - 32,
Extract the repeated collection initialization sequence from the three smoke
tests into a shared async helper that accepts a unique collection id, creates
the collection with mockSyncCollectionOptionsNoInitialState, preloads it, runs
begin/commit/markReady, awaits preload completion, and returns the ready
collection. Replace each duplicated setup with this helper and pass a distinct
id for each test instead of reusing “test”.

Source: Coding guidelines

packages/octane-db/tests/useLiveQuery.test.tsx (2)

1227-1228: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Three comments state the opposite of the assertion they precede. Line 1227 says "isLoading should be true" before expect(...isLoading).toBe(false); Line 1463 says "transitions from false to true" (it's true→false); Line 1506 says "Initially should be false" before expect(...).toBe(true). Inverted comments are worse than none here.

Also applies to: 1462-1463, 1506-1507

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/octane-db/tests/useLiveQuery.test.tsx` around lines 1227 - 1228,
Correct the three misleading comments in the live-query tests: update the
comment near the pre-created syncing collection to state that isLoading is
false, the transition comment near line 1463 to describe true-to-false behavior,
and the initial-state comment near line 1506 to state that isLoading is true.
Leave the assertions unchanged.

Source: Coding guidelines


90-90: 📐 Maintainability & Code Quality | 🔵 Trivial | 💤 Low value

Duplicate collection ids reused across independent tests. Both ported suites create multiple collections under the same ids, which muddies debugging and risks interference if any id-keyed registry behavior changes.

  • packages/octane-db/tests/useLiveQuery.test.tsx#L90-L90: give each collection a unique id instead of reusing test-persons (L90, L126) and test-persons-2 (L168, L202, L237, L274).
  • packages/octane-db/tests/useLiveQuery.test-d.tsx#L27-L27: give each of the four type tests its own id instead of reusing test-persons-2 (L27, L50, L74, L104).
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/octane-db/tests/useLiveQuery.test.tsx` at line 90, Use distinct
collection ids for every independent test in
packages/octane-db/tests/useLiveQuery.test.tsx, replacing repeated test-persons
and test-persons-2 values at all referenced locations. Also assign unique ids to
each of the four type tests in packages/octane-db/tests/useLiveQuery.test-d.tsx
instead of reusing test-persons-2; no other test behavior needs to change.
packages/octane-db/tests/conformance.test.tsx (1)

1-11: 📐 Maintainability & Code Quality | 🔵 Trivial | 💤 Low value

Stale React references in the Octane driver docs. The header says the realm-sensitive imports come from the "React package's @tanstack/db", and Line 139 calls null-return "React's disabled convention". Retitle both to Octane to avoid confusion for the next porter.

♻️ Suggested wording
- * Everything realm-sensitive — collection creation and query operators — is
- * imported here (React package's `@tanstack/db`) and handed to the shared
- * scenarios, so instances match what this package's `useLiveQuery` expects.
+ * Everything realm-sensitive — collection creation and query operators — is
+ * imported here (this package's `@tanstack/db` realm) and handed to the shared
+ * scenarios, so instances match what this package's `useLiveQuery` expects.
-  // React's disabled convention: the query callback returns null.
+  // Octane adapter's disabled convention: the query callback returns null.
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/octane-db/tests/conformance.test.tsx` around lines 1 - 11, Update
the Octane driver documentation to remove stale React references: revise the
header comment to identify the imports as coming from Octane’s `@tanstack/db`,
and update the null-return wording near the disabled-convention documentation to
refer to Octane rather than React. Keep the documented behavior unchanged.

Source: Coding guidelines

packages/octane-db/tests/useLiveQuery.test-d.tsx (1)

42-44: 📐 Maintainability & Code Quality | 🔵 Trivial | 💤 Low value

Align expectTypeOf matchers to toExtend. This file already uses toExtend for collection assertions, but the data assertions still use the deprecated toMatchTypeOf; replace the remaining occurrences at lines 42, 66, 96, and 124.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/octane-db/tests/useLiveQuery.test-d.tsx` around lines 42 - 44,
Replace the deprecated toMatchTypeOf matcher with toExtend in the data
assertions of useLiveQuery tests at the referenced occurrences, while preserving
each existing expected type and assertion structure.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@docs/framework/octane/overview.md`:
- Around line 26-33: Update the Octane documentation examples, including
TodoList and the snippets around postsCollection, category, and gt, so every
referenced identifier is either declared in the example setup or imported from
the appropriate package. Add only the minimal shared setup needed, or explicitly
indicate that values are defined earlier, and ensure each snippet compiles as
written.

In `@packages/octane-db/skills/octane-db/SKILL.md`:
- Around line 220-232: Update the comment following the useLiveQuery projection
to document project.issues as an array of objects containing id and title,
matching the objects selected inside toArray, rather than string[].
- Around line 135-143: Update the useLiveInfiniteQuery call to either apply
category in the query predicate so changing category affects results, or remove
category from the dependency array if the query is intentionally
category-independent; keep the remaining pagination and ordering behavior
unchanged.
- Around line 19-23: Register useLiveQueryEffect consistently across the Octane
metadata: in packages/octane-db/skills/octane-db/SKILL.md at lines 19-23 add
useLiveQueryEffect.ts to the source list, and at lines 57-59 add its hook
section; in _artifacts/skill_tree.yaml at lines 172-185 include the hook in the
description and source references; in domain_map.yaml at lines 306-308 add it to
config_surface.

In `@packages/octane-db/src/slot.ts`:
- Around line 23-29: Adopt splitTrailingSlot as the single non-mutating
implementation for trailing slot extraction. In
packages/octane-db/src/slot.ts:23-29, retain or extend splitTrailingSlot to
provide the parsed argument array needed by callers; update
packages/octane-db/src/useLiveQuery.ts:322-326,
packages/octane-db/src/useLiveQueryEffect.ts:39-42,
packages/octane-db/src/useLiveSuspenseQuery.ts:160-164,
packages/octane-db/src/usePacedMutations.ts:101-104, and
packages/octane-db/src/useLiveInfiniteQuery.ts:141-145 to call it, using the
returned args for deps where required and eliminating inline rest-array
mutation.

In `@packages/octane-db/src/useLiveInfiniteQuery.ts`:
- Around line 18-22: Update isLiveQueryCollectionUtils to handle null and
undefined inputs before accessing setWindow, returning false for absent utils
while preserving the existing function-type check for populated values.
- Around line 147-148: Update the pageSize defaulting in useLiveInfiniteQuery to
use nullish coalescing so an explicit 0 is not silently replaced with 20. If
pageSize 0 is invalid, add explicit validation and reject it rather than
allowing empty-page fetchNextPage loops; leave initialPageParam unchanged.

In `@packages/octane-db/src/useLiveSuspenseQuery.ts`:
- Around line 170-184: Namespace nested useLiveQuery calls to prevent ref-slot
collisions: in packages/octane-db/src/useLiveSuspenseQuery.ts lines 170-184,
pass subSlot(slot, 'lq') to the useLiveQuery call; in
packages/octane-db/src/useLiveInfiniteQuery.ts lines 172-175, pass the same
namespaced slot to both useLiveQuery calls. Preserve the existing
collection-change reset logic in each wrapper.

---

Nitpick comments:
In `@packages/octane-db/src/useLiveInfiniteQuery.ts`:
- Around line 182-191: Replace the JSON.stringify-based dependency key logic in
useLiveInfiniteQuery with element-wise identity comparison matching
useLiveQuery, using the existing previous-dependencies ref and deriving
depsChanged from that comparison. Preserve the effect’s update behavior by
assigning the current deps to prevDepsRef.current after processing, and remove
the obsolete serialization-error path and test.

In `@packages/octane-db/tests/conformance.test.tsx`:
- Around line 1-11: Update the Octane driver documentation to remove stale React
references: revise the header comment to identify the imports as coming from
Octane’s `@tanstack/db`, and update the null-return wording near the
disabled-convention documentation to refer to Octane rather than React. Keep the
documented behavior unchanged.

In `@packages/octane-db/tests/useLiveInfiniteQuery.test.tsx`:
- Around line 1640-1670: Replace the skipped test around useLiveInfiniteQuery
with an active regression test for the missing-orderBy validation. Because the
error is emitted from a passive effect rather than render, flush effects and
assert through the established error channel instead of using
expect(renderHook).toThrow; preserve the existing collection setup and ORDER
BY/setWindow() validation expectation.
- Around line 10-11: Update useLiveInfiniteQuery.test.tsx to stop importing
mockSyncCollectionOptions and createFilterFunctionFromExpression through
packages/db test or source internals; use the shared test entry or public
`@tanstack/db` API that exposes these helpers instead, while preserving the test
behavior.

In `@packages/octane-db/tests/useLiveQuery.test-d.tsx`:
- Around line 42-44: Replace the deprecated toMatchTypeOf matcher with toExtend
in the data assertions of useLiveQuery tests at the referenced occurrences,
while preserving each existing expected type and assertion structure.

In `@packages/octane-db/tests/useLiveQuery.test.tsx`:
- Around line 1227-1228: Correct the three misleading comments in the live-query
tests: update the comment near the pre-created syncing collection to state that
isLoading is false, the transition comment near line 1463 to describe
true-to-false behavior, and the initial-state comment near line 1506 to state
that isLoading is true. Leave the assertions unchanged.
- Line 90: Use distinct collection ids for every independent test in
packages/octane-db/tests/useLiveQuery.test.tsx, replacing repeated test-persons
and test-persons-2 values at all referenced locations. Also assign unique ids to
each of the four type tests in packages/octane-db/tests/useLiveQuery.test-d.tsx
instead of reusing test-persons-2; no other test behavior needs to change.

In `@packages/octane-db/tests/useLiveSuspenseQuery.test.tsx`:
- Line 13: Update the ChildrenProps type used by the test wrappers to replace
children: unknown with Octane’s node type, such as JSX.Element or the
framework’s established Node type, so rendered children receive proper type
checking.
- Around line 662-668: Update the test around the live query collection’s
load-promise setup to use a public API for tracking the promise instead of
reaching through collection._sync.trackLoadPromise. Reuse an existing exposed
helper if available, or add the smallest public helper needed, while preserving
the assertions that isLoadingSubset is true and status remains ready.

In `@packages/octane-db/tests/usePacedMutations.test.tsx`:
- Around line 44-47: Annotate the transaction variables assigned from
result.current in the affected usePacedMutations test cases as Transaction<Item>
(or Transaction<Item> | undefined), including the cases around lines 44, 83, and
121, so subsequent tx!.state and tx!.isPersisted accesses are type-checked.
- Around line 21-32: Extract the repeated collection initialization sequence
from the three smoke tests into a shared async helper that accepts a unique
collection id, creates the collection with
mockSyncCollectionOptionsNoInitialState, preloads it, runs
begin/commit/markReady, awaits preload completion, and returns the ready
collection. Replace each duplicated setup with this helper and pass a distinct
id for each test instead of reusing “test”.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: a9941cbc-6d8f-4dea-93f1-cb4c32476bdb

📥 Commits

Reviewing files that changed from the base of the PR and between 67c840f and 2235dfe.

⛔ Files ignored due to path filters (1)
  • pnpm-lock.yaml is excluded by !**/pnpm-lock.yaml
📒 Files selected for processing (32)
  • .changeset/octane-db-package.md
  • _artifacts/skill_tree.yaml
  • docs/framework/octane/overview.md
  • docs/framework/octane/reference/index.md
  • docs/installation.md
  • domain_map.yaml
  • packages/db/src/live-query-adapter.ts
  • packages/octane-db/CHANGELOG.md
  • packages/octane-db/README.md
  • packages/octane-db/package.json
  • packages/octane-db/skills/octane-db/SKILL.md
  • packages/octane-db/src/index.ts
  • packages/octane-db/src/slot.ts
  • packages/octane-db/src/useLiveInfiniteQuery.ts
  • packages/octane-db/src/useLiveQuery.ts
  • packages/octane-db/src/useLiveQueryEffect.ts
  • packages/octane-db/src/useLiveSuspenseQuery.ts
  • packages/octane-db/src/usePacedMutations.ts
  • packages/octane-db/tests/conformance.test.tsx
  • packages/octane-db/tests/test-setup.ts
  • packages/octane-db/tests/useLiveInfiniteQuery.test.tsx
  • packages/octane-db/tests/useLiveQuery.eager-onstorechange.test.tsx
  • packages/octane-db/tests/useLiveQuery.test-d.tsx
  • packages/octane-db/tests/useLiveQuery.test.tsx
  • packages/octane-db/tests/useLiveQueryEffect.test.tsx
  • packages/octane-db/tests/useLiveSuspenseQuery.test.tsx
  • packages/octane-db/tests/usePacedMutations.test.tsx
  • packages/octane-db/tsconfig.docs.json
  • packages/octane-db/tsconfig.json
  • packages/octane-db/vite.config.ts
  • scripts/generate-docs.ts
  • skill_spec.md

Comment thread docs/framework/octane/overview.md
Comment thread packages/octane-db/skills/octane-db/SKILL.md
Comment thread packages/octane-db/skills/octane-db/SKILL.md
Comment thread packages/octane-db/skills/octane-db/SKILL.md Outdated
Comment thread packages/octane-db/src/slot.ts
Comment thread packages/octane-db/src/useLiveInfiniteQuery.ts
Comment thread packages/octane-db/src/useLiveInfiniteQuery.ts Outdated
Comment thread packages/octane-db/src/useLiveSuspenseQuery.ts
- Fix critical slot collision: useLiveSuspenseQuery and useLiveInfiniteQuery
  passed their own slot symbol verbatim into useLiveQuery, so both derived the
  same subSlot(slot, 'coll-ref') symbol and aliased one ref cell — defeating
  each wrapper's "did the collection change?" reset. Namespace the nested call
  with subSlot(slot, 'lq').
- Guard isLiveQueryCollectionUtils against null/undefined utils before reading
  setWindow.
- useLiveInfiniteQuery: treat pageSize with ?? (not ||) and reject pageSize <= 0
  instead of silently defaulting 0 to 20.
- Adopt the previously-unused splitTrailingSlot helper across all five hooks
  instead of re-implementing the trailing-slot extraction inline.
- Docs/metadata: make octane overview examples self-contained, register
  useLiveQueryEffect in SKILL.md/skill_tree.yaml/domain_map.yaml, use category
  in the infinite-query example, and correct the toArray() result type comment.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Actionable comments posted: 1

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@docs/framework/octane/overview.md`:
- Around line 70-83: Update the useLiveInfiniteQuery example to demonstrate
pagination by adding a “Load more” control that is rendered only when
hasNextPage is true and invokes fetchNextPage when activated; keep the existing
query and page-parameter logic unchanged.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: 61b61441-d0d3-4c4b-b7e7-8776228b6c34

📥 Commits

Reviewing files that changed from the base of the PR and between 2235dfe and f2d1096.

📒 Files selected for processing (9)
  • _artifacts/skill_tree.yaml
  • docs/framework/octane/overview.md
  • domain_map.yaml
  • packages/octane-db/skills/octane-db/SKILL.md
  • packages/octane-db/src/useLiveInfiniteQuery.ts
  • packages/octane-db/src/useLiveQuery.ts
  • packages/octane-db/src/useLiveQueryEffect.ts
  • packages/octane-db/src/useLiveSuspenseQuery.ts
  • packages/octane-db/src/usePacedMutations.ts
🚧 Files skipped from review as they are similar to previous changes (8)
  • domain_map.yaml
  • _artifacts/skill_tree.yaml
  • packages/octane-db/skills/octane-db/SKILL.md
  • packages/octane-db/src/useLiveQueryEffect.ts
  • packages/octane-db/src/usePacedMutations.ts
  • packages/octane-db/src/useLiveInfiniteQuery.ts
  • packages/octane-db/src/useLiveSuspenseQuery.ts
  • packages/octane-db/src/useLiveQuery.ts

Comment thread docs/framework/octane/overview.md Outdated
Address CodeRabbit follow-up: the infinite-query example destructured
fetchNextPage/hasNextPage but never used them. Render the posts and a
guarded "Load more" button, and drop the unused `pages` binding.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
@KyleAMathews

Copy link
Copy Markdown
Collaborator

hey this is great! Could you port this though on top of @kevin-dp's in-progress refactor to a live query framework binding library? #1675 & RFC #1623

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.

2 participants