From 72ae8ddefd4b9372674255b8989deb83876a52f4 Mon Sep 17 00:00:00 2001 From: Steve Ruiz Date: Wed, 20 Mar 2024 12:44:09 +0000 Subject: [PATCH] Don't double squash (#3182) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This PR changes the way `Store.squashHistoryEntries` works. Previously, the function would iterate through every entry and squash it against the current entry (using `squashRecordDiffs`) to get the new current entry. However, `squashRecordDiffs` does basically the same pattern, iterating through the properties of every diff. As a result, each diff would be iterated through twice: once as itself, and once again in the next current. This PR tweaks the function to operate on as many diffs as possible at once. ### Change Type - [x] `sdk` — Changes the tldraw SDK - [ ] `dotcom` — Changes the tldraw.com web app - [ ] `docs` — Changes to the documentation, examples, or templates. - [ ] `vs code` — Changes to the vscode plugin - [ ] `internal` — Does not affect user-facing stuff - [ ] `bugfix` — Bug fix - [ ] `feature` — New feature - [x] `improvement` — Improving existing features - [ ] `chore` — Updating dependencies, other boring stuff - [ ] `galaxy brain` — Architectural changes - [ ] `tests` — Changes to any test code - [ ] `tools` — Changes to infrastructure, CI, internal scripts, debugging tools, etc. - [ ] `dunno` — I don't know ### Test Plan - [x] Unit Tests - [ ] End to end tests ### Release Notes - Minor improvement when modifying multiple shapes at once. --- packages/store/src/lib/Store.ts | 33 ++++++++++++++++++--------------- 1 file changed, 18 insertions(+), 15 deletions(-) diff --git a/packages/store/src/lib/Store.ts b/packages/store/src/lib/Store.ts index 2d24ceec6..c0feabd64 100644 --- a/packages/store/src/lib/Store.ts +++ b/packages/store/src/lib/Store.ts @@ -907,7 +907,9 @@ export function squashRecordDiffs( } /** - * Collect all history entries by their sources. + * Collect all history entries by their adjacent sources. + * For example, [user, user, remote, remote, user] would result in [user, remote, user], + * with adjacent entries of the same source squashed into a single entry. * * @param entries - The array of history entries. * @returns A map of history entries by their sources. @@ -916,28 +918,29 @@ export function squashRecordDiffs( function squashHistoryEntries( entries: HistoryEntry[] ): HistoryEntry[] { - const result: HistoryEntry[] = [] + if (entries.length === 0) return [] - let current = entries[0] + const chunked: HistoryEntry[][] = [] + let chunk: HistoryEntry[] = [entries[0]] let entry: HistoryEntry for (let i = 1, n = entries.length; i < n; i++) { entry = entries[i] - - if (current.source !== entry.source) { - result.push(current) - current = entry - } else { - current = { - source: current.source, - changes: squashRecordDiffs([current.changes, entry.changes]), - } + if (chunk[0].source !== entry.source) { + chunked.push(chunk) + chunk = [] } + chunk.push(entry) } + // Push the last chunk + chunked.push(chunk) - result.push(current) - - return devFreeze(result) + return devFreeze( + chunked.map((chunk) => ({ + source: chunk[0].source, + changes: squashRecordDiffs(chunk.map((e) => e.changes)), + })) + ) } /** @public */