From ba275eb8221a1165dd11c572ebcd81b209378054 Mon Sep 17 00:00:00 2001 From: Alex Velez Date: Tue, 23 Jul 2024 22:16:22 -0500 Subject: [PATCH 1/2] Fix undo remove last child --- .../frontend/shared/data/changes.js | 31 ++++++++++++------- 1 file changed, 19 insertions(+), 12 deletions(-) diff --git a/contentcuration/contentcuration/frontend/shared/data/changes.js b/contentcuration/contentcuration/frontend/shared/data/changes.js index f081a11678..7bf6f40c4d 100644 --- a/contentcuration/contentcuration/frontend/shared/data/changes.js +++ b/contentcuration/contentcuration/frontend/shared/data/changes.js @@ -140,7 +140,7 @@ export class ChangeTracker { // We'll go through each change one by one and revert each. // // R. Tibbles: I think this could be done in two queries (TODO) - return promiseChunk(this._changes.reverse(), 1, ([change]) => { + return promiseChunk(this._changes.reverse(), 1, async ([change]) => { const resource = INDEXEDDB_RESOURCES[change.table]; if (!resource) { if (process.env.NODE_ENV !== 'production') { @@ -150,6 +150,15 @@ export class ChangeTracker { } return Promise.resolve(); } + + // Query siblings before starting the transaction + // to avoid any potential API call inside the transaction + let siblings; + if (change.type === CHANGE_TYPES.MOVED && change.oldObj) { + const { parent } = change.oldObj; + siblings = await resource.where({ parent }, false); + } + return resource.transaction({}, CHANGES_TABLE, () => { // If we had created something, we'll delete it // Special MOVED case here comes from the operation of COPY then MOVE for duplicating @@ -170,17 +179,15 @@ export class ChangeTracker { const { parent, lft } = change.oldObj; // Collect the affected node's siblings prior to the change - return resource.where({ parent }, false).then(siblings => { - // Search the siblings ordered by `lft` to find the first a sibling - // where we should move the node, positioned before that sibling - const relativeSibling = sortBy(siblings, 'lft').find(sibling => sibling.lft >= lft); - if (relativeSibling) { - return resource.move(change.key, relativeSibling.id, RELATIVE_TREE_POSITIONS.LEFT); - } - - // this handles if there were no siblings OR if the deleted node was at the end - return resource.move(change.key, parent, RELATIVE_TREE_POSITIONS.LAST_CHILD); - }); + // Search the siblings ordered by `lft` to find the first a sibling + // where we should move the node, positioned before that sibling + const relativeSibling = sortBy(siblings, 'lft').find(sibling => sibling.lft >= lft); + if (relativeSibling) { + return resource.move(change.key, relativeSibling.id, RELATIVE_TREE_POSITIONS.LEFT); + } + + // this handles if there were no siblings OR if the deleted node was at the end + return resource.move(change.key, parent, RELATIVE_TREE_POSITIONS.LAST_CHILD); } else { if (process.env.NODE_ENV !== 'production') { /* eslint-disable no-console */ From 1a732718b7647703bb6d224e52a97c2e725b803d Mon Sep 17 00:00:00 2001 From: Alex Velez Date: Mon, 5 Aug 2024 14:42:20 -0500 Subject: [PATCH 2/2] Fix siblings fetch --- contentcuration/contentcuration/frontend/shared/data/changes.js | 1 + .../contentcuration/frontend/shared/data/resources.js | 1 + 2 files changed, 2 insertions(+) diff --git a/contentcuration/contentcuration/frontend/shared/data/changes.js b/contentcuration/contentcuration/frontend/shared/data/changes.js index 7bf6f40c4d..9c00afa7bd 100644 --- a/contentcuration/contentcuration/frontend/shared/data/changes.js +++ b/contentcuration/contentcuration/frontend/shared/data/changes.js @@ -157,6 +157,7 @@ export class ChangeTracker { if (change.type === CHANGE_TYPES.MOVED && change.oldObj) { const { parent } = change.oldObj; siblings = await resource.where({ parent }, false); + siblings = siblings.filter(sibling => sibling.id !== change.key); } return resource.transaction({}, CHANGES_TABLE, () => { diff --git a/contentcuration/contentcuration/frontend/shared/data/resources.js b/contentcuration/contentcuration/frontend/shared/data/resources.js index e23399479f..b1d8319c21 100644 --- a/contentcuration/contentcuration/frontend/shared/data/resources.js +++ b/contentcuration/contentcuration/frontend/shared/data/resources.js @@ -1363,6 +1363,7 @@ export const ContentNode = new TreeResource({ return Promise.all([getNode, this.where({ parent: parent.id }, false)]).then( ([node, siblings]) => { let lft = 1; + siblings = siblings.filter(s => s.id !== id); if (siblings.length) { // If we're creating, we don't need to worry about passing the ID lft = this.getNewSortOrder(isCreate ? null : id, target, position, siblings);