Skip to content

Conversation

@samwillis
Copy link
Collaborator

@samwillis samwillis commented Jun 9, 2025

This is a significant refactor of the Collection replacing the Store based derived state with a more fine grade system that will be faster and more efficient.

Rather than computing a full "derived state" on each change, we only compute a derived upserts and deletes, along with emitting insert/update/delete messages on each change. This should result in much less object churn and far less GC.

The Collection is now also more Map like with many similar methods keys, values, entries, get(key) and has(key).

the config.getId callback has been renamed config.getKey for constancy with the Map like interface.

You can subscribe to either changes to the whole collection, or to a single key - perfect for fine grade reactivity.

Queries still "sync" into a collection as their materialised state.

Finally, as there is only loose coupling between the live query system and collections, the latter can be used without a live query if wanted.

We have temporarily added asStoreMap and asStoreArray to the collection to enable use with only slightly modified versions of the current frameworks hooks - this will be removed when they have been rewritten to take advantage of the frameworks own reactivity systems for fine grade reactivity.

@changeset-bot
Copy link

changeset-bot bot commented Jun 9, 2025

🦋 Changeset detected

Latest commit: 711c1ba

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 5 packages
Name Type
@tanstack/db-collections Patch
@tanstack/react-db Patch
@tanstack/vue-db Patch
@tanstack/db Patch
@tanstack/db-example-react-todo Patch

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

Copy link
Collaborator

@KyleAMathews KyleAMathews left a comment

Choose a reason for hiding this comment

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

very nice! I love the new Map APIs (though they should probably work on the ID not the internal key?)

@wobsoriano
Copy link
Contributor

Nice! I think the other frameworks were limited due to TS Store and this changes it. I'll update the Svelte PR and improve existing ones once this lands 🎉

@samwillis
Copy link
Collaborator Author

samwillis commented Jun 10, 2025

@KyleAMathews I've made those changes.

100% agree on the key, the composite key should be an internal detail that isn't leaked. It would make much more sense for the internal map to just use the actual id of the collection, it makes much more sense for the public api, and then we are able to in future use it as an index on the id for faster queries that use the id.

I'm not 100% sure on how you are using the composite key, I would need to look through the transaction code to understand where to make the changes. But my thinking was to just compute it on the fly when needed, rather than persist it.

The other thing I wanted to suggest is that we remove the restriction on having to have a sync config. A local collection should just be a collection without one. (it may need a dummy one, I've not looked in detail)

@samwillis samwillis changed the title WIP reactor collection WIP refactor collection Jun 10, 2025
…balKey` for transactions, and rename getId to getKey
@samwillis samwillis force-pushed the samwillis/refactor-collection branch from 6604a33 to bffed75 Compare June 12, 2025 12:40
@pkg-pr-new
Copy link

pkg-pr-new bot commented Jun 12, 2025

@tanstack/db-example-react-todo

npm i https://pkg.pr.new/@tanstack/db@155
npm i https://pkg.pr.new/@tanstack/db-collections@155
npm i https://pkg.pr.new/@tanstack/react-db@155
npm i https://pkg.pr.new/@tanstack/vue-db@155

commit: 711c1ba

@samwillis samwillis changed the title WIP refactor collection refactor collection for fine grade reactivity Jun 12, 2025
@samwillis samwillis force-pushed the samwillis/refactor-collection branch from fe422a2 to 044f46b Compare June 12, 2025 15:40
@samwillis samwillis marked this pull request as ready for review June 12, 2025 15:43
@samwillis samwillis requested a review from KyleAMathews June 12, 2025 15:43
@samwillis samwillis changed the title refactor collection for fine grade reactivity refactor collection for fine grained reactivity Jun 12, 2025
Copy link
Collaborator

@KyleAMathews KyleAMathews left a comment

Choose a reason for hiding this comment

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

Just a few questions but otherwise looks great!


expect(collection.state).toEqual(
new Map([
[`KEY::${collection.id}/1`, { id: 1, name: `Test User` }],
Copy link
Collaborator

Choose a reason for hiding this comment

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

lovely change haha


// Currently a query with an orderBy will add a _orderByIndex to the items
// so for now we need to sort the array by _orderByIndex if it exists
// TODO: in the future it would be much better is the keys are sorted - this
Copy link
Collaborator

Choose a reason for hiding this comment

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

let's create a follow-up issue

/**
* Subscribe to changes for a specific key
*/
public subscribeChangesKey(
Copy link
Collaborator

Choose a reason for hiding this comment

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

throw error if key doesn't exist?

Copy link
Collaborator

Choose a reason for hiding this comment

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

Or is it useful to preemptively subscribe to a key?

Copy link
Collaborator

Choose a reason for hiding this comment

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

I also don't see any tests for this?

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Yep, I think preemptively subscribing to a key is useful.

I'll add tests.

* Returns a Tanstack Store Map that is updated when the collection changes
* This is a temporary solution to enable the existing framework hooks to work
* with the new internals of Collection until they are rewritten.
* TODO: Remove this once the framework hooks are rewritten.
Copy link
Collaborator

Choose a reason for hiding this comment

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

let's create follow-up issues

@samwillis samwillis merged commit b4602a0 into main Jun 12, 2025
4 checks passed
@samwillis samwillis deleted the samwillis/refactor-collection branch June 12, 2025 16:56
@github-actions github-actions bot mentioned this pull request Jun 12, 2025
cursor bot pushed a commit that referenced this pull request Jul 16, 2025
Co-authored-by: Kyle Mathews <mathews.kyle@gmail.com>
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.

4 participants