Allow marking code (JavaScript) notes for execution after application loads, closes #19

This commit is contained in:
azivner 2018-01-25 23:49:03 -05:00
parent a42fd9b090
commit 9f3d46ddb1
6 changed files with 47 additions and 8 deletions

View file

@ -202,4 +202,12 @@ window.onerror = function (msg, url, lineNo, columnNo, error) {
return false;
};
$("#logout-button").toggle(!isElectron());
$("#logout-button").toggle(!isElectron());
$(document).ready(() => {
server.get("script/startup").then(scripts => {
for (const script of scripts) {
executeScript(script);
}
});
});

View file

@ -214,14 +214,14 @@ const noteEditor = (function() {
return currentNote ? currentNote.detail.type : null;
}
async function executeScript() {
async function executeCurrentNote() {
if (getCurrentNoteType() === 'code') {
// make sure note is saved so we load latest changes
await saveNoteIfChanged();
const subTreeScripts = await server.get('script/subtree/' + getCurrentNoteId());
const script = await server.get('script/subtree/' + getCurrentNoteId());
eval("(async function() {" + subTreeScripts + "})()");
executeScript(script);
}
}
@ -263,7 +263,7 @@ const noteEditor = (function() {
noteDetailEl.attr("tabindex", 2);
});
$(document).bind('keydown', "ctrl+return", executeScript);
$(document).bind('keydown', "ctrl+return", executeCurrentNote);
setInterval(saveNoteIfChanged, 5000);
@ -281,6 +281,6 @@ const noteEditor = (function() {
newNoteCreated,
getEditor,
focus,
executeScript
executeCurrentNote
};
})();

View file

@ -113,4 +113,8 @@ async function stopWatch(what, func) {
console.log(`${what} took ${tookMs}ms`);
return ret;
}
function executeScript(script) {
eval("(async function() {" + script + "})()");
}

View file

@ -8,6 +8,7 @@ const log = require('../../services/log');
const sql = require('../../services/sql');
const notes = require('../../services/notes');
const protected_session = require('../../services/protected_session');
const attributes = require('../../services/attributes');
router.post('/exec', auth.checkApiAuth, wrap(async (req, res, next) => {
log.info('Executing script: ' + req.body.script);
@ -19,6 +20,18 @@ router.post('/exec', auth.checkApiAuth, wrap(async (req, res, next) => {
res.send(ret);
}));
router.get('/startup', auth.checkApiAuth, wrap(async (req, res, next) => {
const noteIds = await attributes.getNoteIdsWithAttribute("run_on_startup");
const scripts = [];
for (const noteId of noteIds) {
scripts.push(await getNoteWithSubtreeScript(noteId, req));
}
res.send(scripts);
}));
router.get('/subtree/:noteId', auth.checkApiAuth, wrap(async (req, res, next) => {
const noteId = req.params.noteId;
@ -29,6 +42,14 @@ router.get('/subtree/:noteId', auth.checkApiAuth, wrap(async (req, res, next) =>
res.send(subTreeScripts + noteScript);
}));
async function getNoteWithSubtreeScript(noteId, req) {
const noteScript = (await notes.getNoteById(noteId, req)).note_text;
const subTreeScripts = await getSubTreeScripts(noteId, [noteId], req);
return subTreeScripts + noteScript;
}
async function getSubTreeScripts(parentId, includedNoteIds, dataKey) {
const children = await sql.getAll(`SELECT notes.note_id, notes.note_title, notes.note_text, notes.is_protected
FROM notes JOIN notes_tree USING(note_id)

View file

@ -9,10 +9,15 @@ async function getNoteAttributeMap(noteId) {
}
async function getNoteIdWithAttribute(name, value) {
return await sql.getFirstValue(`SELECT notes.note_id FROM notes JOIN attributes USING(note_id)
return await sql.getFirstValue(`SELECT DISTINCT notes.note_id FROM notes JOIN attributes USING(note_id)
WHERE notes.is_deleted = 0 AND attributes.name = ? AND attributes.value = ?`, [name, value]);
}
async function getNoteIdsWithAttribute(name) {
return await sql.getFirstColumn(`SELECT DISTINCT notes.note_id FROM notes JOIN attributes USING(note_id)
WHERE notes.is_deleted = 0 AND attributes.name = ?`, [name]);
}
async function createAttribute(noteId, name, value = null, sourceId = null) {
const now = utils.nowDate();
const attributeId = utils.newAttributeId();
@ -32,5 +37,6 @@ async function createAttribute(noteId, name, value = null, sourceId = null) {
module.exports = {
getNoteAttributeMap,
getNoteIdWithAttribute,
getNoteIdsWithAttribute,
createAttribute
};

View file

@ -98,7 +98,7 @@
<button class="btn btn-sm"
style="display: none; margin-right: 10px"
id="execute-script-button"
onclick="noteEditor.executeScript()">Execute <kbd>Ctrl+Enter</kbd></button>
onclick="noteEditor.executeCurrentNote()">Execute <kbd>Ctrl+Enter</kbd></button>
<div class="dropdown" id="note-type">
<button id="dLabel" type="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false" class="btn btn-sm">