trilium/src/routes/api/note_revisions.js
2021-07-24 22:13:32 +02:00

144 lines
4.3 KiB
JavaScript

"use strict";
const beccaService = require('../../becca/becca_service');
const protectedSessionService = require('../../services/protected_session');
const noteRevisionService = require('../../services/note_revisions');
const utils = require('../../services/utils');
const sql = require('../../services/sql');
const path = require('path');
const becca = require("../../becca/becca");
function getNoteRevisions(req) {
return becca.getNoteRevisionsFromQuery(`
SELECT note_revisions.*,
LENGTH(note_revision_contents.content) AS contentLength
FROM note_revisions
JOIN note_revision_contents ON note_revisions.noteRevisionId = note_revision_contents.noteRevisionId
WHERE noteId = ?
ORDER BY utcDateCreated DESC`, [req.params.noteId]);
}
function getNoteRevision(req) {
const noteRevision = becca.getNoteRevision(req.params.noteRevisionId);
if (noteRevision.type === 'file') {
if (noteRevision.isStringNote()) {
noteRevision.content = noteRevision.getContent().substr(0, 10000);
}
}
else {
noteRevision.content = noteRevision.getContent();
if (noteRevision.content && noteRevision.type === 'image') {
noteRevision.content = noteRevision.content.toString('base64');
}
}
return noteRevision;
}
/**
* @param {NoteRevision} noteRevision
* @return {string}
*/
function getRevisionFilename(noteRevision) {
let filename = utils.formatDownloadTitle(noteRevision.title, noteRevision.type, noteRevision.mime);
const extension = path.extname(filename);
const date = noteRevision.dateCreated
.substr(0, 19)
.replace(' ', '_')
.replace(/[^0-9_]/g, '');
if (extension) {
filename = filename.substr(0, filename.length - extension.length)
+ '-' + date + extension;
}
else {
filename += '-' + date;
}
return filename;
}
function downloadNoteRevision(req, res) {
const noteRevision = becca.getNoteRevision(req.params.noteRevisionId);
if (noteRevision.noteId !== req.params.noteId) {
return res.status(400).send(`Note revision ${req.params.noteRevisionId} does not belong to note ${req.params.noteId}`);
}
if (noteRevision.isProtected && !protectedSessionService.isProtectedSessionAvailable()) {
return res.status(401).send("Protected session not available");
}
const filename = getRevisionFilename(noteRevision);
res.setHeader('Content-Disposition', utils.getContentDisposition(filename));
res.setHeader('Content-Type', noteRevision.mime);
res.send(noteRevision.getContent());
}
function eraseAllNoteRevisions(req) {
const noteRevisionIdsToErase = sql.getColumn('SELECT noteRevisionId FROM note_revisions WHERE noteId = ?',
[req.params.noteId]);
noteRevisionService.eraseNoteRevisions(noteRevisionIdsToErase);
}
function eraseNoteRevision(req) {
noteRevisionService.eraseNoteRevisions([req.params.noteRevisionId]);
}
function restoreNoteRevision(req) {
const noteRevision = becca.getNoteRevision(req.params.noteRevisionId);
if (noteRevision) {
const note = noteRevision.getNote();
noteRevisionService.createNoteRevision(note);
note.title = noteRevision.title;
note.setContent(noteRevision.getContent());
note.save();
}
}
function getEditedNotesOnDate(req) {
const noteIds = sql.getColumn(`
SELECT notes.*
FROM notes
WHERE noteId IN (
SELECT noteId FROM notes
WHERE notes.dateCreated LIKE :date
OR notes.dateModified LIKE :date
UNION ALL
SELECT noteId FROM note_revisions
WHERE note_revisions.dateLastEdited LIKE :date
)
ORDER BY isDeleted
LIMIT 50`, {date: req.params.date + '%'});
const notes = becca.getNotes(noteIds, true)
.map(note => note.getPojo());
for (const note of notes) {
const notePath = note.isDeleted ? null : beccaService.getNotePath(note.noteId);
note.notePath = notePath ? notePath.notePath : null;
}
return notes;
}
module.exports = {
getNoteRevisions,
getNoteRevision,
downloadNoteRevision,
getEditedNotesOnDate,
eraseAllNoteRevisions,
eraseNoteRevision,
restoreNoteRevision
};