From b30792a3da3f104ea1b16f7154b88585bf167406 Mon Sep 17 00:00:00 2001 From: zadam Date: Tue, 21 Dec 2021 11:04:41 +0100 Subject: [PATCH 1/3] make sure that the info about periodically erased entities is sent to the frontend --- src/services/notes.js | 23 +++++++++++++---------- 1 file changed, 13 insertions(+), 10 deletions(-) diff --git a/src/services/notes.js b/src/services/notes.js index 4dee6eb2b..b137517e4 100644 --- a/src/services/notes.js +++ b/src/services/notes.js @@ -732,23 +732,26 @@ function eraseAttributes(attributeIdsToErase) { } function eraseDeletedEntities(eraseEntitiesAfterTimeInSeconds = null) { - if (eraseEntitiesAfterTimeInSeconds === null) { - eraseEntitiesAfterTimeInSeconds = optionService.getOptionInt('eraseEntitiesAfterTimeInSeconds'); - } + // this is important also so that the erased entity changes are sent to the connected clients + sql.transactional(() => { + if (eraseEntitiesAfterTimeInSeconds === null) { + eraseEntitiesAfterTimeInSeconds = optionService.getOptionInt('eraseEntitiesAfterTimeInSeconds'); + } - const cutoffDate = new Date(Date.now() - eraseEntitiesAfterTimeInSeconds * 1000); + const cutoffDate = new Date(Date.now() - eraseEntitiesAfterTimeInSeconds * 1000); - const noteIdsToErase = sql.getColumn("SELECT noteId FROM notes WHERE isDeleted = 1 AND utcDateModified <= ?", [dateUtils.utcDateTimeStr(cutoffDate)]); + const noteIdsToErase = sql.getColumn("SELECT noteId FROM notes WHERE isDeleted = 1 AND utcDateModified <= ?", [dateUtils.utcDateTimeStr(cutoffDate)]); - eraseNotes(noteIdsToErase); + eraseNotes(noteIdsToErase); - const branchIdsToErase = sql.getColumn("SELECT branchId FROM branches WHERE isDeleted = 1 AND utcDateModified <= ?", [dateUtils.utcDateTimeStr(cutoffDate)]); + const branchIdsToErase = sql.getColumn("SELECT branchId FROM branches WHERE isDeleted = 1 AND utcDateModified <= ?", [dateUtils.utcDateTimeStr(cutoffDate)]); - eraseBranches(branchIdsToErase); + eraseBranches(branchIdsToErase); - const attributeIdsToErase = sql.getColumn("SELECT attributeId FROM attributes WHERE isDeleted = 1 AND utcDateModified <= ?", [dateUtils.utcDateTimeStr(cutoffDate)]); + const attributeIdsToErase = sql.getColumn("SELECT attributeId FROM attributes WHERE isDeleted = 1 AND utcDateModified <= ?", [dateUtils.utcDateTimeStr(cutoffDate)]); - eraseAttributes(attributeIdsToErase); + eraseAttributes(attributeIdsToErase); + }); } function eraseNotesWithDeleteId(deleteId) { From 1e8472266f16283c0d027e0a61f8a595786e5407 Mon Sep 17 00:00:00 2001 From: zadam Date: Tue, 21 Dec 2021 13:22:13 +0100 Subject: [PATCH 2/3] small fixes --- src/public/app/services/entrypoints.js | 8 ++++++-- src/public/app/services/tree.js | 4 ++++ src/services/consistency_checks.js | 3 ++- src/services/special_notes.js | 1 + 4 files changed, 13 insertions(+), 3 deletions(-) diff --git a/src/public/app/services/entrypoints.js b/src/public/app/services/entrypoints.js index 2daa21b25..dd0152745 100644 --- a/src/public/app/services/entrypoints.js +++ b/src/public/app/services/entrypoints.js @@ -213,9 +213,13 @@ export default class Entrypoints extends Component { } else if (note.mime.endsWith("env=backend")) { await server.post('script/run/' + note.noteId); } else if (note.mime === 'text/x-sqlite;schema=trilium') { - const {results} = await server.post("sql/execute/" + note.noteId); + const resp = await server.post("sql/execute/" + note.noteId); - await appContext.triggerEvent('sqlQueryResults', {ntxId: ntxId, results: results}); + if (!resp.success) { + alert("Error occurred while executing SQL query: " + resp.message); + } + + await appContext.triggerEvent('sqlQueryResults', {ntxId: ntxId, results: resp.results}); } toastService.showMessage("Note executed"); diff --git a/src/public/app/services/tree.js b/src/public/app/services/tree.js index 7bed9a7a9..e1ea8f24a 100644 --- a/src/public/app/services/tree.js +++ b/src/public/app/services/tree.js @@ -83,6 +83,10 @@ async function resolveNotePathToSegments(notePath, hoistedNoteId = 'root', logEr if (someNotePath) { // in case it's root the path may be empty const pathToRoot = someNotePath.split("/").reverse().slice(1); + if (!pathToRoot.includes("root")) { + pathToRoot.push('root'); + } + for (const noteId of pathToRoot) { effectivePathSegments.push(noteId); } diff --git a/src/services/consistency_checks.js b/src/services/consistency_checks.js index f12f930e3..2869c0390 100644 --- a/src/services/consistency_checks.js +++ b/src/services/consistency_checks.js @@ -258,7 +258,8 @@ class ConsistencyChecks { FROM branches WHERE noteId = ? and parentNoteId = ? - and isDeleted = 0`, [noteId, parentNoteId]); + and isDeleted = 0 + ORDER BY utcDateCreated`, [noteId, parentNoteId]); const branches = branchIds.map(branchId => becca.getBranch(branchId)); diff --git a/src/services/special_notes.js b/src/services/special_notes.js index 9c27f7f14..41c2f99e7 100644 --- a/src/services/special_notes.js +++ b/src/services/special_notes.js @@ -34,6 +34,7 @@ function getHiddenRoot() { if (!hidden) { hidden = noteService.createNewNote({ + branchId: 'hidden', noteId: 'hidden', title: 'hidden', type: 'text', From 10a5773c66e678c6d2bd3bd9dc9952d5cd76b795 Mon Sep 17 00:00:00 2001 From: zadam Date: Tue, 21 Dec 2021 14:25:26 +0100 Subject: [PATCH 3/3] added consistency check to reconcile erased status between entity_changes and data --- src/services/consistency_checks.js | 25 +++++++++++++++++++++++-- 1 file changed, 23 insertions(+), 2 deletions(-) diff --git a/src/services/consistency_checks.js b/src/services/consistency_checks.js index 2869c0390..76debe2db 100644 --- a/src/services/consistency_checks.js +++ b/src/services/consistency_checks.js @@ -538,6 +538,27 @@ class ConsistencyChecks { logError(`Unrecognized entity change id=${id}, entityName=${entityName}, entityId=${entityId}`); } }); + + this.findAndFixIssues(` + SELECT + id, entityId + FROM + entity_changes + JOIN ${entityName} ON entityId = ${key} + WHERE + entity_changes.isErased = 1 + AND entity_changes.entityName = '${entityName}'`, + ({id, entityId}) => { + if (this.autoFix) { + sql.execute(`DELETE FROM ${entityName} WHERE ${key} = ?`, [entityId]); + + this.reloadNeeded = true; + + logFix(`Erasing entityName=${entityName}, entityId=${entityId} since entity change id=${id} has it as erased.`); + } else { + logError(`Entity change id=${id} has entityName=${entityName}, entityId=${entityId} as erased, but it's not.`); + } + }); } findEntityChangeIssues() { @@ -604,14 +625,14 @@ class ConsistencyChecks { this.fixedIssues = false; this.reloadNeeded = false; + this.findEntityChangeIssues(); + this.findBrokenReferenceIssues(); this.findExistencyIssues(); this.findLogicIssues(); - this.findEntityChangeIssues(); - this.findWronglyNamedAttributes(); this.findSyncIssues();