mirror of
				https://github.com/zadam/trilium.git
				synced 2025-10-31 10:26:08 +01:00 
			
		
		
		
	cleanup of isErased obsolete usage
This commit is contained in:
		| @@ -15,7 +15,6 @@ const entityChangesService = require('../services/entity_changes.js'); | ||||
|  * @property {string} type | ||||
|  * @property {string} mime | ||||
|  * @property {string} title | ||||
|  * @property {boolean} isErased | ||||
|  * @property {boolean} isProtected | ||||
|  * @property {string} dateLastEdited | ||||
|  * @property {string} dateCreated | ||||
|   | ||||
| @@ -80,8 +80,7 @@ function downloadNoteRevision(req, res) { | ||||
| } | ||||
|  | ||||
| function eraseAllNoteRevisions(req) { | ||||
|     const noteRevisionIdsToErase = sql.getColumn( | ||||
|         'SELECT noteRevisionId FROM note_revisions WHERE isErased = 0 AND noteId = ?', | ||||
|     const noteRevisionIdsToErase = sql.getColumn('SELECT noteRevisionId FROM note_revisions WHERE noteId = ?', | ||||
|         [req.params.noteId]); | ||||
|  | ||||
|     noteRevisionService.eraseNoteRevisions(noteRevisionIdsToErase); | ||||
| @@ -94,7 +93,7 @@ function eraseNoteRevision(req) { | ||||
| function restoreNoteRevision(req) { | ||||
|     const noteRevision = repository.getNoteRevision(req.params.noteRevisionId); | ||||
|  | ||||
|     if (noteRevision && !noteRevision.isErased) { | ||||
|     if (noteRevision) { | ||||
|         const note = noteRevision.getNote(); | ||||
|  | ||||
|         noteRevisionService.createNoteRevision(note); | ||||
|   | ||||
| @@ -15,7 +15,6 @@ function getRecentChanges(req) { | ||||
|             notes.noteId, | ||||
|             notes.isDeleted AS current_isDeleted, | ||||
|             notes.deleteId AS current_deleteId, | ||||
|             notes.isErased AS current_isErased, | ||||
|             notes.title AS current_title, | ||||
|             notes.isProtected AS current_isProtected, | ||||
|             note_revisions.title, | ||||
| @@ -23,8 +22,7 @@ function getRecentChanges(req) { | ||||
|             note_revisions.dateCreated AS date | ||||
|         FROM  | ||||
|             note_revisions | ||||
|             JOIN notes USING(noteId) | ||||
|         WHERE note_revisions.isErased = 0`); | ||||
|             JOIN notes USING(noteId)`); | ||||
|  | ||||
|     for (const noteRevision of noteRevisions) { | ||||
|         if (noteCacheService.isInAncestor(noteRevision.noteId, ancestorNoteId)) { | ||||
| @@ -40,28 +38,24 @@ function getRecentChanges(req) { | ||||
|                 notes.noteId, | ||||
|                 notes.isDeleted AS current_isDeleted, | ||||
|                 notes.deleteId AS current_deleteId, | ||||
|                 notes.isErased AS current_isErased, | ||||
|                 notes.title AS current_title, | ||||
|                 notes.isProtected AS current_isProtected, | ||||
|                 notes.title, | ||||
|                 notes.utcDateCreated AS utcDate, | ||||
|                 notes.dateCreated AS date | ||||
|             FROM | ||||
|                 notes | ||||
|             FROM notes | ||||
|         UNION ALL | ||||
|             SELECT | ||||
|                 notes.noteId, | ||||
|                 notes.isDeleted AS current_isDeleted, | ||||
|                 notes.deleteId AS current_deleteId, | ||||
|                 notes.isErased AS current_isErased, | ||||
|                 notes.title AS current_title, | ||||
|                 notes.isProtected AS current_isProtected, | ||||
|                 notes.title, | ||||
|                 notes.utcDateModified AS utcDate, | ||||
|                 notes.dateModified AS date | ||||
|             FROM | ||||
|                 notes | ||||
|             WHERE notes.isDeleted = 1 AND notes.isErased = 0`); | ||||
|             FROM notes | ||||
|             WHERE notes.isDeleted = 1`); | ||||
|  | ||||
|     for (const note of notes) { | ||||
|         if (noteCacheService.isInAncestor(note.noteId, ancestorNoteId)) { | ||||
| @@ -85,10 +79,6 @@ function getRecentChanges(req) { | ||||
|         } | ||||
|  | ||||
|         if (change.current_isDeleted) { | ||||
|             if (change.current_isErased) { | ||||
|                 change.canBeUndeleted = false; | ||||
|             } | ||||
|             else { | ||||
|             const deleteId = change.current_deleteId; | ||||
|  | ||||
|             const undeletedParentBranches = noteService.getUndeletedParentBranches(change.noteId, deleteId); | ||||
| @@ -97,7 +87,6 @@ function getRecentChanges(req) { | ||||
|             change.canBeUndeleted = undeletedParentBranches.length > 0; | ||||
|         } | ||||
|     } | ||||
|     } | ||||
|  | ||||
|     return recentChanges; | ||||
| } | ||||
|   | ||||
| @@ -12,6 +12,7 @@ const optionsService = require('./options'); | ||||
| const Branch = require('../entities/branch'); | ||||
| const dateUtils = require('./date_utils'); | ||||
| const attributeService = require('./attributes'); | ||||
| const noteRevisionService = require('./note_revisions'); | ||||
|  | ||||
| class ConsistencyChecks { | ||||
|     constructor(autoFix) { | ||||
| @@ -304,7 +305,7 @@ class ConsistencyChecks { | ||||
|                     } | ||||
|                     else { | ||||
|                         // empty string might be wrong choice for some note types but it's a best guess | ||||
|                         note.setContent(note.isErased ? null : ''); | ||||
|                         note.setContent(''); | ||||
|                     } | ||||
|  | ||||
|                     logFix(`Note ${noteId} content was set to empty string since there was no corresponding row`); | ||||
| @@ -332,53 +333,6 @@ class ConsistencyChecks { | ||||
|                 } | ||||
|             }); | ||||
|  | ||||
|         this.findAndFixIssues(` | ||||
|                     SELECT noteId | ||||
|                     FROM notes | ||||
|                       JOIN note_contents USING (noteId) | ||||
|                     WHERE isErased = 1 | ||||
|                       AND content IS NOT NULL`, | ||||
|             ({noteId}) => { | ||||
|  | ||||
|             // we always fix this issue because there does not seem to be a good way to prevent it. | ||||
|             // Scenario in which this can happen: | ||||
|             // 1. user on instance A deletes the note (sync for notes is created, but not for note_contents) and is later erased | ||||
|             // 2. instance B gets synced from instance A, note is updated because of entity change for notes, | ||||
|             //    but note_contents is not because erasion does not create entity change rows | ||||
|             // 3. therefore note.isErased = true, but note_contents.content remains not updated and not erased. | ||||
|             // | ||||
|             // Considered solutions: | ||||
|             // - don't sync erased notes - this might prevent syncing also of the isDeleted flag and note would continue | ||||
|             //   to exist on the other instance | ||||
|             // - create entity changes for erased event - this would be a problem for undeletion since erasion might happen | ||||
|             //   on one instance after undelete and thus would win even though there's no user action behind it | ||||
|             // | ||||
|             // So instead we just fix such cases afterwards here. | ||||
|  | ||||
|             sql.execute(`UPDATE note_contents SET content = NULL WHERE noteId = ?`, [noteId]); | ||||
|  | ||||
|             logFix(`Note ${noteId} content has been set to null since the note is erased`); | ||||
|         }); | ||||
|  | ||||
|         this.findAndFixIssues(` | ||||
|                     SELECT noteId, noteRevisionId | ||||
|                     FROM notes | ||||
|                       JOIN note_revisions USING (noteId) | ||||
|                     WHERE notes.isErased = 1 | ||||
|                       AND note_revisions.isErased = 0`, | ||||
|             ({noteId, noteRevisionId}) => { | ||||
|                 if (this.autoFix) { | ||||
|                     const noteRevision = repository.getNoteRevision(noteRevisionId); | ||||
|                     noteRevision.isErased = true; | ||||
|                     noteRevision.setContent(null); | ||||
|                     noteRevision.save(); | ||||
|  | ||||
|                     logFix(`Note revision ${noteRevisionId} has been erased since its note ${noteId} is also erased.`); | ||||
|                 } else { | ||||
|                     logError(`Note revision ${noteRevisionId} is not erased even though note ${noteId} is erased.`); | ||||
|                 } | ||||
|             }); | ||||
|  | ||||
|         this.findAndFixIssues(` | ||||
|                     SELECT note_revisions.noteRevisionId | ||||
|                     FROM note_revisions | ||||
| @@ -387,10 +341,7 @@ class ConsistencyChecks { | ||||
|                       AND note_revisions.isProtected = 0`, | ||||
|             ({noteRevisionId}) => { | ||||
|                 if (this.autoFix) { | ||||
|                     const noteRevision = repository.getNoteRevision(noteRevisionId); | ||||
|                     noteRevision.setContent(null); | ||||
|                     noteRevision.isErased = true; | ||||
|                     noteRevision.save(); | ||||
|                     noteRevisionService.eraseNoteRevisions([noteRevisionId]); | ||||
|  | ||||
|                     logFix(`Note revision content ${noteRevisionId} was created and set to erased since it did not exist.`); | ||||
|                 } else { | ||||
| @@ -398,59 +349,6 @@ class ConsistencyChecks { | ||||
|                 } | ||||
|             }); | ||||
|  | ||||
|         this.findAndFixIssues(` | ||||
|                     SELECT noteRevisionId | ||||
|                     FROM note_revisions | ||||
|                       JOIN note_revision_contents USING (noteRevisionId) | ||||
|                     WHERE isErased = 0 | ||||
|                       AND content IS NULL`, | ||||
|             ({noteRevisionId}) => { | ||||
|                 if (this.autoFix) { | ||||
|                     const noteRevision = repository.getNoteRevision(noteRevisionId); | ||||
|                     noteRevision.isErased = true; | ||||
|                     noteRevision.save(); | ||||
|  | ||||
|                     logFix(`Note revision ${noteRevisionId} content was set to erased since it was null even though it was not erased`); | ||||
|                 } else { | ||||
|                     logError(`Note revision ${noteRevisionId} content is null even though it is not erased`); | ||||
|                 } | ||||
|             }); | ||||
|  | ||||
|         this.findAndFixIssues(` | ||||
|                     SELECT noteRevisionId | ||||
|                     FROM note_revisions | ||||
|                              JOIN note_revision_contents USING (noteRevisionId) | ||||
|                     WHERE isErased = 1 | ||||
|                       AND content IS NOT NULL`, | ||||
|             ({noteRevisionId}) => { | ||||
|                 if (this.autoFix) { | ||||
|                     sql.execute(`UPDATE note_revision_contents SET content = NULL WHERE noteRevisionId = ?`, [noteRevisionId]); | ||||
|  | ||||
|                     logFix(`Note revision ${noteRevisionId} content was set to null since the note revision is erased`); | ||||
|                 } | ||||
|                 else { | ||||
|                     logError(`Note revision ${noteRevisionId} content is not null even though the note revision is erased`); | ||||
|                 } | ||||
|             }); | ||||
|  | ||||
|         this.findAndFixIssues(` | ||||
|                     SELECT noteId | ||||
|                     FROM notes | ||||
|                     WHERE isErased = 1 | ||||
|                       AND isDeleted = 0`, | ||||
|             ({noteId}) => { | ||||
|                 if (this.autoFix) { | ||||
|                     const note = repository.getNote(noteId); | ||||
|                     note.isDeleted = true; | ||||
|                     note.save(); | ||||
|  | ||||
|                     logFix(`Note ${noteId} was set to deleted since it is erased`); | ||||
|                 } | ||||
|                 else { | ||||
|                     logError(`Note ${noteId} is not deleted even though it is erased`); | ||||
|                 } | ||||
|             }); | ||||
|  | ||||
|         this.findAndFixIssues(` | ||||
|                     SELECT parentNoteId | ||||
|                     FROM branches | ||||
| @@ -661,36 +559,18 @@ class ConsistencyChecks { | ||||
|         return !this.unrecoveredConsistencyErrors; | ||||
|     } | ||||
|  | ||||
|     showEntityStat(name, query) { | ||||
|         const map = sql.getMap(query); | ||||
|     runDbDiagnostics() { | ||||
|         function showEntityStat(tableName) { | ||||
|             const count = sql.getValue(`SELECT COUNT(1) FROM ${tableName}`); | ||||
|  | ||||
|         map[0] = map[0] || 0; | ||||
|         map[1] = map[1] || 0; | ||||
|  | ||||
|         log.info(`${name} deleted: ${map[1]}, not deleted ${map[0]}`); | ||||
|             log.info(`${tableName}: ${count}`); | ||||
|         } | ||||
|  | ||||
|     runDbDiagnostics() { | ||||
|         this.showEntityStat("Notes", | ||||
|                 `SELECT isDeleted, count(1) | ||||
|                        FROM notes | ||||
|                        GROUP BY isDeleted`); | ||||
|         this.showEntityStat("Note revisions", | ||||
|                 `SELECT isErased, count(1) | ||||
|                        FROM note_revisions | ||||
|                        GROUP BY isErased`); | ||||
|         this.showEntityStat("Branches", | ||||
|                 `SELECT isDeleted, count(1) | ||||
|                        FROM branches | ||||
|                        GROUP BY isDeleted`); | ||||
|         this.showEntityStat("Attributes", | ||||
|                 `SELECT isDeleted, count(1) | ||||
|                        FROM attributes | ||||
|                        GROUP BY isDeleted`); | ||||
|         this.showEntityStat("API tokens", | ||||
|                 `SELECT isDeleted, count(1) | ||||
|                        FROM api_tokens | ||||
|                        GROUP BY isDeleted`); | ||||
|         showEntityStat("notes"); | ||||
|         showEntityStat("note_revisions"); | ||||
|         showEntityStat("branches"); | ||||
|         showEntityStat("attributes"); | ||||
|         showEntityStat("api_tokens"); | ||||
|     } | ||||
|  | ||||
|     async runChecks() { | ||||
|   | ||||
		Reference in New Issue
	
	Block a user