mirror of
https://github.com/laurent22/joplin.git
synced 2024-12-24 10:27:10 +02:00
Tools: Enforce and apply eslint rules prefer-const and no-var
This commit is contained in:
parent
92bee549a1
commit
d0d2bad7f4
@ -54,16 +54,20 @@ module.exports = {
|
||||
// This error is always a false positive so far since it detects
|
||||
// possible race conditions in contexts where we know it cannot happen.
|
||||
"require-atomic-updates": 0,
|
||||
"prefer-const": ["error"],
|
||||
"no-var": ["error"],
|
||||
|
||||
// Checks rules of Hooks
|
||||
"react-hooks/rules-of-hooks": "error",
|
||||
// Checks effect dependencies
|
||||
"react-hooks/exhaustive-deps": "warn",
|
||||
// Disable because of this: https://github.com/facebook/react/issues/16265
|
||||
// "react-hooks/exhaustive-deps": "warn",
|
||||
|
||||
// -------------------------------
|
||||
// Formatting
|
||||
// -------------------------------
|
||||
"space-in-parens": ["error", "never"],
|
||||
"space-infix-ops": ["error"],
|
||||
"semi": ["error", "always"],
|
||||
"eol-last": ["error", "always"],
|
||||
"quotes": ["error", "single"],
|
||||
@ -92,7 +96,7 @@ module.exports = {
|
||||
"multiline-comment-style": ["error", "separate-lines"],
|
||||
"space-before-blocks": "error",
|
||||
"spaced-comment": ["error", "always"],
|
||||
"keyword-spacing": ["error", { "before": true, "after": true }]
|
||||
"keyword-spacing": ["error", { "before": true, "after": true }],
|
||||
},
|
||||
"plugins": [
|
||||
"react",
|
||||
|
@ -134,7 +134,7 @@ class AppGui {
|
||||
const item = folderList.currentItem;
|
||||
|
||||
if (item === '-') {
|
||||
let newIndex = event.currentIndex + (event.previousIndex < event.currentIndex ? +1 : -1);
|
||||
const newIndex = event.currentIndex + (event.previousIndex < event.currentIndex ? +1 : -1);
|
||||
let nextItem = folderList.itemAt(newIndex);
|
||||
if (!nextItem) nextItem = folderList.itemAt(event.previousIndex);
|
||||
|
||||
@ -186,7 +186,7 @@ class AppGui {
|
||||
borderRightWidth: 1,
|
||||
};
|
||||
noteList.on('currentItemChange', async () => {
|
||||
let note = noteList.currentItem;
|
||||
const note = noteList.currentItem;
|
||||
this.store_.dispatch({
|
||||
type: 'NOTE_SELECT',
|
||||
id: note ? note.id : null,
|
||||
@ -338,7 +338,7 @@ class AppGui {
|
||||
|
||||
if (consoleWidget.isMaximized__ === doMaximize) return;
|
||||
|
||||
let constraints = {
|
||||
const constraints = {
|
||||
type: 'stretch',
|
||||
factor: !doMaximize ? 1 : 4,
|
||||
};
|
||||
@ -415,10 +415,10 @@ class AppGui {
|
||||
async handleModelAction(action) {
|
||||
this.logger().info('Action:', action);
|
||||
|
||||
let state = Object.assign({}, defaultState);
|
||||
const state = Object.assign({}, defaultState);
|
||||
state.notes = this.widget('noteList').items;
|
||||
|
||||
let newState = reducer(state, action);
|
||||
const newState = reducer(state, action);
|
||||
|
||||
if (newState !== state) {
|
||||
this.widget('noteList').items = newState.notes;
|
||||
@ -485,9 +485,9 @@ class AppGui {
|
||||
// this.logger().debug('Got command: ' + cmd);
|
||||
|
||||
try {
|
||||
let note = this.widget('noteList').currentItem;
|
||||
let folder = this.widget('folderList').currentItem;
|
||||
let args = splitCommandString(cmd);
|
||||
const note = this.widget('noteList').currentItem;
|
||||
const folder = this.widget('folderList').currentItem;
|
||||
const args = splitCommandString(cmd);
|
||||
|
||||
for (let i = 0; i < args.length; i++) {
|
||||
if (args[i] == '$n') {
|
||||
@ -548,7 +548,7 @@ class AppGui {
|
||||
stdout(text) {
|
||||
if (text === null || text === undefined) return;
|
||||
|
||||
let lines = text.split('\n');
|
||||
const lines = text.split('\n');
|
||||
for (let i = 0; i < lines.length; i++) {
|
||||
const v = typeof lines[i] === 'object' ? JSON.stringify(lines[i]) : lines[i];
|
||||
this.widget('console').addLine(v);
|
||||
@ -626,7 +626,7 @@ class AppGui {
|
||||
|
||||
if (link.type === 'item') {
|
||||
const itemId = link.id;
|
||||
let item = await BaseItem.loadItemById(itemId);
|
||||
const item = await BaseItem.loadItemById(itemId);
|
||||
if (!item) throw new Error(`No item with ID ${itemId}`); // Should be nearly impossible
|
||||
|
||||
if (item.type_ === BaseModel.TYPE_RESOURCE) {
|
||||
@ -750,7 +750,7 @@ class AppGui {
|
||||
// -------------------------------------------------------------------------
|
||||
|
||||
const shortcutKey = this.currentShortcutKeys_.join('');
|
||||
let keymapItem = this.keymapItemByKey(shortcutKey);
|
||||
const keymapItem = this.keymapItemByKey(shortcutKey);
|
||||
|
||||
// If this command is an alias to another command, resolve to the actual command
|
||||
|
||||
@ -766,7 +766,7 @@ class AppGui {
|
||||
if (keymapItem.type === 'function') {
|
||||
this.processFunctionCommand(keymapItem.command);
|
||||
} else if (keymapItem.type === 'prompt') {
|
||||
let promptOptions = {};
|
||||
const promptOptions = {};
|
||||
if ('cursorPosition' in keymapItem) promptOptions.cursorPosition = keymapItem.cursorPosition;
|
||||
const commandString = await statusBar.prompt(keymapItem.command ? keymapItem.command : '', null, promptOptions);
|
||||
this.addCommandToConsole(commandString);
|
||||
|
@ -47,7 +47,7 @@ class Application extends BaseApplication {
|
||||
}
|
||||
|
||||
async loadItem(type, pattern, options = null) {
|
||||
let output = await this.loadItems(type, pattern, options);
|
||||
const output = await this.loadItems(type, pattern, options);
|
||||
|
||||
if (output.length > 1) {
|
||||
// output.sort((a, b) => { return a.user_updated_time < b.user_updated_time ? +1 : -1; });
|
||||
@ -144,7 +144,7 @@ class Application extends BaseApplication {
|
||||
if (options.type === 'boolean') {
|
||||
if (answer === null) return false; // Pressed ESCAPE
|
||||
if (!answer) answer = options.answers[0];
|
||||
let positiveIndex = options.booleanAnswerDefault == 'y' ? 0 : 1;
|
||||
const positiveIndex = options.booleanAnswerDefault == 'y' ? 0 : 1;
|
||||
return answer.toLowerCase() === options.answers[positiveIndex].toLowerCase();
|
||||
} else {
|
||||
return answer;
|
||||
@ -181,7 +181,7 @@ class Application extends BaseApplication {
|
||||
const ext = fileExtension(path);
|
||||
if (ext != 'js') return;
|
||||
|
||||
let CommandClass = require(`./${path}`);
|
||||
const CommandClass = require(`./${path}`);
|
||||
let cmd = new CommandClass();
|
||||
if (!cmd.enabled()) return;
|
||||
cmd = this.setupCommand(cmd);
|
||||
@ -192,8 +192,8 @@ class Application extends BaseApplication {
|
||||
}
|
||||
|
||||
if (uiType !== null) {
|
||||
let temp = [];
|
||||
for (let n in this.commands_) {
|
||||
const temp = [];
|
||||
for (const n in this.commands_) {
|
||||
if (!this.commands_.hasOwnProperty(n)) continue;
|
||||
const c = this.commands_[n];
|
||||
if (!c.supportsUi(uiType)) continue;
|
||||
@ -207,8 +207,8 @@ class Application extends BaseApplication {
|
||||
|
||||
async commandNames() {
|
||||
const metadata = await this.commandMetadata();
|
||||
let output = [];
|
||||
for (let n in metadata) {
|
||||
const output = [];
|
||||
for (const n in metadata) {
|
||||
if (!metadata.hasOwnProperty(n)) continue;
|
||||
output.push(n);
|
||||
}
|
||||
@ -227,7 +227,7 @@ class Application extends BaseApplication {
|
||||
const commands = this.commands();
|
||||
|
||||
output = {};
|
||||
for (let n in commands) {
|
||||
for (const n in commands) {
|
||||
if (!commands.hasOwnProperty(n)) continue;
|
||||
const cmd = commands[n];
|
||||
output[n] = cmd.metadata();
|
||||
@ -251,7 +251,7 @@ class Application extends BaseApplication {
|
||||
CommandClass = require(`${__dirname}/command-${name}.js`);
|
||||
} catch (error) {
|
||||
if (error.message && error.message.indexOf('Cannot find module') >= 0) {
|
||||
let e = new Error(_('No such command: %s', name));
|
||||
const e = new Error(_('No such command: %s', name));
|
||||
e.type = 'notFound';
|
||||
throw e;
|
||||
} else {
|
||||
@ -362,7 +362,7 @@ class Application extends BaseApplication {
|
||||
}
|
||||
|
||||
const output = [];
|
||||
for (let n in itemsByCommand) {
|
||||
for (const n in itemsByCommand) {
|
||||
if (!itemsByCommand.hasOwnProperty(n)) continue;
|
||||
output.push(itemsByCommand[n]);
|
||||
}
|
||||
|
@ -1,20 +1,20 @@
|
||||
var { app } = require('./app.js');
|
||||
var Note = require('lib/models/Note.js');
|
||||
var Folder = require('lib/models/Folder.js');
|
||||
var Tag = require('lib/models/Tag.js');
|
||||
var { cliUtils } = require('./cli-utils.js');
|
||||
var yargParser = require('yargs-parser');
|
||||
var fs = require('fs-extra');
|
||||
const { app } = require('./app.js');
|
||||
const Note = require('lib/models/Note.js');
|
||||
const Folder = require('lib/models/Folder.js');
|
||||
const Tag = require('lib/models/Tag.js');
|
||||
const { cliUtils } = require('./cli-utils.js');
|
||||
const yargParser = require('yargs-parser');
|
||||
const fs = require('fs-extra');
|
||||
|
||||
async function handleAutocompletionPromise(line) {
|
||||
// Auto-complete the command name
|
||||
const names = await app().commandNames();
|
||||
let words = getArguments(line);
|
||||
const words = getArguments(line);
|
||||
// If there is only one word and it is not already a command name then you
|
||||
// should look for commands it could be
|
||||
if (words.length == 1) {
|
||||
if (names.indexOf(words[0]) === -1) {
|
||||
let x = names.filter(n => n.indexOf(words[0]) === 0);
|
||||
const x = names.filter(n => n.indexOf(words[0]) === 0);
|
||||
if (x.length === 1) {
|
||||
return `${x[0]} `;
|
||||
}
|
||||
@ -36,8 +36,8 @@ async function handleAutocompletionPromise(line) {
|
||||
}
|
||||
|
||||
// complete an option
|
||||
let next = words.length > 1 ? words[words.length - 1] : '';
|
||||
let l = [];
|
||||
const next = words.length > 1 ? words[words.length - 1] : '';
|
||||
const l = [];
|
||||
if (next[0] === '-') {
|
||||
for (let i = 0; i < metadata.options.length; i++) {
|
||||
const options = metadata.options[i][0].split(' ');
|
||||
@ -60,7 +60,7 @@ async function handleAutocompletionPromise(line) {
|
||||
if (l.length === 0) {
|
||||
return line;
|
||||
}
|
||||
let ret = l.map(a => toCommandLine(a));
|
||||
const ret = l.map(a => toCommandLine(a));
|
||||
ret.prefix = `${toCommandLine(words.slice(0, -1))} `;
|
||||
return ret;
|
||||
}
|
||||
@ -69,7 +69,7 @@ async function handleAutocompletionPromise(line) {
|
||||
// words that don't start with a - less one for the command name
|
||||
const positionalArgs = words.filter(a => a.indexOf('-') !== 0).length - 1;
|
||||
|
||||
let cmdUsage = yargParser(metadata.usage)['_'];
|
||||
const cmdUsage = yargParser(metadata.usage)['_'];
|
||||
cmdUsage.splice(0, 1);
|
||||
|
||||
if (cmdUsage.length >= positionalArgs) {
|
||||
@ -95,29 +95,29 @@ async function handleAutocompletionPromise(line) {
|
||||
}
|
||||
|
||||
if (argName == 'tag') {
|
||||
let tags = await Tag.search({ titlePattern: `${next}*` });
|
||||
const tags = await Tag.search({ titlePattern: `${next}*` });
|
||||
l.push(...tags.map(n => n.title));
|
||||
}
|
||||
|
||||
if (argName == 'file') {
|
||||
let files = await fs.readdir('.');
|
||||
const files = await fs.readdir('.');
|
||||
l.push(...files);
|
||||
}
|
||||
|
||||
if (argName == 'tag-command') {
|
||||
let c = filterList(['add', 'remove', 'list', 'notetags'], next);
|
||||
const c = filterList(['add', 'remove', 'list', 'notetags'], next);
|
||||
l.push(...c);
|
||||
}
|
||||
|
||||
if (argName == 'todo-command') {
|
||||
let c = filterList(['toggle', 'clear'], next);
|
||||
const c = filterList(['toggle', 'clear'], next);
|
||||
l.push(...c);
|
||||
}
|
||||
}
|
||||
if (l.length === 1) {
|
||||
return toCommandLine([...words.slice(0, -1), l[0]]);
|
||||
} else if (l.length > 1) {
|
||||
let ret = l.map(a => toCommandLine(a));
|
||||
const ret = l.map(a => toCommandLine(a));
|
||||
ret.prefix = `${toCommandLine(words.slice(0, -1))} `;
|
||||
return ret;
|
||||
}
|
||||
@ -155,7 +155,7 @@ function getArguments(line) {
|
||||
let inSingleQuotes = false;
|
||||
let inDoubleQuotes = false;
|
||||
let currentWord = '';
|
||||
let parsed = [];
|
||||
const parsed = [];
|
||||
for (let i = 0; i < line.length; i++) {
|
||||
if (line[i] === '"') {
|
||||
if (inDoubleQuotes) {
|
||||
@ -192,7 +192,7 @@ function getArguments(line) {
|
||||
return parsed;
|
||||
}
|
||||
function filterList(list, next) {
|
||||
let output = [];
|
||||
const output = [];
|
||||
for (let i = 0; i < list.length; i++) {
|
||||
if (list[i].indexOf(next) !== 0) continue;
|
||||
output.push(list[i]);
|
||||
|
@ -50,7 +50,7 @@ class BaseCommand {
|
||||
async cancel() {}
|
||||
|
||||
name() {
|
||||
let r = this.usage().split(' ');
|
||||
const r = this.usage().split(' ');
|
||||
return r[0];
|
||||
}
|
||||
|
||||
|
@ -15,11 +15,11 @@ function wrap(text, indent) {
|
||||
}
|
||||
|
||||
function renderOptions(options) {
|
||||
let output = [];
|
||||
const output = [];
|
||||
const optionColWidth = getOptionColWidth(options);
|
||||
|
||||
for (let i = 0; i < options.length; i++) {
|
||||
let option = options[i];
|
||||
const option = options[i];
|
||||
const flag = option[0];
|
||||
const indent = INDENT + INDENT + ' '.repeat(optionColWidth + 2);
|
||||
|
||||
@ -33,7 +33,7 @@ function renderOptions(options) {
|
||||
}
|
||||
|
||||
function renderCommand(cmd) {
|
||||
let output = [];
|
||||
const output = [];
|
||||
output.push(INDENT + cmd.usage());
|
||||
output.push('');
|
||||
output.push(wrap(cmd.description(), INDENT + INDENT));
|
||||
@ -48,14 +48,14 @@ function renderCommand(cmd) {
|
||||
}
|
||||
|
||||
function getCommands() {
|
||||
let output = [];
|
||||
const output = [];
|
||||
fs.readdirSync(__dirname).forEach(path => {
|
||||
if (path.indexOf('command-') !== 0) return;
|
||||
const ext = fileExtension(path);
|
||||
if (ext != 'js') return;
|
||||
|
||||
let CommandClass = require(`./${path}`);
|
||||
let cmd = new CommandClass();
|
||||
const CommandClass = require(`./${path}`);
|
||||
const cmd = new CommandClass();
|
||||
if (!cmd.enabled()) return;
|
||||
if (cmd.hidden()) return;
|
||||
output.push(cmd);
|
||||
@ -73,7 +73,7 @@ function getOptionColWidth(options) {
|
||||
}
|
||||
|
||||
function getHeader() {
|
||||
let output = [];
|
||||
const output = [];
|
||||
|
||||
output.push('NAME');
|
||||
output.push('');
|
||||
@ -84,7 +84,7 @@ function getHeader() {
|
||||
output.push('DESCRIPTION');
|
||||
output.push('');
|
||||
|
||||
let description = [];
|
||||
const description = [];
|
||||
description.push('Joplin is a note taking and to-do application, which can handle a large number of notes organised into notebooks.');
|
||||
description.push('The notes are searchable, can be copied, tagged and modified with your own text editor.');
|
||||
description.push('\n\n');
|
||||
@ -98,7 +98,7 @@ function getHeader() {
|
||||
}
|
||||
|
||||
function getFooter() {
|
||||
let output = [];
|
||||
const output = [];
|
||||
|
||||
output.push('WEBSITE');
|
||||
output.push('');
|
||||
@ -120,10 +120,10 @@ async function main() {
|
||||
// setLocale('fr_FR');
|
||||
|
||||
const commands = getCommands();
|
||||
let commandBlocks = [];
|
||||
const commandBlocks = [];
|
||||
|
||||
for (let i = 0; i < commands.length; i++) {
|
||||
let cmd = commands[i];
|
||||
const cmd = commands[i];
|
||||
commandBlocks.push(renderCommand(cmd));
|
||||
}
|
||||
|
||||
|
@ -40,8 +40,8 @@ function createClient(id) {
|
||||
const client = createClient(1);
|
||||
|
||||
function execCommand(client, command) {
|
||||
let exePath = `node ${joplinAppPath}`;
|
||||
let cmd = `${exePath} --update-geolocation-disabled --env dev --profile ${client.profileDir} ${command}`;
|
||||
const exePath = `node ${joplinAppPath}`;
|
||||
const cmd = `${exePath} --update-geolocation-disabled --env dev --profile ${client.profileDir} ${command}`;
|
||||
logger.info(`${client.id}: ${command}`);
|
||||
|
||||
return new Promise((resolve, reject) => {
|
||||
@ -129,8 +129,8 @@ testUnits.testCat = async () => {
|
||||
await execCommand(client, 'mkbook nb1');
|
||||
await execCommand(client, 'mknote mynote');
|
||||
|
||||
let folder = await Folder.loadByTitle('nb1');
|
||||
let note = await Note.loadFolderNoteByField(folder.id, 'title', 'mynote');
|
||||
const folder = await Folder.loadByTitle('nb1');
|
||||
const note = await Note.loadFolderNoteByField(folder.id, 'title', 'mynote');
|
||||
|
||||
let r = await execCommand(client, 'cat mynote');
|
||||
assertTrue(r.indexOf('mynote') >= 0);
|
||||
@ -149,7 +149,7 @@ testUnits.testConfig = async () => {
|
||||
await Setting.load();
|
||||
assertEquals('subl', Setting.value('editor'));
|
||||
|
||||
let r = await execCommand(client, 'config');
|
||||
const r = await execCommand(client, 'config');
|
||||
assertTrue(r.indexOf('editor') >= 0);
|
||||
assertTrue(r.indexOf('subl') >= 0);
|
||||
};
|
||||
@ -161,14 +161,14 @@ testUnits.testCp = async () => {
|
||||
|
||||
await execCommand(client, 'cp n1');
|
||||
|
||||
let f1 = await Folder.loadByTitle('nb1');
|
||||
let f2 = await Folder.loadByTitle('nb2');
|
||||
const f1 = await Folder.loadByTitle('nb1');
|
||||
const f2 = await Folder.loadByTitle('nb2');
|
||||
let notes = await Note.previews(f1.id);
|
||||
|
||||
assertEquals(2, notes.length);
|
||||
|
||||
await execCommand(client, 'cp n1 nb2');
|
||||
let notesF1 = await Note.previews(f1.id);
|
||||
const notesF1 = await Note.previews(f1.id);
|
||||
assertEquals(2, notesF1.length);
|
||||
notes = await Note.previews(f2.id);
|
||||
assertEquals(1, notes.length);
|
||||
@ -179,7 +179,7 @@ testUnits.testLs = async () => {
|
||||
await execCommand(client, 'mkbook nb1');
|
||||
await execCommand(client, 'mknote note1');
|
||||
await execCommand(client, 'mknote note2');
|
||||
let r = await execCommand(client, 'ls');
|
||||
const r = await execCommand(client, 'ls');
|
||||
|
||||
assertTrue(r.indexOf('note1') >= 0);
|
||||
assertTrue(r.indexOf('note2') >= 0);
|
||||
@ -191,8 +191,8 @@ testUnits.testMv = async () => {
|
||||
await execCommand(client, 'mknote n1');
|
||||
await execCommand(client, 'mv n1 nb2');
|
||||
|
||||
let f1 = await Folder.loadByTitle('nb1');
|
||||
let f2 = await Folder.loadByTitle('nb2');
|
||||
const f1 = await Folder.loadByTitle('nb1');
|
||||
const f2 = await Folder.loadByTitle('nb2');
|
||||
let notes1 = await Note.previews(f1.id);
|
||||
let notes2 = await Note.previews(f2.id);
|
||||
|
||||
@ -224,12 +224,12 @@ async function main() {
|
||||
let onlyThisTest = 'testMv';
|
||||
onlyThisTest = '';
|
||||
|
||||
for (let n in testUnits) {
|
||||
for (const n in testUnits) {
|
||||
if (!testUnits.hasOwnProperty(n)) continue;
|
||||
if (onlyThisTest && n != onlyThisTest) continue;
|
||||
|
||||
await clearDatabase();
|
||||
let testName = n.substr(4).toLowerCase();
|
||||
const testName = n.substr(4).toLowerCase();
|
||||
process.stdout.write(`${testName}: `);
|
||||
await testUnits[n]();
|
||||
console.info('');
|
||||
|
@ -11,27 +11,27 @@ cliUtils.printArray = function(logFunction, rows) {
|
||||
const ALIGN_LEFT = 0;
|
||||
const ALIGN_RIGHT = 1;
|
||||
|
||||
let colWidths = [];
|
||||
let colAligns = [];
|
||||
const colWidths = [];
|
||||
const colAligns = [];
|
||||
|
||||
for (let i = 0; i < rows.length; i++) {
|
||||
let row = rows[i];
|
||||
const row = rows[i];
|
||||
|
||||
for (let j = 0; j < row.length; j++) {
|
||||
let item = row[j];
|
||||
let width = item ? item.toString().length : 0;
|
||||
let align = typeof item == 'number' ? ALIGN_RIGHT : ALIGN_LEFT;
|
||||
const item = row[j];
|
||||
const width = item ? item.toString().length : 0;
|
||||
const align = typeof item == 'number' ? ALIGN_RIGHT : ALIGN_LEFT;
|
||||
if (!colWidths[j] || colWidths[j] < width) colWidths[j] = width;
|
||||
if (colAligns.length <= j) colAligns[j] = align;
|
||||
}
|
||||
}
|
||||
|
||||
for (let row = 0; row < rows.length; row++) {
|
||||
let line = [];
|
||||
const line = [];
|
||||
for (let col = 0; col < colWidths.length; col++) {
|
||||
let item = rows[row][col];
|
||||
let width = colWidths[col];
|
||||
let dir = colAligns[col] == ALIGN_LEFT ? stringPadding.RIGHT : stringPadding.LEFT;
|
||||
const item = rows[row][col];
|
||||
const width = colWidths[col];
|
||||
const dir = colAligns[col] == ALIGN_LEFT ? stringPadding.RIGHT : stringPadding.LEFT;
|
||||
line.push(stringPadding(item, width, ' ', dir));
|
||||
}
|
||||
logFunction(line.join(' '));
|
||||
@ -39,7 +39,7 @@ cliUtils.printArray = function(logFunction, rows) {
|
||||
};
|
||||
|
||||
cliUtils.parseFlags = function(flags) {
|
||||
let output = {};
|
||||
const output = {};
|
||||
flags = flags.split(',');
|
||||
for (let i = 0; i < flags.length; i++) {
|
||||
let f = flags[i].trim();
|
||||
@ -76,11 +76,11 @@ cliUtils.parseCommandArg = function(arg) {
|
||||
cliUtils.makeCommandArgs = function(cmd, argv) {
|
||||
let cmdUsage = cmd.usage();
|
||||
cmdUsage = yargParser(cmdUsage);
|
||||
let output = {};
|
||||
const output = {};
|
||||
|
||||
let options = cmd.options();
|
||||
let booleanFlags = [];
|
||||
let aliases = {};
|
||||
const options = cmd.options();
|
||||
const booleanFlags = [];
|
||||
const aliases = {};
|
||||
for (let i = 0; i < options.length; i++) {
|
||||
if (options[i].length != 2) throw new Error(`Invalid options: ${options[i]}`);
|
||||
let flags = options[i][0];
|
||||
@ -97,7 +97,7 @@ cliUtils.makeCommandArgs = function(cmd, argv) {
|
||||
}
|
||||
}
|
||||
|
||||
let args = yargParser(argv, {
|
||||
const args = yargParser(argv, {
|
||||
boolean: booleanFlags,
|
||||
alias: aliases,
|
||||
string: ['_'],
|
||||
@ -113,8 +113,8 @@ cliUtils.makeCommandArgs = function(cmd, argv) {
|
||||
}
|
||||
}
|
||||
|
||||
let argOptions = {};
|
||||
for (let key in args) {
|
||||
const argOptions = {};
|
||||
for (const key in args) {
|
||||
if (!args.hasOwnProperty(key)) continue;
|
||||
if (key == '_') continue;
|
||||
argOptions[key] = args[key];
|
||||
@ -134,7 +134,7 @@ cliUtils.promptMcq = function(message, answers) {
|
||||
});
|
||||
|
||||
message += '\n\n';
|
||||
for (let n in answers) {
|
||||
for (const n in answers) {
|
||||
if (!answers.hasOwnProperty(n)) continue;
|
||||
message += `${_('%s: %s', n, answers[n])}\n`;
|
||||
}
|
||||
|
@ -14,9 +14,9 @@ class Command extends BaseCommand {
|
||||
}
|
||||
|
||||
async action(args) {
|
||||
let title = args['note'];
|
||||
const title = args['note'];
|
||||
|
||||
let note = await app().loadItem(BaseModel.TYPE_NOTE, title, { parent: app().currentFolder() });
|
||||
const note = await app().loadItem(BaseModel.TYPE_NOTE, title, { parent: app().currentFolder() });
|
||||
this.encryptionCheck(note);
|
||||
if (!note) throw new Error(_('Cannot find "%s".', title));
|
||||
|
||||
|
@ -18,9 +18,9 @@ class Command extends BaseCommand {
|
||||
}
|
||||
|
||||
async action(args) {
|
||||
let title = args['note'];
|
||||
const title = args['note'];
|
||||
|
||||
let item = await app().loadItem(BaseModel.TYPE_NOTE, title, { parent: app().currentFolder() });
|
||||
const item = await app().loadItem(BaseModel.TYPE_NOTE, title, { parent: app().currentFolder() });
|
||||
if (!item) throw new Error(_('Cannot find "%s".', title));
|
||||
|
||||
const content = args.options.verbose ? await Note.serialize(item) : await Note.serializeForEdit(item);
|
||||
|
@ -35,7 +35,7 @@ class Command extends BaseCommand {
|
||||
});
|
||||
|
||||
inputStream.on('end', () => {
|
||||
let json = chunks.join('');
|
||||
const json = chunks.join('');
|
||||
let settingsObj;
|
||||
try {
|
||||
settingsObj = JSON.parse(json);
|
||||
@ -83,7 +83,7 @@ class Command extends BaseCommand {
|
||||
};
|
||||
|
||||
if (isExport || (!isImport && !args.value)) {
|
||||
let keys = Setting.keys(!verbose, 'cli');
|
||||
const keys = Setting.keys(!verbose, 'cli');
|
||||
keys.sort();
|
||||
|
||||
if (isExport) {
|
||||
|
@ -18,15 +18,15 @@ class Command extends BaseCommand {
|
||||
|
||||
async action() {
|
||||
let items = [];
|
||||
let folders = await Folder.all();
|
||||
const folders = await Folder.all();
|
||||
for (let i = 0; i < folders.length; i++) {
|
||||
let folder = folders[i];
|
||||
let notes = await Note.previews(folder.id);
|
||||
const folder = folders[i];
|
||||
const notes = await Note.previews(folder.id);
|
||||
items.push(folder);
|
||||
items = items.concat(notes);
|
||||
}
|
||||
|
||||
let tags = await Tag.all();
|
||||
const tags = await Tag.all();
|
||||
for (let i = 0; i < tags.length; i++) {
|
||||
tags[i].notes_ = await Tag.noteIds(tags[i].id);
|
||||
}
|
||||
|
@ -138,7 +138,7 @@ class Command extends BaseCommand {
|
||||
if (!targetPath) throw new Error('Please specify the sync target path.');
|
||||
|
||||
const dirPaths = function(targetPath) {
|
||||
let paths = [];
|
||||
const paths = [];
|
||||
fs.readdirSync(targetPath).forEach(path => {
|
||||
paths.push(path);
|
||||
});
|
||||
@ -151,10 +151,10 @@ class Command extends BaseCommand {
|
||||
let encryptedResourceCount = 0;
|
||||
let otherItemCount = 0;
|
||||
|
||||
let encryptedPaths = [];
|
||||
let decryptedPaths = [];
|
||||
const encryptedPaths = [];
|
||||
const decryptedPaths = [];
|
||||
|
||||
let paths = dirPaths(targetPath);
|
||||
const paths = dirPaths(targetPath);
|
||||
|
||||
for (let i = 0; i < paths.length; i++) {
|
||||
const path = paths[i];
|
||||
@ -164,7 +164,7 @@ class Command extends BaseCommand {
|
||||
// this.stdout(fullPath);
|
||||
|
||||
if (path === '.resource') {
|
||||
let resourcePaths = dirPaths(fullPath);
|
||||
const resourcePaths = dirPaths(fullPath);
|
||||
for (let j = 0; j < resourcePaths.length; j++) {
|
||||
const resourcePath = resourcePaths[j];
|
||||
resourceCount++;
|
||||
|
@ -35,7 +35,7 @@ class Command extends BaseCommand {
|
||||
// Load note or create it if it doesn't exist
|
||||
// -------------------------------------------------------------------------
|
||||
|
||||
let title = args['note'];
|
||||
const title = args['note'];
|
||||
|
||||
if (!app().currentFolder()) throw new Error(_('No active notebook.'));
|
||||
let note = await app().loadItem(BaseModel.TYPE_NOTE, title);
|
||||
@ -91,7 +91,7 @@ class Command extends BaseCommand {
|
||||
|
||||
const updatedContent = await fs.readFile(tempFilePath, 'utf8');
|
||||
if (updatedContent !== originalContent) {
|
||||
let updatedNote = await Note.unserializeForEdit(updatedContent);
|
||||
const updatedNote = await Note.unserializeForEdit(updatedContent);
|
||||
updatedNote.id = note.id;
|
||||
await Note.save(updatedNote);
|
||||
this.stdout(_('Note has been saved.'));
|
||||
|
@ -24,7 +24,7 @@ class Command extends BaseCommand {
|
||||
}
|
||||
|
||||
async action(args) {
|
||||
let exportOptions = {};
|
||||
const exportOptions = {};
|
||||
exportOptions.path = args.path;
|
||||
|
||||
exportOptions.format = args.options.format ? args.options.format : 'jex';
|
||||
|
@ -14,9 +14,9 @@ class Command extends BaseCommand {
|
||||
}
|
||||
|
||||
async action(args) {
|
||||
let title = args['note'];
|
||||
const title = args['note'];
|
||||
|
||||
let item = await app().loadItem(BaseModel.TYPE_NOTE, title, { parent: app().currentFolder() });
|
||||
const item = await app().loadItem(BaseModel.TYPE_NOTE, title, { parent: app().currentFolder() });
|
||||
if (!item) throw new Error(_('Cannot find "%s".', title));
|
||||
const url = Note.geolocationUrl(item);
|
||||
this.stdout(url);
|
||||
|
@ -15,8 +15,8 @@ class Command extends BaseCommand {
|
||||
|
||||
allCommands() {
|
||||
const commands = app().commands(app().uiType());
|
||||
let output = [];
|
||||
for (let n in commands) {
|
||||
const output = [];
|
||||
for (const n in commands) {
|
||||
if (!commands.hasOwnProperty(n)) continue;
|
||||
const command = commands[n];
|
||||
if (command.hidden()) continue;
|
||||
@ -48,7 +48,7 @@ class Command extends BaseCommand {
|
||||
.gui()
|
||||
.keymap();
|
||||
|
||||
let rows = [];
|
||||
const rows = [];
|
||||
|
||||
for (let i = 0; i < keymap.length; i++) {
|
||||
const item = keymap[i];
|
||||
|
@ -25,7 +25,7 @@ class Command extends BaseCommand {
|
||||
}
|
||||
|
||||
async action(args) {
|
||||
let folder = await app().loadItem(BaseModel.TYPE_FOLDER, args.notebook);
|
||||
const folder = await app().loadItem(BaseModel.TYPE_FOLDER, args.notebook);
|
||||
|
||||
if (args.notebook && !folder) throw new Error(_('Cannot find "%s".', args.notebook));
|
||||
|
||||
@ -39,7 +39,7 @@ class Command extends BaseCommand {
|
||||
// onProgress/onError supported by Enex import only
|
||||
|
||||
importOptions.onProgress = progressState => {
|
||||
let line = [];
|
||||
const line = [];
|
||||
line.push(_('Found: %d.', progressState.loaded));
|
||||
line.push(_('Created: %d.', progressState.created));
|
||||
if (progressState.updated) line.push(_('Updated: %d.', progressState.updated));
|
||||
@ -51,7 +51,7 @@ class Command extends BaseCommand {
|
||||
};
|
||||
|
||||
importOptions.onError = error => {
|
||||
let s = error.trace ? error.trace : error.toString();
|
||||
const s = error.trace ? error.trace : error.toString();
|
||||
this.stdout(s);
|
||||
};
|
||||
|
||||
|
@ -34,11 +34,11 @@ class Command extends BaseCommand {
|
||||
}
|
||||
|
||||
async action(args) {
|
||||
let pattern = args['note-pattern'];
|
||||
const pattern = args['note-pattern'];
|
||||
let items = [];
|
||||
let options = args.options;
|
||||
const options = args.options;
|
||||
|
||||
let queryOptions = {};
|
||||
const queryOptions = {};
|
||||
if (options.limit) queryOptions.limit = options.limit;
|
||||
if (options.sort) {
|
||||
queryOptions.orderBy = options.sort;
|
||||
@ -70,19 +70,19 @@ class Command extends BaseCommand {
|
||||
} else {
|
||||
let hasTodos = false;
|
||||
for (let i = 0; i < items.length; i++) {
|
||||
let item = items[i];
|
||||
const item = items[i];
|
||||
if (item.is_todo) {
|
||||
hasTodos = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
let seenTitles = [];
|
||||
let rows = [];
|
||||
const seenTitles = [];
|
||||
const rows = [];
|
||||
let shortIdShown = false;
|
||||
for (let i = 0; i < items.length; i++) {
|
||||
let item = items[i];
|
||||
let row = [];
|
||||
const item = items[i];
|
||||
const row = [];
|
||||
|
||||
if (options.long) {
|
||||
row.push(BaseModel.shortId(item.id));
|
||||
|
@ -13,7 +13,7 @@ class Command extends BaseCommand {
|
||||
}
|
||||
|
||||
async action(args) {
|
||||
let folder = await Folder.save({ title: args['new-notebook'] }, { userSideValidation: true });
|
||||
const folder = await Folder.save({ title: args['new-notebook'] }, { userSideValidation: true });
|
||||
app().switchCurrentFolder(folder);
|
||||
}
|
||||
}
|
||||
|
@ -26,7 +26,7 @@ class Command extends BaseCommand {
|
||||
|
||||
const ok = force ? true : await this.prompt(notes.length > 1 ? _('%d notes match this pattern. Delete them?', notes.length) : _('Delete note?'), { booleanAnswerDefault: 'n' });
|
||||
if (!ok) return;
|
||||
let ids = notes.map(n => n.id);
|
||||
const ids = notes.map(n => n.id);
|
||||
await Note.batchDelete(ids);
|
||||
}
|
||||
}
|
||||
|
@ -18,8 +18,8 @@ class Command extends BaseCommand {
|
||||
}
|
||||
|
||||
async action(args) {
|
||||
let pattern = args['pattern'];
|
||||
let folderTitle = args['notebook'];
|
||||
const pattern = args['pattern'];
|
||||
const folderTitle = args['notebook'];
|
||||
|
||||
let folder = null;
|
||||
if (folderTitle) {
|
||||
|
@ -23,18 +23,18 @@ class Command extends BaseCommand {
|
||||
}
|
||||
|
||||
async action(args) {
|
||||
let title = args['note'];
|
||||
let propName = args['name'];
|
||||
const title = args['note'];
|
||||
const propName = args['name'];
|
||||
let propValue = args['value'];
|
||||
if (!propValue) propValue = '';
|
||||
|
||||
let notes = await app().loadItems(BaseModel.TYPE_NOTE, title);
|
||||
const notes = await app().loadItems(BaseModel.TYPE_NOTE, title);
|
||||
if (!notes.length) throw new Error(_('Cannot find "%s".', title));
|
||||
|
||||
for (let i = 0; i < notes.length; i++) {
|
||||
this.encryptionCheck(notes[i]);
|
||||
|
||||
let newNote = {
|
||||
const newNote = {
|
||||
id: notes[i].id,
|
||||
type_: notes[i].type_,
|
||||
};
|
||||
|
@ -14,20 +14,20 @@ class Command extends BaseCommand {
|
||||
}
|
||||
|
||||
async action() {
|
||||
let service = new ReportService();
|
||||
let report = await service.status(Setting.value('sync.target'));
|
||||
const service = new ReportService();
|
||||
const report = await service.status(Setting.value('sync.target'));
|
||||
|
||||
for (let i = 0; i < report.length; i++) {
|
||||
let section = report[i];
|
||||
const section = report[i];
|
||||
|
||||
if (i > 0) this.stdout('');
|
||||
|
||||
this.stdout(`# ${section.title}`);
|
||||
this.stdout('');
|
||||
|
||||
for (let n in section.body) {
|
||||
for (const n in section.body) {
|
||||
if (!section.body.hasOwnProperty(n)) continue;
|
||||
let line = section.body[n];
|
||||
const line = section.body[n];
|
||||
this.stdout(line);
|
||||
}
|
||||
}
|
||||
|
@ -161,9 +161,9 @@ class Command extends BaseCommand {
|
||||
|
||||
const sync = await syncTarget.synchronizer();
|
||||
|
||||
let options = {
|
||||
const options = {
|
||||
onProgress: report => {
|
||||
let lines = Synchronizer.reportToLines(report);
|
||||
const lines = Synchronizer.reportToLines(report);
|
||||
if (lines.length) cliUtils.redraw(lines.join(' '));
|
||||
},
|
||||
onMessage: msg => {
|
||||
@ -185,7 +185,7 @@ class Command extends BaseCommand {
|
||||
options.context = context;
|
||||
|
||||
try {
|
||||
let newContext = await sync.start(options);
|
||||
const newContext = await sync.start(options);
|
||||
Setting.setValue(contextKey, JSON.stringify(newContext));
|
||||
} catch (error) {
|
||||
if (error.code == 'alreadyStarted') {
|
||||
|
@ -20,7 +20,7 @@ class Command extends BaseCommand {
|
||||
|
||||
async action(args) {
|
||||
let tag = null;
|
||||
let options = args.options;
|
||||
const options = args.options;
|
||||
|
||||
if (args.tag) tag = await app().loadItem(BaseModel.TYPE_TAG, args.tag);
|
||||
let notes = [];
|
||||
@ -46,7 +46,7 @@ class Command extends BaseCommand {
|
||||
}
|
||||
} else if (command == 'list') {
|
||||
if (tag) {
|
||||
let notes = await Tag.notes(tag.id);
|
||||
const notes = await Tag.notes(tag.id);
|
||||
notes.map(note => {
|
||||
let line = '';
|
||||
if (options.long) {
|
||||
@ -70,7 +70,7 @@ class Command extends BaseCommand {
|
||||
this.stdout(line);
|
||||
});
|
||||
} else {
|
||||
let tags = await Tag.all();
|
||||
const tags = await Tag.all();
|
||||
tags.map(tag => {
|
||||
this.stdout(tag.title);
|
||||
});
|
||||
|
@ -17,7 +17,7 @@ class Command extends BaseCommand {
|
||||
}
|
||||
|
||||
async action(args) {
|
||||
let folder = await app().loadItem(BaseModel.TYPE_FOLDER, args['notebook']);
|
||||
const folder = await app().loadItem(BaseModel.TYPE_FOLDER, args['notebook']);
|
||||
if (!folder) throw new Error(_('Cannot find "%s".', args['notebook']));
|
||||
app().switchCurrentFolder(folder);
|
||||
}
|
||||
|
@ -12,7 +12,7 @@ const fs = require('fs-extra');
|
||||
const baseDir = `${dirname(__dirname)}/tests/fuzzing`;
|
||||
const syncDir = `${baseDir}/sync`;
|
||||
const joplinAppPath = `${__dirname}/main.js`;
|
||||
let syncDurations = [];
|
||||
const syncDurations = [];
|
||||
|
||||
const fsDriver = new FsDriverNode();
|
||||
Logger.fsDriver_ = fsDriver;
|
||||
@ -34,10 +34,10 @@ function createClient(id) {
|
||||
}
|
||||
|
||||
async function createClients() {
|
||||
let output = [];
|
||||
let promises = [];
|
||||
const output = [];
|
||||
const promises = [];
|
||||
for (let clientId = 0; clientId < 2; clientId++) {
|
||||
let client = createClient(clientId);
|
||||
const client = createClient(clientId);
|
||||
promises.push(fs.remove(client.profileDir));
|
||||
promises.push(
|
||||
execCommand(client, 'config sync.target 2').then(() => {
|
||||
@ -2064,8 +2064,8 @@ function randomWord() {
|
||||
}
|
||||
|
||||
function execCommand(client, command, options = {}) {
|
||||
let exePath = `node ${joplinAppPath}`;
|
||||
let cmd = `${exePath} --update-geolocation-disabled --env dev --log-level debug --profile ${client.profileDir} ${command}`;
|
||||
const exePath = `node ${joplinAppPath}`;
|
||||
const cmd = `${exePath} --update-geolocation-disabled --env dev --log-level debug --profile ${client.profileDir} ${command}`;
|
||||
logger.info(`${client.id}: ${command}`);
|
||||
|
||||
if (options.killAfter) {
|
||||
@ -2073,7 +2073,7 @@ function execCommand(client, command, options = {}) {
|
||||
}
|
||||
|
||||
return new Promise((resolve, reject) => {
|
||||
let childProcess = exec(cmd, (error, stdout, stderr) => {
|
||||
const childProcess = exec(cmd, (error, stdout, stderr) => {
|
||||
if (error) {
|
||||
if (error.signal == 'SIGTERM') {
|
||||
resolve('Process was killed');
|
||||
@ -2096,7 +2096,7 @@ function execCommand(client, command, options = {}) {
|
||||
}
|
||||
|
||||
async function clientItems(client) {
|
||||
let itemsJson = await execCommand(client, 'dump');
|
||||
const itemsJson = await execCommand(client, 'dump');
|
||||
try {
|
||||
return JSON.parse(itemsJson);
|
||||
} catch (error) {
|
||||
@ -2105,7 +2105,7 @@ async function clientItems(client) {
|
||||
}
|
||||
|
||||
function randomTag(items) {
|
||||
let tags = [];
|
||||
const tags = [];
|
||||
for (let i = 0; i < items.length; i++) {
|
||||
if (items[i].type_ != 5) continue;
|
||||
tags.push(items[i]);
|
||||
@ -2115,7 +2115,7 @@ function randomTag(items) {
|
||||
}
|
||||
|
||||
function randomNote(items) {
|
||||
let notes = [];
|
||||
const notes = [];
|
||||
for (let i = 0; i < items.length; i++) {
|
||||
if (items[i].type_ != 1) continue;
|
||||
notes.push(items[i]);
|
||||
@ -2125,14 +2125,14 @@ function randomNote(items) {
|
||||
}
|
||||
|
||||
async function execRandomCommand(client) {
|
||||
let possibleCommands = [
|
||||
const possibleCommands = [
|
||||
['mkbook {word}', 40], // CREATE FOLDER
|
||||
['mknote {word}', 70], // CREATE NOTE
|
||||
[
|
||||
async () => {
|
||||
// DELETE RANDOM ITEM
|
||||
let items = await clientItems(client);
|
||||
let item = randomElement(items);
|
||||
const items = await clientItems(client);
|
||||
const item = randomElement(items);
|
||||
if (!item) return;
|
||||
|
||||
if (item.type_ == 1) {
|
||||
@ -2150,8 +2150,8 @@ async function execRandomCommand(client) {
|
||||
[
|
||||
async () => {
|
||||
// SYNC
|
||||
let avgSyncDuration = averageSyncDuration();
|
||||
let options = {};
|
||||
const avgSyncDuration = averageSyncDuration();
|
||||
const options = {};
|
||||
if (!isNaN(avgSyncDuration)) {
|
||||
if (Math.random() >= 0.5) {
|
||||
options.killAfter = avgSyncDuration * Math.random();
|
||||
@ -2164,8 +2164,8 @@ async function execRandomCommand(client) {
|
||||
[
|
||||
async () => {
|
||||
// UPDATE RANDOM ITEM
|
||||
let items = await clientItems(client);
|
||||
let item = randomNote(items);
|
||||
const items = await clientItems(client);
|
||||
const item = randomNote(items);
|
||||
if (!item) return;
|
||||
|
||||
return execCommand(client, `set ${item.id} title "${randomWord()}"`);
|
||||
@ -2175,12 +2175,12 @@ async function execRandomCommand(client) {
|
||||
[
|
||||
async () => {
|
||||
// ADD TAG
|
||||
let items = await clientItems(client);
|
||||
let note = randomNote(items);
|
||||
const items = await clientItems(client);
|
||||
const note = randomNote(items);
|
||||
if (!note) return;
|
||||
|
||||
let tag = randomTag(items);
|
||||
let tagTitle = !tag || Math.random() >= 0.9 ? `tag-${randomWord()}` : tag.title;
|
||||
const tag = randomTag(items);
|
||||
const tagTitle = !tag || Math.random() >= 0.9 ? `tag-${randomWord()}` : tag.title;
|
||||
|
||||
return execCommand(client, `tag add ${tagTitle} ${note.id}`);
|
||||
},
|
||||
@ -2191,7 +2191,7 @@ async function execRandomCommand(client) {
|
||||
let cmd = null;
|
||||
while (true) {
|
||||
cmd = randomElement(possibleCommands);
|
||||
let r = 1 + Math.floor(Math.random() * 100);
|
||||
const r = 1 + Math.floor(Math.random() * 100);
|
||||
if (r <= cmd[1]) break;
|
||||
}
|
||||
|
||||
@ -2210,7 +2210,7 @@ function averageSyncDuration() {
|
||||
}
|
||||
|
||||
function randomNextCheckTime() {
|
||||
let output = time.unixMs() + 1000 + Math.random() * 1000 * 120;
|
||||
const output = time.unixMs() + 1000 + Math.random() * 1000 * 120;
|
||||
logger.info(`Next sync check: ${time.unixMsToIso(output)} (${Math.round((output - time.unixMs()) / 1000)} sec.)`);
|
||||
return output;
|
||||
}
|
||||
@ -2223,11 +2223,11 @@ function findItem(items, itemId) {
|
||||
}
|
||||
|
||||
function compareItems(item1, item2) {
|
||||
let output = [];
|
||||
for (let n in item1) {
|
||||
const output = [];
|
||||
for (const n in item1) {
|
||||
if (!item1.hasOwnProperty(n)) continue;
|
||||
let p1 = item1[n];
|
||||
let p2 = item2[n];
|
||||
const p1 = item1[n];
|
||||
const p2 = item2[n];
|
||||
|
||||
if (n == 'notes_') {
|
||||
p1.sort();
|
||||
@ -2243,13 +2243,13 @@ function compareItems(item1, item2) {
|
||||
}
|
||||
|
||||
function findMissingItems_(items1, items2) {
|
||||
let output = [];
|
||||
const output = [];
|
||||
|
||||
for (let i = 0; i < items1.length; i++) {
|
||||
let item1 = items1[i];
|
||||
const item1 = items1[i];
|
||||
let found = false;
|
||||
for (let j = 0; j < items2.length; j++) {
|
||||
let item2 = items2[j];
|
||||
const item2 = items2[j];
|
||||
if (item1.id == item2.id) {
|
||||
found = true;
|
||||
break;
|
||||
@ -2269,33 +2269,33 @@ function findMissingItems(items1, items2) {
|
||||
}
|
||||
|
||||
async function compareClientItems(clientItems) {
|
||||
let itemCounts = [];
|
||||
const itemCounts = [];
|
||||
for (let i = 0; i < clientItems.length; i++) {
|
||||
let items = clientItems[i];
|
||||
const items = clientItems[i];
|
||||
itemCounts.push(items.length);
|
||||
}
|
||||
logger.info(`Item count: ${itemCounts.join(', ')}`);
|
||||
|
||||
let missingItems = findMissingItems(clientItems[0], clientItems[1]);
|
||||
const missingItems = findMissingItems(clientItems[0], clientItems[1]);
|
||||
if (missingItems[0].length || missingItems[1].length) {
|
||||
logger.error('Items are different');
|
||||
logger.error(missingItems);
|
||||
process.exit(1);
|
||||
}
|
||||
|
||||
let differences = [];
|
||||
let items = clientItems[0];
|
||||
const differences = [];
|
||||
const items = clientItems[0];
|
||||
for (let i = 0; i < items.length; i++) {
|
||||
let item1 = items[i];
|
||||
const item1 = items[i];
|
||||
for (let clientId = 1; clientId < clientItems.length; clientId++) {
|
||||
let item2 = findItem(clientItems[clientId], item1.id);
|
||||
const item2 = findItem(clientItems[clientId], item1.id);
|
||||
if (!item2) {
|
||||
logger.error(`Item not found on client ${clientId}:`);
|
||||
logger.error(item1);
|
||||
process.exit(1);
|
||||
}
|
||||
|
||||
let diff = compareItems(item1, item2);
|
||||
const diff = compareItems(item1, item2);
|
||||
if (diff.length) {
|
||||
differences.push({
|
||||
item1: JSON.stringify(item1),
|
||||
@ -2315,7 +2315,7 @@ async function compareClientItems(clientItems) {
|
||||
async function main() {
|
||||
await fs.remove(syncDir);
|
||||
|
||||
let clients = await createClients();
|
||||
const clients = await createClients();
|
||||
let clientId = 0;
|
||||
|
||||
for (let i = 0; i < clients.length; i++) {
|
||||
@ -2348,7 +2348,7 @@ async function main() {
|
||||
|
||||
if (state == 'syncCheck') {
|
||||
state = 'waitForSyncCheck';
|
||||
let clientItems = [];
|
||||
const clientItems = [];
|
||||
// Up to 3 sync operations must be performed by each clients in order for them
|
||||
// to be perfectly in sync - in order for each items to send their changes
|
||||
// and get those from the other clients, and to also get changes that are
|
||||
@ -2356,12 +2356,12 @@ async function main() {
|
||||
// with another one).
|
||||
for (let loopCount = 0; loopCount < 3; loopCount++) {
|
||||
for (let i = 0; i < clients.length; i++) {
|
||||
let beforeTime = time.unixMs();
|
||||
const beforeTime = time.unixMs();
|
||||
await execCommand(clients[i], 'sync');
|
||||
syncDurations.push(time.unixMs() - beforeTime);
|
||||
if (syncDurations.length > 20) syncDurations.splice(0, 1);
|
||||
if (loopCount === 2) {
|
||||
let dump = await execCommand(clients[i], 'dump');
|
||||
const dump = await execCommand(clients[i], 'dump');
|
||||
clientItems[i] = JSON.parse(dump);
|
||||
}
|
||||
}
|
||||
|
@ -20,7 +20,7 @@ class FolderListWidget extends ListWidget {
|
||||
this.trimItemTitle = false;
|
||||
|
||||
this.itemRenderer = item => {
|
||||
let output = [];
|
||||
const output = [];
|
||||
if (item === '-') {
|
||||
output.push('-'.repeat(this.innerWidth));
|
||||
} else if (item.type_ === Folder.modelType()) {
|
||||
@ -121,7 +121,7 @@ class FolderListWidget extends ListWidget {
|
||||
|
||||
folderHasChildren_(folders, folderId) {
|
||||
for (let i = 0; i < folders.length; i++) {
|
||||
let folder = folders[i];
|
||||
const folder = folders[i];
|
||||
if (folder.parent_id === folderId) return true;
|
||||
}
|
||||
return false;
|
||||
|
@ -106,7 +106,7 @@ class StatusBarWidget extends BaseWidget {
|
||||
|
||||
const isSecurePrompt = !!this.promptState_.secure;
|
||||
|
||||
let options = {
|
||||
const options = {
|
||||
cancelable: true,
|
||||
history: this.history,
|
||||
default: this.promptState_.initialText,
|
||||
|
@ -6,11 +6,11 @@ const MAX_WIDTH = 78;
|
||||
const INDENT = ' ';
|
||||
|
||||
function renderTwoColumnData(options, baseIndent, width) {
|
||||
let output = [];
|
||||
const output = [];
|
||||
const optionColWidth = getOptionColWidth(options);
|
||||
|
||||
for (let i = 0; i < options.length; i++) {
|
||||
let option = options[i];
|
||||
const option = options[i];
|
||||
const flag = option[0];
|
||||
const indent = baseIndent + INDENT + ' '.repeat(optionColWidth + 2);
|
||||
|
||||
@ -28,7 +28,7 @@ function renderCommandHelp(cmd, width = null) {
|
||||
|
||||
const baseIndent = '';
|
||||
|
||||
let output = [];
|
||||
const output = [];
|
||||
output.push(baseIndent + cmd.usage());
|
||||
output.push('');
|
||||
output.push(wrap(cmd.description(), baseIndent + INDENT, width));
|
||||
@ -42,7 +42,7 @@ function renderCommandHelp(cmd, width = null) {
|
||||
|
||||
if (cmd.name() === 'config') {
|
||||
const renderMetadata = md => {
|
||||
let desc = [];
|
||||
const desc = [];
|
||||
|
||||
if (md.label) {
|
||||
let label = md.label();
|
||||
@ -77,7 +77,7 @@ function renderCommandHelp(cmd, width = null) {
|
||||
output.push(_('Possible keys/values:'));
|
||||
output.push('');
|
||||
|
||||
let keysValues = [];
|
||||
const keysValues = [];
|
||||
const keys = Setting.keys(true, 'cli');
|
||||
for (let i = 0; i < keys.length; i++) {
|
||||
if (keysValues.length) keysValues.push(['', '']);
|
||||
|
@ -54,7 +54,7 @@ shimInit();
|
||||
const application = app();
|
||||
|
||||
if (process.platform === 'win32') {
|
||||
var rl = require('readline').createInterface({
|
||||
const rl = require('readline').createInterface({
|
||||
input: process.stdin,
|
||||
output: process.stdout,
|
||||
});
|
||||
|
@ -14,14 +14,14 @@ describe('InteropService_Importer_Md: importLocalImages', function() {
|
||||
it('should import linked files and modify tags appropriately', async function() {
|
||||
const tagNonExistentFile = '![does not exist](does_not_exist.png)';
|
||||
const note = await importer.importFile(`${__dirname}/md_to_md/sample.md`, 'notebook');
|
||||
let items = await Note.linkedItems(note.body);
|
||||
const items = await Note.linkedItems(note.body);
|
||||
expect(items.length).toBe(2);
|
||||
const inexistentLinkUnchanged = note.body.includes(tagNonExistentFile);
|
||||
expect(inexistentLinkUnchanged).toBe(true);
|
||||
});
|
||||
it('should only create 1 resource for duplicate links, all tags should be updated', async function() {
|
||||
const note = await importer.importFile(`${__dirname}/md_to_md/sample-duplicate-links.md`, 'notebook');
|
||||
let items = await Note.linkedItems(note.body);
|
||||
const items = await Note.linkedItems(note.body);
|
||||
expect(items.length).toBe(1);
|
||||
const reg = new RegExp(items[0].id, 'g');
|
||||
const matched = note.body.match(reg);
|
||||
@ -29,12 +29,12 @@ describe('InteropService_Importer_Md: importLocalImages', function() {
|
||||
});
|
||||
it('should import linked files and modify tags appropriately when link is also in alt text', async function() {
|
||||
const note = await importer.importFile(`${__dirname}/md_to_md/sample-link-in-alt-text.md`, 'notebook');
|
||||
let items = await Note.linkedItems(note.body);
|
||||
const items = await Note.linkedItems(note.body);
|
||||
expect(items.length).toBe(1);
|
||||
});
|
||||
it('should passthrough unchanged if no links present', async function() {
|
||||
const note = await importer.importFile(`${__dirname}/md_to_md/sample-no-links.md`, 'notebook');
|
||||
let items = await Note.linkedItems(note.body);
|
||||
const items = await Note.linkedItems(note.body);
|
||||
expect(items.length).toBe(0);
|
||||
expect(note.body).toContain('Unidentified vessel travelling at sub warp speed, bearing 235.7. Fluctuations in energy readings from it, Captain. All transporters off.');
|
||||
});
|
||||
|
@ -44,19 +44,19 @@ describe('integration_ShowAllNotes', function() {
|
||||
|
||||
it('should show all notes', asyncTest(async () => {
|
||||
// setup
|
||||
let folders = await createNTestFolders(3);
|
||||
const folders = await createNTestFolders(3);
|
||||
Folder.moveToFolder(id(folders[2]), id(folders[1])); // subfolder
|
||||
await time.msleep(100);
|
||||
let notes0 = await createNTestNotes(3, folders[0]);
|
||||
let notes1 = await createNTestNotes(3, folders[1]);
|
||||
let notes2 = await createNTestNotes(3, folders[2]);
|
||||
const notes0 = await createNTestNotes(3, folders[0]);
|
||||
const notes1 = await createNTestNotes(3, folders[1]);
|
||||
const notes2 = await createNTestNotes(3, folders[2]);
|
||||
|
||||
// TEST ACTION: View all-notes
|
||||
testApp.dispatch({ type: 'SMART_FILTER_SELECT', id: ALL_NOTES_FILTER_ID });
|
||||
await time.msleep(100);
|
||||
|
||||
// check: all the notes are shown
|
||||
let state = testApp.store().getState();
|
||||
const state = testApp.store().getState();
|
||||
expect(state.notesParentType).toEqual('SmartFilter');
|
||||
expect(state.selectedSmartFilterId).toEqual(ALL_NOTES_FILTER_ID);
|
||||
expect(sortedIds(state.notes)).toEqual(sortedIds(notes0.concat(notes1).concat(notes2)));
|
||||
@ -64,9 +64,9 @@ describe('integration_ShowAllNotes', function() {
|
||||
|
||||
it('should show retain note selection when going from a folder to all-notes', asyncTest(async () => {
|
||||
// setup
|
||||
let folders = await createNTestFolders(2);
|
||||
let notes0 = await createNTestNotes(3, folders[0]);
|
||||
let notes1 = await createNTestNotes(3, folders[1]);
|
||||
const folders = await createNTestFolders(2);
|
||||
const notes0 = await createNTestNotes(3, folders[0]);
|
||||
const notes1 = await createNTestNotes(3, folders[1]);
|
||||
testApp.dispatch({ type: 'FOLDER_SELECT', id: id(folders[1]) });
|
||||
await time.msleep(100);
|
||||
testApp.dispatch({ type: 'NOTE_SELECT', id: id(notes1[1]) });
|
||||
|
@ -8,27 +8,27 @@ const Tag = require('lib/models/Tag.js');
|
||||
const { time } = require('lib/time-utils.js');
|
||||
|
||||
async function createNTestFolders(n) {
|
||||
let folders = [];
|
||||
const folders = [];
|
||||
for (let i = 0; i < n; i++) {
|
||||
let folder = await Folder.save({ title: 'folder' });
|
||||
const folder = await Folder.save({ title: 'folder' });
|
||||
folders.push(folder);
|
||||
}
|
||||
return folders;
|
||||
}
|
||||
|
||||
async function createNTestNotes(n, folder) {
|
||||
let notes = [];
|
||||
const notes = [];
|
||||
for (let i = 0; i < n; i++) {
|
||||
let note = await Note.save({ title: 'note', parent_id: folder.id, is_conflict: 0 });
|
||||
const note = await Note.save({ title: 'note', parent_id: folder.id, is_conflict: 0 });
|
||||
notes.push(note);
|
||||
}
|
||||
return notes;
|
||||
}
|
||||
|
||||
async function createNTestTags(n) {
|
||||
let tags = [];
|
||||
const tags = [];
|
||||
for (let i = 0; i < n; i++) {
|
||||
let tag = await Tag.save({ title: 'tag' });
|
||||
const tag = await Tag.save({ title: 'tag' });
|
||||
tags.push(tag);
|
||||
}
|
||||
return tags;
|
||||
@ -58,9 +58,9 @@ describe('integration_TagList', function() {
|
||||
// the tag list should be cleared if the next note has no tags
|
||||
it('should clear tag list when a note is deleted', asyncTest(async () => {
|
||||
// setup and select the note
|
||||
let folders = await createNTestFolders(1);
|
||||
let notes = await createNTestNotes(5, folders[0]);
|
||||
let tags = await createNTestTags(3);
|
||||
const folders = await createNTestFolders(1);
|
||||
const notes = await createNTestNotes(5, folders[0]);
|
||||
const tags = await createNTestTags(3);
|
||||
|
||||
await Tag.addNote(tags[2].id, notes[2].id);
|
||||
|
||||
@ -96,9 +96,9 @@ describe('integration_TagList', function() {
|
||||
// the tag list should be updated if the next note has tags
|
||||
it('should update tag list when a note is deleted', asyncTest(async () => {
|
||||
// set up and select the note
|
||||
let folders = await createNTestFolders(1);
|
||||
let notes = await createNTestNotes(5, folders[0]);
|
||||
let tags = await createNTestTags(3);
|
||||
const folders = await createNTestFolders(1);
|
||||
const notes = await createNTestNotes(5, folders[0]);
|
||||
const tags = await createNTestTags(3);
|
||||
|
||||
await Tag.addNote(tags[1].id, notes[1].id);
|
||||
await Tag.addNote(tags[0].id, notes[0].id);
|
||||
@ -130,8 +130,8 @@ describe('integration_TagList', function() {
|
||||
|
||||
// check the tag list is updated
|
||||
state = testApp.store().getState();
|
||||
let tagIds = state.selectedNoteTags.map(n => n.id).sort();
|
||||
let expectedTagIds = [tags[0].id, tags[2].id].sort();
|
||||
const tagIds = state.selectedNoteTags.map(n => n.id).sort();
|
||||
const expectedTagIds = [tags[0].id, tags[2].id].sort();
|
||||
expect(state.selectedNoteTags.length).toEqual(2);
|
||||
expect(tagIds).toEqual(expectedTagIds);
|
||||
}));
|
||||
|
@ -16,8 +16,8 @@ process.on('unhandledRejection', (reason, p) => {
|
||||
});
|
||||
|
||||
async function allItems() {
|
||||
let folders = await Folder.all();
|
||||
let notes = await Note.all();
|
||||
const folders = await Folder.all();
|
||||
const notes = await Note.all();
|
||||
return folders.concat(notes);
|
||||
}
|
||||
|
||||
@ -32,27 +32,27 @@ describe('models_BaseItem', function() {
|
||||
// This is to handle the case where a property is removed from a BaseItem table - in that case files in
|
||||
// the sync target will still have the old property but we don't need it locally.
|
||||
it('should ignore properties that are present in sync file but not in database when serialising', asyncTest(async () => {
|
||||
let folder = await Folder.save({ title: 'folder1' });
|
||||
const folder = await Folder.save({ title: 'folder1' });
|
||||
|
||||
let serialized = await Folder.serialize(folder);
|
||||
serialized += '\nignore_me: true';
|
||||
|
||||
let unserialized = await Folder.unserialize(serialized);
|
||||
const unserialized = await Folder.unserialize(serialized);
|
||||
|
||||
expect('ignore_me' in unserialized).toBe(false);
|
||||
}));
|
||||
|
||||
it('should not modify title when unserializing', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: '' });
|
||||
let folder2 = await Folder.save({ title: 'folder1' });
|
||||
const folder1 = await Folder.save({ title: '' });
|
||||
const folder2 = await Folder.save({ title: 'folder1' });
|
||||
|
||||
let serialized1 = await Folder.serialize(folder1);
|
||||
let unserialized1 = await Folder.unserialize(serialized1);
|
||||
const serialized1 = await Folder.serialize(folder1);
|
||||
const unserialized1 = await Folder.unserialize(serialized1);
|
||||
|
||||
expect(unserialized1.title).toBe(folder1.title);
|
||||
|
||||
let serialized2 = await Folder.serialize(folder2);
|
||||
let unserialized2 = await Folder.unserialize(serialized2);
|
||||
const serialized2 = await Folder.serialize(folder2);
|
||||
const unserialized2 = await Folder.unserialize(serialized2);
|
||||
|
||||
expect(unserialized2.title).toBe(folder2.title);
|
||||
}));
|
||||
|
@ -14,8 +14,8 @@ process.on('unhandledRejection', (reason, p) => {
|
||||
});
|
||||
|
||||
async function allItems() {
|
||||
let folders = await Folder.all();
|
||||
let notes = await Note.all();
|
||||
const folders = await Folder.all();
|
||||
const notes = await Note.all();
|
||||
return folders.concat(notes);
|
||||
}
|
||||
|
||||
@ -28,10 +28,10 @@ describe('models_Folder', function() {
|
||||
});
|
||||
|
||||
it('should tell if a notebook can be nested under another one', asyncTest(async () => {
|
||||
let f1 = await Folder.save({ title: 'folder1' });
|
||||
let f2 = await Folder.save({ title: 'folder2', parent_id: f1.id });
|
||||
let f3 = await Folder.save({ title: 'folder3', parent_id: f2.id });
|
||||
let f4 = await Folder.save({ title: 'folder4' });
|
||||
const f1 = await Folder.save({ title: 'folder1' });
|
||||
const f2 = await Folder.save({ title: 'folder2', parent_id: f1.id });
|
||||
const f3 = await Folder.save({ title: 'folder3', parent_id: f2.id });
|
||||
const f4 = await Folder.save({ title: 'folder4' });
|
||||
|
||||
expect(await Folder.canNestUnder(f1.id, f2.id)).toBe(false);
|
||||
expect(await Folder.canNestUnder(f2.id, f2.id)).toBe(false);
|
||||
@ -44,9 +44,9 @@ describe('models_Folder', function() {
|
||||
}));
|
||||
|
||||
it('should recursively delete notes and sub-notebooks', asyncTest(async () => {
|
||||
let f1 = await Folder.save({ title: 'folder1' });
|
||||
let f2 = await Folder.save({ title: 'folder2', parent_id: f1.id });
|
||||
let n1 = await Note.save({ title: 'note1', parent_id: f2.id });
|
||||
const f1 = await Folder.save({ title: 'folder1' });
|
||||
const f2 = await Folder.save({ title: 'folder2', parent_id: f1.id });
|
||||
const n1 = await Note.save({ title: 'note1', parent_id: f2.id });
|
||||
|
||||
await Folder.delete(f1.id);
|
||||
|
||||
@ -57,10 +57,10 @@ describe('models_Folder', function() {
|
||||
it('should sort by last modified, based on content', asyncTest(async () => {
|
||||
let folders;
|
||||
|
||||
let f1 = await Folder.save({ title: 'folder1' }); await sleep(0.1);
|
||||
let f2 = await Folder.save({ title: 'folder2' }); await sleep(0.1);
|
||||
let f3 = await Folder.save({ title: 'folder3' }); await sleep(0.1);
|
||||
let n1 = await Note.save({ title: 'note1', parent_id: f2.id });
|
||||
const f1 = await Folder.save({ title: 'folder1' }); await sleep(0.1);
|
||||
const f2 = await Folder.save({ title: 'folder2' }); await sleep(0.1);
|
||||
const f3 = await Folder.save({ title: 'folder3' }); await sleep(0.1);
|
||||
const n1 = await Note.save({ title: 'note1', parent_id: f2.id });
|
||||
|
||||
folders = await Folder.orderByLastModified(await Folder.all(), 'desc');
|
||||
expect(folders.length).toBe(3);
|
||||
@ -68,7 +68,7 @@ describe('models_Folder', function() {
|
||||
expect(folders[1].id).toBe(f3.id);
|
||||
expect(folders[2].id).toBe(f1.id);
|
||||
|
||||
let n2 = await Note.save({ title: 'note1', parent_id: f1.id });
|
||||
const n2 = await Note.save({ title: 'note1', parent_id: f1.id });
|
||||
|
||||
folders = await Folder.orderByLastModified(await Folder.all(), 'desc');
|
||||
expect(folders[0].id).toBe(f1.id);
|
||||
@ -91,10 +91,10 @@ describe('models_Folder', function() {
|
||||
it('should sort by last modified, based on content (sub-folders too)', asyncTest(async () => {
|
||||
let folders;
|
||||
|
||||
let f1 = await Folder.save({ title: 'folder1' }); await sleep(0.1);
|
||||
let f2 = await Folder.save({ title: 'folder2' }); await sleep(0.1);
|
||||
let f3 = await Folder.save({ title: 'folder3', parent_id: f1.id }); await sleep(0.1);
|
||||
let n1 = await Note.save({ title: 'note1', parent_id: f3.id });
|
||||
const f1 = await Folder.save({ title: 'folder1' }); await sleep(0.1);
|
||||
const f2 = await Folder.save({ title: 'folder2' }); await sleep(0.1);
|
||||
const f3 = await Folder.save({ title: 'folder3', parent_id: f1.id }); await sleep(0.1);
|
||||
const n1 = await Note.save({ title: 'note1', parent_id: f3.id });
|
||||
|
||||
folders = await Folder.orderByLastModified(await Folder.all(), 'desc');
|
||||
expect(folders.length).toBe(3);
|
||||
@ -102,7 +102,7 @@ describe('models_Folder', function() {
|
||||
expect(folders[1].id).toBe(f3.id);
|
||||
expect(folders[2].id).toBe(f2.id);
|
||||
|
||||
let n2 = await Note.save({ title: 'note2', parent_id: f2.id });
|
||||
const n2 = await Note.save({ title: 'note2', parent_id: f2.id });
|
||||
folders = await Folder.orderByLastModified(await Folder.all(), 'desc');
|
||||
|
||||
expect(folders[0].id).toBe(f2.id);
|
||||
@ -116,8 +116,8 @@ describe('models_Folder', function() {
|
||||
expect(folders[1].id).toBe(f3.id);
|
||||
expect(folders[2].id).toBe(f2.id);
|
||||
|
||||
let f4 = await Folder.save({ title: 'folder4', parent_id: f1.id }); await sleep(0.1);
|
||||
let n3 = await Note.save({ title: 'note3', parent_id: f4.id });
|
||||
const f4 = await Folder.save({ title: 'folder4', parent_id: f1.id }); await sleep(0.1);
|
||||
const n3 = await Note.save({ title: 'note3', parent_id: f4.id });
|
||||
|
||||
folders = await Folder.orderByLastModified(await Folder.all(), 'desc');
|
||||
expect(folders.length).toBe(4);
|
||||
@ -128,14 +128,14 @@ describe('models_Folder', function() {
|
||||
}));
|
||||
|
||||
it('should add node counts', asyncTest(async () => {
|
||||
let f1 = await Folder.save({ title: 'folder1' });
|
||||
let f2 = await Folder.save({ title: 'folder2', parent_id: f1.id });
|
||||
let f3 = await Folder.save({ title: 'folder3', parent_id: f2.id });
|
||||
let f4 = await Folder.save({ title: 'folder4' });
|
||||
const f1 = await Folder.save({ title: 'folder1' });
|
||||
const f2 = await Folder.save({ title: 'folder2', parent_id: f1.id });
|
||||
const f3 = await Folder.save({ title: 'folder3', parent_id: f2.id });
|
||||
const f4 = await Folder.save({ title: 'folder4' });
|
||||
|
||||
let n1 = await Note.save({ title: 'note1', parent_id: f3.id });
|
||||
let n2 = await Note.save({ title: 'note1', parent_id: f3.id });
|
||||
let n3 = await Note.save({ title: 'note1', parent_id: f1.id });
|
||||
const n1 = await Note.save({ title: 'note1', parent_id: f3.id });
|
||||
const n2 = await Note.save({ title: 'note1', parent_id: f3.id });
|
||||
const n3 = await Note.save({ title: 'note1', parent_id: f1.id });
|
||||
|
||||
const folders = await Folder.all();
|
||||
await Folder.addNoteCounts(folders);
|
||||
@ -152,17 +152,17 @@ describe('models_Folder', function() {
|
||||
|
||||
it('should not count completed to-dos', asyncTest(async () => {
|
||||
|
||||
let f1 = await Folder.save({ title: 'folder1' });
|
||||
let f2 = await Folder.save({ title: 'folder2', parent_id: f1.id });
|
||||
let f3 = await Folder.save({ title: 'folder3', parent_id: f2.id });
|
||||
let f4 = await Folder.save({ title: 'folder4' });
|
||||
const f1 = await Folder.save({ title: 'folder1' });
|
||||
const f2 = await Folder.save({ title: 'folder2', parent_id: f1.id });
|
||||
const f3 = await Folder.save({ title: 'folder3', parent_id: f2.id });
|
||||
const f4 = await Folder.save({ title: 'folder4' });
|
||||
|
||||
let n1 = await Note.save({ title: 'note1', parent_id: f3.id });
|
||||
let n2 = await Note.save({ title: 'note2', parent_id: f3.id });
|
||||
let n3 = await Note.save({ title: 'note3', parent_id: f1.id });
|
||||
let n4 = await Note.save({ title: 'note4', parent_id: f3.id, is_todo: true, todo_completed: 0 });
|
||||
let n5 = await Note.save({ title: 'note5', parent_id: f3.id, is_todo: true, todo_completed: 999 });
|
||||
let n6 = await Note.save({ title: 'note6', parent_id: f3.id, is_todo: true, todo_completed: 999 });
|
||||
const n1 = await Note.save({ title: 'note1', parent_id: f3.id });
|
||||
const n2 = await Note.save({ title: 'note2', parent_id: f3.id });
|
||||
const n3 = await Note.save({ title: 'note3', parent_id: f1.id });
|
||||
const n4 = await Note.save({ title: 'note4', parent_id: f3.id, is_todo: true, todo_completed: 0 });
|
||||
const n5 = await Note.save({ title: 'note5', parent_id: f3.id, is_todo: true, todo_completed: 999 });
|
||||
const n6 = await Note.save({ title: 'note6', parent_id: f3.id, is_todo: true, todo_completed: 999 });
|
||||
|
||||
const folders = await Folder.all();
|
||||
await Folder.addNoteCounts(folders, false);
|
||||
@ -179,9 +179,9 @@ describe('models_Folder', function() {
|
||||
|
||||
it('should recursively find folder path', asyncTest(async () => {
|
||||
|
||||
let f1 = await Folder.save({ title: 'folder1' });
|
||||
let f2 = await Folder.save({ title: 'folder2', parent_id: f1.id });
|
||||
let f3 = await Folder.save({ title: 'folder3', parent_id: f2.id });
|
||||
const f1 = await Folder.save({ title: 'folder1' });
|
||||
const f2 = await Folder.save({ title: 'folder2', parent_id: f1.id });
|
||||
const f3 = await Folder.save({ title: 'folder3', parent_id: f2.id });
|
||||
|
||||
const folders = await Folder.all();
|
||||
const folderPath = await Folder.folderPath(folders, f3.id);
|
||||
|
@ -23,8 +23,8 @@ describe('models_Note', function() {
|
||||
});
|
||||
|
||||
it('should find resource and note IDs', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
let note2 = await Note.save({ title: 'ma deuxième note', body: `Lien vers première note : ${Note.markdownTag(note1)}`, parent_id: folder1.id });
|
||||
|
||||
let items = await Note.linkedItems(note2.body);
|
||||
@ -69,7 +69,7 @@ describe('models_Note', function() {
|
||||
}));
|
||||
|
||||
it('should change the type of notes', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
note1 = await Note.load(note1.id);
|
||||
|
||||
@ -90,7 +90,7 @@ describe('models_Note', function() {
|
||||
}));
|
||||
|
||||
it('should serialize and unserialize without modifying data', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const testCases = [
|
||||
[{ title: '', body: 'Body and no title\nSecond line\nThird Line', parent_id: folder1.id },
|
||||
'', 'Body and no title\nSecond line\nThird Line'],
|
||||
@ -107,9 +107,9 @@ describe('models_Note', function() {
|
||||
const expectedTitle = t[1];
|
||||
const expectedBody = t[1];
|
||||
|
||||
let note1 = await Note.save(input);
|
||||
let serialized = await Note.serialize(note1);
|
||||
let unserialized = await Note.unserialize(serialized);
|
||||
const note1 = await Note.save(input);
|
||||
const serialized = await Note.serialize(note1);
|
||||
const unserialized = await Note.unserialize(serialized);
|
||||
|
||||
expect(unserialized.title).toBe(input.title);
|
||||
expect(unserialized.body).toBe(input.body);
|
||||
@ -117,10 +117,10 @@ describe('models_Note', function() {
|
||||
}));
|
||||
|
||||
it('should reset fields for a duplicate', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'note', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'note', parent_id: folder1.id });
|
||||
|
||||
let duplicatedNote = await Note.duplicate(note1.id);
|
||||
const duplicatedNote = await Note.duplicate(note1.id);
|
||||
|
||||
expect(duplicatedNote !== note1).toBe(true);
|
||||
expect(duplicatedNote.created_time !== note1.created_time).toBe(true);
|
||||
|
@ -27,30 +27,30 @@ describe('models_Resource', function() {
|
||||
});
|
||||
|
||||
it('should have a "done" fetch_status when created locally', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
await shim.attachFileToNote(note1, testImagePath);
|
||||
let resource1 = (await Resource.all())[0];
|
||||
let ls = await Resource.localState(resource1);
|
||||
const resource1 = (await Resource.all())[0];
|
||||
const ls = await Resource.localState(resource1);
|
||||
expect(ls.fetch_status).toBe(Resource.FETCH_STATUS_DONE);
|
||||
}));
|
||||
|
||||
it('should have a default local state', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
await shim.attachFileToNote(note1, testImagePath);
|
||||
let resource1 = (await Resource.all())[0];
|
||||
let ls = await Resource.localState(resource1);
|
||||
const resource1 = (await Resource.all())[0];
|
||||
const ls = await Resource.localState(resource1);
|
||||
expect(!ls.id).toBe(true);
|
||||
expect(ls.resource_id).toBe(resource1.id);
|
||||
expect(ls.fetch_status).toBe(Resource.FETCH_STATUS_DONE);
|
||||
}));
|
||||
|
||||
it('should save and delete local state', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
await shim.attachFileToNote(note1, testImagePath);
|
||||
let resource1 = (await Resource.all())[0];
|
||||
const resource1 = (await Resource.all())[0];
|
||||
await Resource.setLocalState(resource1, { fetch_status: Resource.FETCH_STATUS_IDLE });
|
||||
|
||||
let ls = await Resource.localState(resource1);
|
||||
@ -63,13 +63,13 @@ describe('models_Resource', function() {
|
||||
}));
|
||||
|
||||
it('should resize the resource if the image is below the required dimensions', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const previousMax = Resource.IMAGE_MAX_DIMENSION;
|
||||
Resource.IMAGE_MAX_DIMENSION = 5;
|
||||
await shim.attachFileToNote(note1, testImagePath);
|
||||
Resource.IMAGE_MAX_DIMENSION = previousMax;
|
||||
let resource1 = (await Resource.all())[0];
|
||||
const resource1 = (await Resource.all())[0];
|
||||
|
||||
const originalStat = await shim.fsDriver().stat(testImagePath);
|
||||
const newStat = await shim.fsDriver().stat(Resource.fullPath(resource1));
|
||||
@ -78,10 +78,10 @@ describe('models_Resource', function() {
|
||||
}));
|
||||
|
||||
it('should not resize the resource if the image is below the required dimensions', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
await shim.attachFileToNote(note1, testImagePath);
|
||||
let resource1 = (await Resource.all())[0];
|
||||
const resource1 = (await Resource.all())[0];
|
||||
|
||||
const originalStat = await shim.fsDriver().stat(testImagePath);
|
||||
const newStat = await shim.fsDriver().stat(Resource.fullPath(resource1));
|
||||
|
@ -24,8 +24,8 @@ describe('models_Tag', function() {
|
||||
});
|
||||
|
||||
it('should add tags by title', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
|
||||
await Tag.setNoteTagsByTitles(note1.id, ['un', 'deux']);
|
||||
|
||||
@ -34,8 +34,8 @@ describe('models_Tag', function() {
|
||||
}));
|
||||
|
||||
it('should not allow renaming tag to existing tag names', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
|
||||
await Tag.setNoteTagsByTitles(note1.id, ['un', 'deux']);
|
||||
|
||||
@ -46,8 +46,8 @@ describe('models_Tag', function() {
|
||||
}));
|
||||
|
||||
it('should not return tags without notes', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
await Tag.setNoteTagsByTitles(note1.id, ['un']);
|
||||
|
||||
let tags = await Tag.allWithNotes();
|
||||
@ -60,9 +60,9 @@ describe('models_Tag', function() {
|
||||
}));
|
||||
|
||||
it('should return tags with note counts', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
let note2 = await Note.save({ title: 'ma 2nd note', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const note2 = await Note.save({ title: 'ma 2nd note', parent_id: folder1.id });
|
||||
await Tag.setNoteTagsByTitles(note1.id, ['un']);
|
||||
await Tag.setNoteTagsByTitles(note2.id, ['un']);
|
||||
|
||||
@ -83,10 +83,10 @@ describe('models_Tag', function() {
|
||||
}));
|
||||
|
||||
it('should load individual tags with note count', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
let note2 = await Note.save({ title: 'ma 2nd note', parent_id: folder1.id });
|
||||
let tag = await Tag.save({ title: 'mytag' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const note2 = await Note.save({ title: 'ma 2nd note', parent_id: folder1.id });
|
||||
const tag = await Tag.save({ title: 'mytag' });
|
||||
await Tag.addNote(tag.id, note1.id);
|
||||
|
||||
let tagWithCount = await Tag.loadWithCount(tag.id);
|
||||
@ -98,16 +98,16 @@ describe('models_Tag', function() {
|
||||
}));
|
||||
|
||||
it('should get common tags for set of notes', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let taga = await Tag.save({ title: 'mytaga' });
|
||||
let tagb = await Tag.save({ title: 'mytagb' });
|
||||
let tagc = await Tag.save({ title: 'mytagc' });
|
||||
let tagd = await Tag.save({ title: 'mytagd' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const taga = await Tag.save({ title: 'mytaga' });
|
||||
const tagb = await Tag.save({ title: 'mytagb' });
|
||||
const tagc = await Tag.save({ title: 'mytagc' });
|
||||
const tagd = await Tag.save({ title: 'mytagd' });
|
||||
|
||||
let note0 = await Note.save({ title: 'ma note 0', parent_id: folder1.id });
|
||||
let note1 = await Note.save({ title: 'ma note 1', parent_id: folder1.id });
|
||||
let note2 = await Note.save({ title: 'ma note 2', parent_id: folder1.id });
|
||||
let note3 = await Note.save({ title: 'ma note 3', parent_id: folder1.id });
|
||||
const note0 = await Note.save({ title: 'ma note 0', parent_id: folder1.id });
|
||||
const note1 = await Note.save({ title: 'ma note 1', parent_id: folder1.id });
|
||||
const note2 = await Note.save({ title: 'ma note 2', parent_id: folder1.id });
|
||||
const note3 = await Note.save({ title: 'ma note 3', parent_id: folder1.id });
|
||||
|
||||
await Tag.addNote(taga.id, note1.id);
|
||||
|
||||
|
@ -7,7 +7,7 @@ const Note = require('lib/models/Note.js');
|
||||
const Tag = require('lib/models/Tag.js');
|
||||
const { reducer, defaultState, stateUtils } = require('lib/reducer.js');
|
||||
|
||||
function initTestState(folders, selectedFolderIndex, notes, selectedNoteIndexes, tags=null, selectedTagIndex=null) {
|
||||
function initTestState(folders, selectedFolderIndex, notes, selectedNoteIndexes, tags = null, selectedTagIndex = null) {
|
||||
let state = defaultState;
|
||||
|
||||
if (selectedFolderIndex != null) {
|
||||
@ -20,7 +20,7 @@ function initTestState(folders, selectedFolderIndex, notes, selectedNoteIndexes,
|
||||
state = reducer(state, { type: 'NOTE_UPDATE_ALL', notes: notes, noteSource: 'test' });
|
||||
}
|
||||
if (selectedNoteIndexes != null) {
|
||||
let selectedIds = [];
|
||||
const selectedIds = [];
|
||||
for (let i = 0; i < selectedNoteIndexes.length; i++) {
|
||||
selectedIds.push(notes[selectedNoteIndexes[i]].id);
|
||||
}
|
||||
@ -37,7 +37,7 @@ function initTestState(folders, selectedFolderIndex, notes, selectedNoteIndexes,
|
||||
}
|
||||
|
||||
function createExpectedState(items, keepIndexes, selectedIndexes) {
|
||||
let expected = { items: [], selectedIds: [] };
|
||||
const expected = { items: [], selectedIds: [] };
|
||||
|
||||
for (let i = 0; i < selectedIndexes.length; i++) {
|
||||
expected.selectedIds.push(items[selectedIndexes[i]].id);
|
||||
@ -48,8 +48,8 @@ function createExpectedState(items, keepIndexes, selectedIndexes) {
|
||||
return expected;
|
||||
}
|
||||
|
||||
function getIds(items, indexes=null) {
|
||||
let ids = [];
|
||||
function getIds(items, indexes = null) {
|
||||
const ids = [];
|
||||
for (let i = 0; i < items.length; i++) {
|
||||
if (indexes == null || i in indexes) {
|
||||
ids.push(items[i].id);
|
||||
@ -76,9 +76,9 @@ describe('Reducer', function() {
|
||||
// tests for NOTE_DELETE
|
||||
it('should delete selected note', asyncTest(async () => {
|
||||
// create 1 folder
|
||||
let folders = await createNTestFolders(1);
|
||||
const folders = await createNTestFolders(1);
|
||||
// create 5 notes
|
||||
let notes = await createNTestNotes(5, folders[0]);
|
||||
const notes = await createNTestNotes(5, folders[0]);
|
||||
// select the 1st folder and the 3rd note
|
||||
let state = initTestState(folders, 0, notes, [2]);
|
||||
|
||||
@ -87,7 +87,7 @@ describe('Reducer', function() {
|
||||
state = reducer(state, { type: 'NOTE_DELETE', id: notes[2].id });
|
||||
|
||||
// expect that the third note is missing, and the 4th note is now selected
|
||||
let expected = createExpectedState(notes, [0,1,3,4], [3]);
|
||||
const expected = createExpectedState(notes, [0,1,3,4], [3]);
|
||||
|
||||
// check the ids of all the remaining notes
|
||||
expect(getIds(state.notes)).toEqual(getIds(expected.items));
|
||||
@ -96,136 +96,136 @@ describe('Reducer', function() {
|
||||
}));
|
||||
|
||||
it('should delete selected note at top', asyncTest(async () => {
|
||||
let folders = await createNTestFolders(1);
|
||||
let notes = await createNTestNotes(5, folders[0]);
|
||||
const folders = await createNTestFolders(1);
|
||||
const notes = await createNTestNotes(5, folders[0]);
|
||||
let state = initTestState(folders, 0, notes, [1]);
|
||||
|
||||
// test action
|
||||
state = reducer(state, { type: 'NOTE_DELETE', id: notes[0].id });
|
||||
|
||||
let expected = createExpectedState(notes, [1,2,3,4], [1]);
|
||||
const expected = createExpectedState(notes, [1,2,3,4], [1]);
|
||||
|
||||
expect(getIds(state.notes)).toEqual(getIds(expected.items));
|
||||
expect(state.selectedNoteIds).toEqual(expected.selectedIds);
|
||||
}));
|
||||
|
||||
it('should delete last remaining note', asyncTest(async () => {
|
||||
let folders = await createNTestFolders(1);
|
||||
let notes = await createNTestNotes(1, folders[0]);
|
||||
const folders = await createNTestFolders(1);
|
||||
const notes = await createNTestNotes(1, folders[0]);
|
||||
let state = initTestState(folders, 0, notes, [0]);
|
||||
|
||||
// test action
|
||||
state = reducer(state, { type: 'NOTE_DELETE', id: notes[0].id });
|
||||
|
||||
let expected = createExpectedState(notes, [], []);
|
||||
const expected = createExpectedState(notes, [], []);
|
||||
|
||||
expect(getIds(state.notes)).toEqual(getIds(expected.items));
|
||||
expect(state.selectedNoteIds).toEqual(expected.selectedIds);
|
||||
}));
|
||||
|
||||
it('should delete selected note at bottom', asyncTest(async () => {
|
||||
let folders = await createNTestFolders(1);
|
||||
let notes = await createNTestNotes(5, folders[0]);
|
||||
const folders = await createNTestFolders(1);
|
||||
const notes = await createNTestNotes(5, folders[0]);
|
||||
let state = initTestState(folders, 0, notes, [4]);
|
||||
|
||||
// test action
|
||||
state = reducer(state, { type: 'NOTE_DELETE', id: notes[4].id });
|
||||
|
||||
let expected = createExpectedState(notes, [0,1,2,3], [3]);
|
||||
const expected = createExpectedState(notes, [0,1,2,3], [3]);
|
||||
|
||||
expect(getIds(state.notes)).toEqual(getIds(expected.items));
|
||||
expect(state.selectedNoteIds).toEqual(expected.selectedIds);
|
||||
}));
|
||||
|
||||
it('should delete note when a note below is selected', asyncTest(async () => {
|
||||
let folders = await createNTestFolders(1);
|
||||
let notes = await createNTestNotes(5, folders[0]);
|
||||
const folders = await createNTestFolders(1);
|
||||
const notes = await createNTestNotes(5, folders[0]);
|
||||
let state = initTestState(folders, 0, notes, [3]);
|
||||
|
||||
// test action
|
||||
state = reducer(state, { type: 'NOTE_DELETE', id: notes[1].id });
|
||||
|
||||
let expected = createExpectedState(notes, [0,2,3,4], [3]);
|
||||
const expected = createExpectedState(notes, [0,2,3,4], [3]);
|
||||
|
||||
expect(getIds(state.notes)).toEqual(getIds(expected.items));
|
||||
expect(state.selectedNoteIds).toEqual(expected.selectedIds);
|
||||
}));
|
||||
|
||||
it('should delete note when a note above is selected', asyncTest(async () => {
|
||||
let folders = await createNTestFolders(1);
|
||||
let notes = await createNTestNotes(5, folders[0]);
|
||||
const folders = await createNTestFolders(1);
|
||||
const notes = await createNTestNotes(5, folders[0]);
|
||||
let state = initTestState(folders, 0, notes, [1]);
|
||||
|
||||
// test action
|
||||
state = reducer(state, { type: 'NOTE_DELETE', id: notes[3].id });
|
||||
|
||||
let expected = createExpectedState(notes, [0,1,2,4], [1]);
|
||||
const expected = createExpectedState(notes, [0,1,2,4], [1]);
|
||||
|
||||
expect(getIds(state.notes)).toEqual(getIds(expected.items));
|
||||
expect(state.selectedNoteIds).toEqual(expected.selectedIds);
|
||||
}));
|
||||
|
||||
it('should delete selected notes', asyncTest(async () => {
|
||||
let folders = await createNTestFolders(1);
|
||||
let notes = await createNTestNotes(5, folders[0]);
|
||||
const folders = await createNTestFolders(1);
|
||||
const notes = await createNTestNotes(5, folders[0]);
|
||||
let state = initTestState(folders, 0, notes, [1,2]);
|
||||
|
||||
// test action
|
||||
state = reducer(state, { type: 'NOTE_DELETE', id: notes[1].id });
|
||||
state = reducer(state, { type: 'NOTE_DELETE', id: notes[2].id });
|
||||
|
||||
let expected = createExpectedState(notes, [0,3,4], [3]);
|
||||
const expected = createExpectedState(notes, [0,3,4], [3]);
|
||||
|
||||
expect(getIds(state.notes)).toEqual(getIds(expected.items));
|
||||
expect(state.selectedNoteIds).toEqual(expected.selectedIds);
|
||||
}));
|
||||
|
||||
it('should delete note when a notes below it are selected', asyncTest(async () => {
|
||||
let folders = await createNTestFolders(1);
|
||||
let notes = await createNTestNotes(5, folders[0]);
|
||||
const folders = await createNTestFolders(1);
|
||||
const notes = await createNTestNotes(5, folders[0]);
|
||||
let state = initTestState(folders, 0, notes, [3,4]);
|
||||
|
||||
// test action
|
||||
state = reducer(state, { type: 'NOTE_DELETE', id: notes[1].id });
|
||||
|
||||
let expected = createExpectedState(notes, [0,2,3,4], [3,4]);
|
||||
const expected = createExpectedState(notes, [0,2,3,4], [3,4]);
|
||||
|
||||
expect(getIds(state.notes)).toEqual(getIds(expected.items));
|
||||
expect(state.selectedNoteIds).toEqual(expected.selectedIds);
|
||||
}));
|
||||
|
||||
it('should delete note when a notes above it are selected', asyncTest(async () => {
|
||||
let folders = await createNTestFolders(1);
|
||||
let notes = await createNTestNotes(5, folders[0]);
|
||||
const folders = await createNTestFolders(1);
|
||||
const notes = await createNTestNotes(5, folders[0]);
|
||||
let state = initTestState(folders, 0, notes, [1,2]);
|
||||
|
||||
// test action
|
||||
state = reducer(state, { type: 'NOTE_DELETE', id: notes[3].id });
|
||||
|
||||
let expected = createExpectedState(notes, [0,1,2,4], [1,2]);
|
||||
const expected = createExpectedState(notes, [0,1,2,4], [1,2]);
|
||||
|
||||
expect(getIds(state.notes)).toEqual(getIds(expected.items));
|
||||
expect(state.selectedNoteIds).toEqual(expected.selectedIds);
|
||||
}));
|
||||
|
||||
it('should delete notes at end', asyncTest(async () => {
|
||||
let folders = await createNTestFolders(1);
|
||||
let notes = await createNTestNotes(5, folders[0]);
|
||||
const folders = await createNTestFolders(1);
|
||||
const notes = await createNTestNotes(5, folders[0]);
|
||||
let state = initTestState(folders, 0, notes, [3,4]);
|
||||
|
||||
// test action
|
||||
state = reducer(state, { type: 'NOTE_DELETE', id: notes[3].id });
|
||||
state = reducer(state, { type: 'NOTE_DELETE', id: notes[4].id });
|
||||
|
||||
let expected = createExpectedState(notes, [0,1,2], [2]);
|
||||
const expected = createExpectedState(notes, [0,1,2], [2]);
|
||||
|
||||
expect(getIds(state.notes)).toEqual(getIds(expected.items));
|
||||
expect(state.selectedNoteIds).toEqual(expected.selectedIds);
|
||||
}));
|
||||
|
||||
it('should delete notes when non-contiguous selection', asyncTest(async () => {
|
||||
let folders = await createNTestFolders(1);
|
||||
let notes = await createNTestNotes(5, folders[0]);
|
||||
const folders = await createNTestFolders(1);
|
||||
const notes = await createNTestNotes(5, folders[0]);
|
||||
let state = initTestState(folders, 0, notes, [0,2,4]);
|
||||
|
||||
// test action
|
||||
@ -233,7 +233,7 @@ describe('Reducer', function() {
|
||||
state = reducer(state, { type: 'NOTE_DELETE', id: notes[2].id });
|
||||
state = reducer(state, { type: 'NOTE_DELETE', id: notes[4].id });
|
||||
|
||||
let expected = createExpectedState(notes, [1,3], [1]);
|
||||
const expected = createExpectedState(notes, [1,3], [1]);
|
||||
|
||||
expect(getIds(state.notes)).toEqual(getIds(expected.items));
|
||||
expect(state.selectedNoteIds).toEqual(expected.selectedIds);
|
||||
@ -241,42 +241,42 @@ describe('Reducer', function() {
|
||||
|
||||
// tests for FOLDER_DELETE
|
||||
it('should delete selected notebook', asyncTest(async () => {
|
||||
let folders = await createNTestFolders(5);
|
||||
let notes = await createNTestNotes(5, folders[0]);
|
||||
const folders = await createNTestFolders(5);
|
||||
const notes = await createNTestNotes(5, folders[0]);
|
||||
let state = initTestState(folders, 2, notes, [2]);
|
||||
|
||||
// test action
|
||||
state = reducer(state, { type: 'FOLDER_DELETE', id: folders[2].id });
|
||||
|
||||
let expected = createExpectedState(folders, [0,1,3,4], [3]);
|
||||
const expected = createExpectedState(folders, [0,1,3,4], [3]);
|
||||
|
||||
expect(getIds(state.folders)).toEqual(getIds(expected.items));
|
||||
expect(state.selectedFolderId).toEqual(expected.selectedIds[0]);
|
||||
}));
|
||||
|
||||
it('should delete notebook when a book above is selected', asyncTest(async () => {
|
||||
let folders = await createNTestFolders(5);
|
||||
let notes = await createNTestNotes(5, folders[0]);
|
||||
const folders = await createNTestFolders(5);
|
||||
const notes = await createNTestNotes(5, folders[0]);
|
||||
let state = initTestState(folders, 1, notes, [2]);
|
||||
|
||||
// test action
|
||||
state = reducer(state, { type: 'FOLDER_DELETE', id: folders[2].id });
|
||||
|
||||
let expected = createExpectedState(folders, [0,1,3,4], [1]);
|
||||
const expected = createExpectedState(folders, [0,1,3,4], [1]);
|
||||
|
||||
expect(getIds(state.folders)).toEqual(getIds(expected.items));
|
||||
expect(state.selectedFolderId).toEqual(expected.selectedIds[0]);
|
||||
}));
|
||||
|
||||
it('should delete notebook when a book below is selected', asyncTest(async () => {
|
||||
let folders = await createNTestFolders(5);
|
||||
let notes = await createNTestNotes(5, folders[0]);
|
||||
const folders = await createNTestFolders(5);
|
||||
const notes = await createNTestNotes(5, folders[0]);
|
||||
let state = initTestState(folders, 4, notes, [2]);
|
||||
|
||||
// test action
|
||||
state = reducer(state, { type: 'FOLDER_DELETE', id: folders[2].id });
|
||||
|
||||
let expected = createExpectedState(folders, [0,1,3,4], [4]);
|
||||
const expected = createExpectedState(folders, [0,1,3,4], [4]);
|
||||
|
||||
expect(getIds(state.folders)).toEqual(getIds(expected.items));
|
||||
expect(state.selectedFolderId).toEqual(expected.selectedIds[0]);
|
||||
@ -284,47 +284,47 @@ describe('Reducer', function() {
|
||||
|
||||
// tests for TAG_DELETE
|
||||
it('should delete selected tag', asyncTest(async () => {
|
||||
let tags = await createNTestTags(5);
|
||||
const tags = await createNTestTags(5);
|
||||
let state = initTestState(null, null, null, null, tags, [2]);
|
||||
|
||||
// test action
|
||||
state = reducer(state, { type: 'TAG_DELETE', id: tags[2].id });
|
||||
|
||||
let expected = createExpectedState(tags, [0,1,3,4], [3]);
|
||||
const expected = createExpectedState(tags, [0,1,3,4], [3]);
|
||||
|
||||
expect(getIds(state.tags)).toEqual(getIds(expected.items));
|
||||
expect(state.selectedTagId).toEqual(expected.selectedIds[0]);
|
||||
}));
|
||||
|
||||
it('should delete tag when a tag above is selected', asyncTest(async () => {
|
||||
let tags = await createNTestTags(5);
|
||||
const tags = await createNTestTags(5);
|
||||
let state = initTestState(null, null, null, null, tags, [2]);
|
||||
|
||||
// test action
|
||||
state = reducer(state, { type: 'TAG_DELETE', id: tags[4].id });
|
||||
|
||||
let expected = createExpectedState(tags, [0,1,2,3], [2]);
|
||||
const expected = createExpectedState(tags, [0,1,2,3], [2]);
|
||||
|
||||
expect(getIds(state.tags)).toEqual(getIds(expected.items));
|
||||
expect(state.selectedTagId).toEqual(expected.selectedIds[0]);
|
||||
}));
|
||||
|
||||
it('should delete tag when a tag below is selected', asyncTest(async () => {
|
||||
let tags = await createNTestTags(5);
|
||||
const tags = await createNTestTags(5);
|
||||
let state = initTestState(null, null, null, null, tags, [2]);
|
||||
|
||||
// test action
|
||||
state = reducer(state, { type: 'TAG_DELETE', id: tags[0].id });
|
||||
|
||||
let expected = createExpectedState(tags, [1,2,3,4], [2]);
|
||||
const expected = createExpectedState(tags, [1,2,3,4], [2]);
|
||||
|
||||
expect(getIds(state.tags)).toEqual(getIds(expected.items));
|
||||
expect(state.selectedTagId).toEqual(expected.selectedIds[0]);
|
||||
}));
|
||||
|
||||
it('should select all notes', asyncTest(async () => {
|
||||
let folders = await createNTestFolders(2);
|
||||
let notes = [];
|
||||
const folders = await createNTestFolders(2);
|
||||
const notes = [];
|
||||
for (let i = 0; i < folders.length; i++) {
|
||||
notes.push(...await createNTestNotes(3, folders[i]));
|
||||
}
|
||||
|
@ -94,7 +94,7 @@ describe('services_EncryptionService', function() {
|
||||
}));
|
||||
|
||||
it('should not upgrade master key if invalid password', asyncTest(async () => {
|
||||
let masterKey = await service.generateMasterKey('123456', {
|
||||
const masterKey = await service.generateMasterKey('123456', {
|
||||
encryptionMethod: EncryptionService.METHOD_SJCL_2,
|
||||
});
|
||||
|
||||
@ -207,7 +207,7 @@ describe('services_EncryptionService', function() {
|
||||
|
||||
await service.unloadMasterKey(masterKey);
|
||||
|
||||
let hasThrown = await checkThrowAsync(async () => await service.decryptString(cipherText));
|
||||
const hasThrown = await checkThrowAsync(async () => await service.decryptString(cipherText));
|
||||
|
||||
expect(hasThrown).toBe(true);
|
||||
}));
|
||||
@ -222,7 +222,7 @@ describe('services_EncryptionService', function() {
|
||||
let cipherText = await service.encryptString('some secret');
|
||||
cipherText += 'ABCDEFGHIJ';
|
||||
|
||||
let hasThrown = await checkThrowAsync(async () => await service.decryptString(cipherText));
|
||||
const hasThrown = await checkThrowAsync(async () => await service.decryptString(cipherText));
|
||||
|
||||
expect(hasThrown).toBe(true);
|
||||
}));
|
||||
@ -232,10 +232,10 @@ describe('services_EncryptionService', function() {
|
||||
masterKey = await MasterKey.save(masterKey);
|
||||
await service.loadMasterKey_(masterKey, '123456', true);
|
||||
|
||||
let folder = await Folder.save({ title: 'folder' });
|
||||
let note = await Note.save({ title: 'encrypted note', body: 'something', parent_id: folder.id });
|
||||
let serialized = await Note.serializeForSync(note);
|
||||
let deserialized = Note.filter(await Note.unserialize(serialized));
|
||||
const folder = await Folder.save({ title: 'folder' });
|
||||
const note = await Note.save({ title: 'encrypted note', body: 'something', parent_id: folder.id });
|
||||
const serialized = await Note.serializeForSync(note);
|
||||
const deserialized = Note.filter(await Note.unserialize(serialized));
|
||||
|
||||
// Check that required properties are not encrypted
|
||||
expect(deserialized.id).toBe(note.id);
|
||||
|
@ -59,7 +59,7 @@ describe('services_InteropService', function() {
|
||||
// Check that a new folder, with a new ID, has been created
|
||||
|
||||
expect(await Folder.count()).toBe(1);
|
||||
let folder2 = (await Folder.all())[0];
|
||||
const folder2 = (await Folder.all())[0];
|
||||
expect(folder2.id).not.toBe(folder1.id);
|
||||
expect(folder2.title).toBe(folder1.title);
|
||||
|
||||
@ -68,7 +68,7 @@ describe('services_InteropService', function() {
|
||||
// As there was already a folder with the same title, check that the new one has been renamed
|
||||
|
||||
await Folder.delete(folder2.id);
|
||||
let folder3 = (await Folder.all())[0];
|
||||
const folder3 = (await Folder.all())[0];
|
||||
expect(await Folder.count()).toBe(1);
|
||||
expect(folder3.title).not.toBe(folder2.title);
|
||||
|
||||
@ -81,7 +81,7 @@ describe('services_InteropService', function() {
|
||||
|
||||
it('should export and import folders and notes', asyncTest(async () => {
|
||||
const service = new InteropService();
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
note1 = await Note.load(note1.id);
|
||||
const filePath = `${exportDir()}/test.jex`;
|
||||
@ -95,7 +95,7 @@ describe('services_InteropService', function() {
|
||||
|
||||
expect(await Note.count()).toBe(1);
|
||||
let note2 = (await Note.all())[0];
|
||||
let folder2 = (await Folder.all())[0];
|
||||
const folder2 = (await Folder.all())[0];
|
||||
|
||||
expect(note1.parent_id).not.toBe(note2.parent_id);
|
||||
expect(note1.id).not.toBe(note2.id);
|
||||
@ -110,7 +110,7 @@ describe('services_InteropService', function() {
|
||||
await service.import({ path: filePath });
|
||||
|
||||
note2 = (await Note.all())[0];
|
||||
let note3 = (await Note.all())[1];
|
||||
const note3 = (await Note.all())[1];
|
||||
|
||||
expect(note2.id).not.toBe(note3.id);
|
||||
expect(note2.parent_id).not.toBe(note3.parent_id);
|
||||
@ -120,7 +120,7 @@ describe('services_InteropService', function() {
|
||||
|
||||
it('should export and import notes to specific folder', asyncTest(async () => {
|
||||
const service = new InteropService();
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
note1 = await Note.load(note1.id);
|
||||
const filePath = `${exportDir()}/test.jex`;
|
||||
@ -140,8 +140,8 @@ describe('services_InteropService', function() {
|
||||
it('should export and import tags', asyncTest(async () => {
|
||||
const service = new InteropService();
|
||||
const filePath = `${exportDir()}/test.jex`;
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
let tag1 = await Tag.save({ title: 'mon tag' });
|
||||
tag1 = await Tag.load(tag1.id);
|
||||
await Tag.addNote(tag1.id, note1.id);
|
||||
@ -155,8 +155,8 @@ describe('services_InteropService', function() {
|
||||
await service.import({ path: filePath });
|
||||
|
||||
expect(await Tag.count()).toBe(1);
|
||||
let tag2 = (await Tag.all())[0];
|
||||
let note2 = (await Note.all())[0];
|
||||
const tag2 = (await Tag.all())[0];
|
||||
const note2 = (await Note.all())[0];
|
||||
expect(tag1.id).not.toBe(tag2.id);
|
||||
|
||||
let fieldNames = Note.fieldNames();
|
||||
@ -180,12 +180,12 @@ describe('services_InteropService', function() {
|
||||
it('should export and import resources', asyncTest(async () => {
|
||||
const service = new InteropService();
|
||||
const filePath = `${exportDir()}/test.jex`;
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
await shim.attachFileToNote(note1, `${__dirname}/../tests/support/photo.jpg`);
|
||||
note1 = await Note.load(note1.id);
|
||||
let resourceIds = await Note.linkedResourceIds(note1.body);
|
||||
let resource1 = await Resource.load(resourceIds[0]);
|
||||
const resource1 = await Resource.load(resourceIds[0]);
|
||||
|
||||
await service.export({ path: filePath });
|
||||
|
||||
@ -195,11 +195,11 @@ describe('services_InteropService', function() {
|
||||
|
||||
expect(await Resource.count()).toBe(2);
|
||||
|
||||
let note2 = (await Note.all())[0];
|
||||
const note2 = (await Note.all())[0];
|
||||
expect(note2.body).not.toBe(note1.body);
|
||||
resourceIds = await Note.linkedResourceIds(note2.body);
|
||||
expect(resourceIds.length).toBe(1);
|
||||
let resource2 = await Resource.load(resourceIds[0]);
|
||||
const resource2 = await Resource.load(resourceIds[0]);
|
||||
expect(resource2.id).not.toBe(resource1.id);
|
||||
|
||||
let fieldNames = Note.fieldNames();
|
||||
@ -216,8 +216,8 @@ describe('services_InteropService', function() {
|
||||
it('should export and import single notes', asyncTest(async () => {
|
||||
const service = new InteropService();
|
||||
const filePath = `${exportDir()}/test.jex`;
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
|
||||
await service.export({ path: filePath, sourceNoteIds: [note1.id] });
|
||||
|
||||
@ -229,15 +229,15 @@ describe('services_InteropService', function() {
|
||||
expect(await Note.count()).toBe(1);
|
||||
expect(await Folder.count()).toBe(1);
|
||||
|
||||
let folder2 = (await Folder.all())[0];
|
||||
const folder2 = (await Folder.all())[0];
|
||||
expect(folder2.title).toBe('test');
|
||||
}));
|
||||
|
||||
it('should export and import single folders', asyncTest(async () => {
|
||||
const service = new InteropService();
|
||||
const filePath = `${exportDir()}/test.jex`;
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
|
||||
await service.export({ path: filePath, sourceFolderIds: [folder1.id] });
|
||||
|
||||
@ -249,7 +249,7 @@ describe('services_InteropService', function() {
|
||||
expect(await Note.count()).toBe(1);
|
||||
expect(await Folder.count()).toBe(1);
|
||||
|
||||
let folder2 = (await Folder.all())[0];
|
||||
const folder2 = (await Folder.all())[0];
|
||||
expect(folder2.title).toBe('folder1');
|
||||
}));
|
||||
|
||||
@ -257,11 +257,11 @@ describe('services_InteropService', function() {
|
||||
|
||||
const service = new InteropService();
|
||||
const filePath = `${exportDir()}/test.jex`;
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let folder2 = await Folder.save({ title: 'folder2', parent_id: folder1.id });
|
||||
let folder3 = await Folder.save({ title: 'folder3', parent_id: folder2.id });
|
||||
let folder4 = await Folder.save({ title: 'folder4', parent_id: folder2.id });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder4.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder2 = await Folder.save({ title: 'folder2', parent_id: folder1.id });
|
||||
const folder3 = await Folder.save({ title: 'folder3', parent_id: folder2.id });
|
||||
const folder4 = await Folder.save({ title: 'folder4', parent_id: folder2.id });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder4.id });
|
||||
|
||||
await service.export({ path: filePath, sourceFolderIds: [folder1.id] });
|
||||
|
||||
@ -276,11 +276,11 @@ describe('services_InteropService', function() {
|
||||
expect(await Note.count()).toBe(1);
|
||||
expect(await Folder.count()).toBe(4);
|
||||
|
||||
let folder1_2 = await Folder.loadByTitle('folder1');
|
||||
let folder2_2 = await Folder.loadByTitle('folder2');
|
||||
let folder3_2 = await Folder.loadByTitle('folder3');
|
||||
let folder4_2 = await Folder.loadByTitle('folder4');
|
||||
let note1_2 = await Note.loadByTitle('ma note');
|
||||
const folder1_2 = await Folder.loadByTitle('folder1');
|
||||
const folder2_2 = await Folder.loadByTitle('folder2');
|
||||
const folder3_2 = await Folder.loadByTitle('folder3');
|
||||
const folder4_2 = await Folder.loadByTitle('folder4');
|
||||
const note1_2 = await Note.loadByTitle('ma note');
|
||||
|
||||
expect(folder2_2.parent_id).toBe(folder1_2.id);
|
||||
expect(folder3_2.parent_id).toBe(folder2_2.id);
|
||||
@ -291,9 +291,9 @@ describe('services_InteropService', function() {
|
||||
it('should export and import links to notes', asyncTest(async () => {
|
||||
const service = new InteropService();
|
||||
const filePath = `${exportDir()}/test.jex`;
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
let note2 = await Note.save({ title: 'ma deuxième note', body: `Lien vers première note : ${Note.markdownTag(note1)}`, parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const note2 = await Note.save({ title: 'ma deuxième note', body: `Lien vers première note : ${Note.markdownTag(note1)}`, parent_id: folder1.id });
|
||||
|
||||
await service.export({ path: filePath, sourceFolderIds: [folder1.id] });
|
||||
|
||||
@ -306,15 +306,15 @@ describe('services_InteropService', function() {
|
||||
expect(await Note.count()).toBe(2);
|
||||
expect(await Folder.count()).toBe(1);
|
||||
|
||||
let note1_2 = await Note.loadByTitle('ma note');
|
||||
let note2_2 = await Note.loadByTitle('ma deuxième note');
|
||||
const note1_2 = await Note.loadByTitle('ma note');
|
||||
const note2_2 = await Note.loadByTitle('ma deuxième note');
|
||||
|
||||
expect(note2_2.body.indexOf(note1_2.id) >= 0).toBe(true);
|
||||
}));
|
||||
|
||||
it('should export into json format', asyncTest(async () => {
|
||||
const service = new InteropService();
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
note1 = await Note.load(note1.id);
|
||||
const filePath = exportDir();
|
||||
@ -325,8 +325,8 @@ describe('services_InteropService', function() {
|
||||
const items = [folder1, note1];
|
||||
for (let i = 0; i < items.length; i++) {
|
||||
const jsonFile = `${filePath}/${items[i].id}.json`;
|
||||
let json = await fs.readFile(jsonFile, 'utf-8');
|
||||
let obj = JSON.parse(json);
|
||||
const json = await fs.readFile(jsonFile, 'utf-8');
|
||||
const obj = JSON.parse(json);
|
||||
expect(obj.id).toBe(items[i].id);
|
||||
expect(obj.type_).toBe(items[i].type_);
|
||||
expect(obj.title).toBe(items[i].title);
|
||||
@ -336,7 +336,7 @@ describe('services_InteropService', function() {
|
||||
|
||||
it('should export selected notes in md format', asyncTest(async () => {
|
||||
const service = new InteropService();
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note11 = await Note.save({ title: 'title note11', parent_id: folder1.id });
|
||||
note11 = await Note.load(note11.id);
|
||||
let note12 = await Note.save({ title: 'title note12', parent_id: folder1.id });
|
||||
@ -365,15 +365,15 @@ describe('services_InteropService', function() {
|
||||
|
||||
it('should export MD with unicode filenames', asyncTest(async () => {
|
||||
const service = new InteropService();
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let folder2 = await Folder.save({ title: 'ジョプリン' });
|
||||
let note1 = await Note.save({ title: '生活', parent_id: folder1.id });
|
||||
let note2 = await Note.save({ title: '生活', parent_id: folder1.id });
|
||||
let note2b = await Note.save({ title: '生活', parent_id: folder1.id });
|
||||
let note3 = await Note.save({ title: '', parent_id: folder1.id });
|
||||
let note4 = await Note.save({ title: '', parent_id: folder1.id });
|
||||
let note5 = await Note.save({ title: 'salut, ça roule ?', parent_id: folder1.id });
|
||||
let note6 = await Note.save({ title: 'ジョプリン', parent_id: folder2.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder2 = await Folder.save({ title: 'ジョプリン' });
|
||||
const note1 = await Note.save({ title: '生活', parent_id: folder1.id });
|
||||
const note2 = await Note.save({ title: '生活', parent_id: folder1.id });
|
||||
const note2b = await Note.save({ title: '生活', parent_id: folder1.id });
|
||||
const note3 = await Note.save({ title: '', parent_id: folder1.id });
|
||||
const note4 = await Note.save({ title: '', parent_id: folder1.id });
|
||||
const note5 = await Note.save({ title: 'salut, ça roule ?', parent_id: folder1.id });
|
||||
const note6 = await Note.save({ title: 'ジョプリン', parent_id: folder2.id });
|
||||
|
||||
const outDir = exportDir();
|
||||
|
||||
|
@ -49,9 +49,9 @@ describe('services_InteropService_Exporter_Md', function() {
|
||||
});
|
||||
};
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'note1', parent_id: folder1.id });
|
||||
let note2 = await Note.save({ title: 'note2', parent_id: folder1.id });
|
||||
const note2 = await Note.save({ title: 'note2', parent_id: folder1.id });
|
||||
await shim.attachFileToNote(note1, `${__dirname}/../tests/support/photo.jpg`);
|
||||
note1 = await Note.load(note1.id);
|
||||
queueExportItem(BaseModel.TYPE_FOLDER, folder1.id);
|
||||
@ -59,7 +59,7 @@ describe('services_InteropService_Exporter_Md', function() {
|
||||
queueExportItem(BaseModel.TYPE_NOTE, note2);
|
||||
queueExportItem(BaseModel.TYPE_RESOURCE, (await Note.linkedResourceIds(note1.body))[0]);
|
||||
|
||||
let folder2 = await Folder.save({ title: 'folder2' });
|
||||
const folder2 = await Folder.save({ title: 'folder2' });
|
||||
let note3 = await Note.save({ title: 'note3', parent_id: folder2.id });
|
||||
await shim.attachFileToNote(note3, `${__dirname}/../tests/support/photo.jpg`);
|
||||
note3 = await Note.load(note3.id);
|
||||
@ -91,9 +91,9 @@ describe('services_InteropService_Exporter_Md', function() {
|
||||
});
|
||||
};
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'note1', parent_id: folder1.id });
|
||||
let note1_2 = await Note.save({ title: 'note1', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'note1', parent_id: folder1.id });
|
||||
const note1_2 = await Note.save({ title: 'note1', parent_id: folder1.id });
|
||||
queueExportItem(BaseModel.TYPE_FOLDER, folder1.id);
|
||||
queueExportItem(BaseModel.TYPE_NOTE, note1);
|
||||
queueExportItem(BaseModel.TYPE_NOTE, note1_2);
|
||||
@ -118,8 +118,8 @@ describe('services_InteropService_Exporter_Md', function() {
|
||||
});
|
||||
};
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'note1', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'note1', parent_id: folder1.id });
|
||||
queueExportItem(BaseModel.TYPE_FOLDER, folder1.id);
|
||||
queueExportItem(BaseModel.TYPE_NOTE, note1);
|
||||
|
||||
@ -145,23 +145,23 @@ describe('services_InteropService_Exporter_Md', function() {
|
||||
});
|
||||
};
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'note1', parent_id: folder1.id });
|
||||
await shim.attachFileToNote(note1, `${__dirname}/../tests/support/photo.jpg`);
|
||||
note1 = await Note.load(note1.id);
|
||||
queueExportItem(BaseModel.TYPE_FOLDER, folder1.id);
|
||||
queueExportItem(BaseModel.TYPE_NOTE, note1);
|
||||
queueExportItem(BaseModel.TYPE_RESOURCE, (await Note.linkedResourceIds(note1.body))[0]);
|
||||
let resource1 = await Resource.load(itemsToExport[2].itemOrId);
|
||||
const resource1 = await Resource.load(itemsToExport[2].itemOrId);
|
||||
|
||||
let folder2 = await Folder.save({ title: 'folder2', parent_id: folder1.id });
|
||||
const folder2 = await Folder.save({ title: 'folder2', parent_id: folder1.id });
|
||||
let note2 = await Note.save({ title: 'note2', parent_id: folder2.id });
|
||||
await shim.attachFileToNote(note2, `${__dirname}/../tests/support/photo.jpg`);
|
||||
note2 = await Note.load(note2.id);
|
||||
queueExportItem(BaseModel.TYPE_FOLDER, folder2.id);
|
||||
queueExportItem(BaseModel.TYPE_NOTE, note2);
|
||||
queueExportItem(BaseModel.TYPE_RESOURCE, (await Note.linkedResourceIds(note2.body))[0]);
|
||||
let resource2 = await Resource.load(itemsToExport[5].itemOrId);
|
||||
const resource2 = await Resource.load(itemsToExport[5].itemOrId);
|
||||
|
||||
await exporter.processResource(resource1, Resource.fullPath(resource1));
|
||||
await exporter.processResource(resource2, Resource.fullPath(resource2));
|
||||
@ -182,13 +182,13 @@ describe('services_InteropService_Exporter_Md', function() {
|
||||
});
|
||||
};
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
|
||||
let folder2 = await Folder.save({ title: 'folder2', parent_id: folder1.id });
|
||||
let note2 = await Note.save({ title: 'note2', parent_id: folder2.id });
|
||||
const folder2 = await Folder.save({ title: 'folder2', parent_id: folder1.id });
|
||||
const note2 = await Note.save({ title: 'note2', parent_id: folder2.id });
|
||||
queueExportItem(BaseModel.TYPE_NOTE, note2);
|
||||
|
||||
let folder3 = await Folder.save({ title: 'folder3', parent_id: folder1.id });
|
||||
const folder3 = await Folder.save({ title: 'folder3', parent_id: folder1.id });
|
||||
queueExportItem(BaseModel.TYPE_FOLDER, folder3.id);
|
||||
|
||||
await exporter.processItem(Folder, folder2);
|
||||
@ -213,18 +213,18 @@ describe('services_InteropService_Exporter_Md', function() {
|
||||
});
|
||||
};
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'note1', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'note1', parent_id: folder1.id });
|
||||
queueExportItem(BaseModel.TYPE_FOLDER, folder1.id);
|
||||
queueExportItem(BaseModel.TYPE_NOTE, note1);
|
||||
|
||||
let folder2 = await Folder.save({ title: 'folder2', parent_id: folder1.id });
|
||||
let note2 = await Note.save({ title: 'note2', parent_id: folder2.id });
|
||||
const folder2 = await Folder.save({ title: 'folder2', parent_id: folder1.id });
|
||||
const note2 = await Note.save({ title: 'note2', parent_id: folder2.id });
|
||||
queueExportItem(BaseModel.TYPE_FOLDER, folder2.id);
|
||||
queueExportItem(BaseModel.TYPE_NOTE, note2);
|
||||
|
||||
let folder3 = await Folder.save({ title: 'folder3' });
|
||||
let note3 = await Note.save({ title: 'note3', parent_id: folder3.id });
|
||||
const folder3 = await Folder.save({ title: 'folder3' });
|
||||
const note3 = await Note.save({ title: 'note3', parent_id: folder3.id });
|
||||
queueExportItem(BaseModel.TYPE_FOLDER, folder3.id);
|
||||
queueExportItem(BaseModel.TYPE_NOTE, note3);
|
||||
|
||||
@ -250,24 +250,24 @@ describe('services_InteropService_Exporter_Md', function() {
|
||||
});
|
||||
};
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'note1', parent_id: folder1.id });
|
||||
await shim.attachFileToNote(note1, `${__dirname}/../tests/support/photo.jpg`);
|
||||
note1 = await Note.load(note1.id);
|
||||
queueExportItem(BaseModel.TYPE_NOTE, note1);
|
||||
let resource1 = await Resource.load((await Note.linkedResourceIds(note1.body))[0]);
|
||||
const resource1 = await Resource.load((await Note.linkedResourceIds(note1.body))[0]);
|
||||
|
||||
let folder2 = await Folder.save({ title: 'folder2', parent_id: folder1.id });
|
||||
const folder2 = await Folder.save({ title: 'folder2', parent_id: folder1.id });
|
||||
let note2 = await Note.save({ title: 'note2', parent_id: folder2.id });
|
||||
await shim.attachFileToNote(note2, `${__dirname}/../tests/support/photo.jpg`);
|
||||
note2 = await Note.load(note2.id);
|
||||
queueExportItem(BaseModel.TYPE_NOTE, note2);
|
||||
let resource2 = await Resource.load((await Note.linkedResourceIds(note2.body))[0]);
|
||||
const resource2 = await Resource.load((await Note.linkedResourceIds(note2.body))[0]);
|
||||
|
||||
await exporter.processItem(Folder, folder1);
|
||||
await exporter.processItem(Folder, folder2);
|
||||
await exporter.prepareForProcessingItemType(BaseModel.TYPE_NOTE, itemsToExport);
|
||||
let context = {
|
||||
const context = {
|
||||
resourcePaths: {},
|
||||
};
|
||||
context.resourcePaths[resource1.id] = 'resource1.jpg';
|
||||
@ -276,8 +276,8 @@ describe('services_InteropService_Exporter_Md', function() {
|
||||
await exporter.processItem(Note, note1);
|
||||
await exporter.processItem(Note, note2);
|
||||
|
||||
let note1_body = await shim.fsDriver().readFile(`${exportDir}/${exporter.context().notePaths[note1.id]}`);
|
||||
let note2_body = await shim.fsDriver().readFile(`${exportDir}/${exporter.context().notePaths[note2.id]}`);
|
||||
const note1_body = await shim.fsDriver().readFile(`${exportDir}/${exporter.context().notePaths[note1.id]}`);
|
||||
const note2_body = await shim.fsDriver().readFile(`${exportDir}/${exporter.context().notePaths[note2.id]}`);
|
||||
|
||||
expect(note1_body).toContain('](../_resources/resource1.jpg)', 'Resource id should be replaced with a relative path.');
|
||||
expect(note2_body).toContain('](../../_resources/resource2.jpg)', 'Resource id should be replaced with a relative path.');
|
||||
@ -301,13 +301,13 @@ describe('services_InteropService_Exporter_Md', function() {
|
||||
return await Note.load(note.id);
|
||||
};
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'note1', parent_id: folder1.id });
|
||||
|
||||
let folder2 = await Folder.save({ title: 'folder2', parent_id: folder1.id });
|
||||
const folder2 = await Folder.save({ title: 'folder2', parent_id: folder1.id });
|
||||
let note2 = await Note.save({ title: 'note2', parent_id: folder2.id });
|
||||
|
||||
let folder3 = await Folder.save({ title: 'folder3' });
|
||||
const folder3 = await Folder.save({ title: 'folder3' });
|
||||
let note3 = await Note.save({ title: 'note3', parent_id: folder3.id });
|
||||
|
||||
note1 = await changeNoteBodyAndReload(note1, `# Some text \n\n [A link to note3](:/${note3.id})`);
|
||||
@ -325,9 +325,9 @@ describe('services_InteropService_Exporter_Md', function() {
|
||||
await exporter.processItem(Note, note2);
|
||||
await exporter.processItem(Note, note3);
|
||||
|
||||
let note1_body = await shim.fsDriver().readFile(`${exportDir}/${exporter.context().notePaths[note1.id]}`);
|
||||
let note2_body = await shim.fsDriver().readFile(`${exportDir}/${exporter.context().notePaths[note2.id]}`);
|
||||
let note3_body = await shim.fsDriver().readFile(`${exportDir}/${exporter.context().notePaths[note3.id]}`);
|
||||
const note1_body = await shim.fsDriver().readFile(`${exportDir}/${exporter.context().notePaths[note1.id]}`);
|
||||
const note2_body = await shim.fsDriver().readFile(`${exportDir}/${exporter.context().notePaths[note2.id]}`);
|
||||
const note3_body = await shim.fsDriver().readFile(`${exportDir}/${exporter.context().notePaths[note3.id]}`);
|
||||
|
||||
expect(note1_body).toContain('](../folder3/note3.md)', 'Note id should be replaced with a relative path.');
|
||||
expect(note2_body).toContain('](../../folder3/note3.md)', 'Resource id should be replaced with a relative path.');
|
||||
@ -347,9 +347,9 @@ describe('services_InteropService_Exporter_Md', function() {
|
||||
});
|
||||
};
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder with space1' });
|
||||
let note1 = await Note.save({ title: 'note1 name with space', parent_id: folder1.id });
|
||||
let note2 = await Note.save({ title: 'note2', parent_id: folder1.id, body: `[link](:/${note1.id})` });
|
||||
const folder1 = await Folder.save({ title: 'folder with space1' });
|
||||
const note1 = await Note.save({ title: 'note1 name with space', parent_id: folder1.id });
|
||||
const note2 = await Note.save({ title: 'note2', parent_id: folder1.id, body: `[link](:/${note1.id})` });
|
||||
queueExportItem(BaseModel.TYPE_NOTE, note1);
|
||||
queueExportItem(BaseModel.TYPE_NOTE, note2);
|
||||
|
||||
@ -358,7 +358,7 @@ describe('services_InteropService_Exporter_Md', function() {
|
||||
await exporter.processItem(Note, note1);
|
||||
await exporter.processItem(Note, note2);
|
||||
|
||||
let note2_body = await shim.fsDriver().readFile(`${exportDir}/${exporter.context().notePaths[note2.id]}`);
|
||||
const note2_body = await shim.fsDriver().readFile(`${exportDir}/${exporter.context().notePaths[note2.id]}`);
|
||||
expect(note2_body).toContain('[link](../folder%20with%20space1/note1%20name%20with%20space.md)', 'Whitespace in URL should be encoded');
|
||||
}));
|
||||
});
|
||||
|
@ -48,10 +48,10 @@ describe('services_ResourceService', function() {
|
||||
it('should delete orphaned resources', asyncTest(async () => {
|
||||
const service = new ResourceService();
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
note1 = await shim.attachFileToNote(note1, `${__dirname}/../tests/support/photo.jpg`);
|
||||
let resource1 = (await Resource.all())[0];
|
||||
const resource1 = (await Resource.all())[0];
|
||||
const resourcePath = Resource.fullPath(resource1);
|
||||
|
||||
await service.indexNoteResources();
|
||||
@ -79,11 +79,11 @@ describe('services_ResourceService', function() {
|
||||
it('should not delete resource if still associated with at least one note', asyncTest(async () => {
|
||||
const service = new ResourceService();
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
let note2 = await Note.save({ title: 'ma deuxième note', parent_id: folder1.id });
|
||||
const note2 = await Note.save({ title: 'ma deuxième note', parent_id: folder1.id });
|
||||
note1 = await shim.attachFileToNote(note1, `${__dirname}/../tests/support/photo.jpg`);
|
||||
let resource1 = (await Resource.all())[0];
|
||||
const resource1 = (await Resource.all())[0];
|
||||
|
||||
await service.indexNoteResources();
|
||||
|
||||
@ -113,10 +113,10 @@ describe('services_ResourceService', function() {
|
||||
it('should not delete resource if it is used in an IMG tag', asyncTest(async () => {
|
||||
const service = new ResourceService();
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
note1 = await shim.attachFileToNote(note1, `${__dirname}/../tests/support/photo.jpg`);
|
||||
let resource1 = (await Resource.all())[0];
|
||||
const resource1 = (await Resource.all())[0];
|
||||
|
||||
await service.indexNoteResources();
|
||||
|
||||
@ -132,10 +132,10 @@ describe('services_ResourceService', function() {
|
||||
it('should not process twice the same change', asyncTest(async () => {
|
||||
const service = new ResourceService();
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
note1 = await shim.attachFileToNote(note1, `${__dirname}/../tests/support/photo.jpg`);
|
||||
let resource1 = (await Resource.all())[0];
|
||||
const resource1 = (await Resource.all())[0];
|
||||
|
||||
await service.indexNoteResources();
|
||||
|
||||
@ -169,8 +169,8 @@ describe('services_ResourceService', function() {
|
||||
const masterKey = await loadEncryptionMasterKey();
|
||||
await encryptionService().enableEncryption(masterKey, '123456');
|
||||
await encryptionService().loadMasterKeysFromSettings();
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
await shim.attachFileToNote(note1, `${__dirname}/../tests/support/photo.jpg`); // R1
|
||||
await resourceService().indexNoteResources();
|
||||
await synchronizer().start();
|
||||
@ -199,7 +199,7 @@ describe('services_ResourceService', function() {
|
||||
it('should double-check if the resource is still linked before deleting it', asyncTest(async () => {
|
||||
SearchEngine.instance().setDb(db()); // /!\ Note that we use the global search engine here, which we shouldn't but will work for now
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
note1 = await shim.attachFileToNote(note1, `${__dirname}/../tests/support/photo.jpg`);
|
||||
await resourceService().indexNoteResources();
|
||||
|
@ -1,4 +1,5 @@
|
||||
/* eslint-disable no-unused-vars */
|
||||
/* eslint prefer-const: 0*/
|
||||
|
||||
require('app-module-path').addPath(__dirname);
|
||||
|
||||
|
@ -37,26 +37,26 @@ describe('services_rest_Api', function() {
|
||||
}));
|
||||
|
||||
it('should get folders', asyncTest(async () => {
|
||||
let f1 = await Folder.save({ title: 'mon carnet' });
|
||||
const f1 = await Folder.save({ title: 'mon carnet' });
|
||||
const response = await api.route('GET', 'folders');
|
||||
expect(response.length).toBe(1);
|
||||
}));
|
||||
|
||||
it('should update folders', asyncTest(async () => {
|
||||
let f1 = await Folder.save({ title: 'mon carnet' });
|
||||
const f1 = await Folder.save({ title: 'mon carnet' });
|
||||
const response = await api.route('PUT', `folders/${f1.id}`, null, JSON.stringify({
|
||||
title: 'modifié',
|
||||
}));
|
||||
|
||||
let f1b = await Folder.load(f1.id);
|
||||
const f1b = await Folder.load(f1.id);
|
||||
expect(f1b.title).toBe('modifié');
|
||||
}));
|
||||
|
||||
it('should delete folders', asyncTest(async () => {
|
||||
let f1 = await Folder.save({ title: 'mon carnet' });
|
||||
const f1 = await Folder.save({ title: 'mon carnet' });
|
||||
await api.route('DELETE', `folders/${f1.id}`);
|
||||
|
||||
let f1b = await Folder.load(f1.id);
|
||||
const f1b = await Folder.load(f1.id);
|
||||
expect(!f1b).toBe(true);
|
||||
}));
|
||||
|
||||
@ -67,13 +67,13 @@ describe('services_rest_Api', function() {
|
||||
|
||||
expect(!!response.id).toBe(true);
|
||||
|
||||
let f = await Folder.all();
|
||||
const f = await Folder.all();
|
||||
expect(f.length).toBe(1);
|
||||
expect(f[0].title).toBe('from api');
|
||||
}));
|
||||
|
||||
it('should get one folder', asyncTest(async () => {
|
||||
let f1 = await Folder.save({ title: 'mon carnet' });
|
||||
const f1 = await Folder.save({ title: 'mon carnet' });
|
||||
const response = await api.route('GET', `folders/${f1.id}`);
|
||||
expect(response.id).toBe(f1.id);
|
||||
|
||||
@ -82,7 +82,7 @@ describe('services_rest_Api', function() {
|
||||
}));
|
||||
|
||||
it('should get the folder notes', asyncTest(async () => {
|
||||
let f1 = await Folder.save({ title: 'mon carnet' });
|
||||
const f1 = await Folder.save({ title: 'mon carnet' });
|
||||
const response2 = await api.route('GET', `folders/${f1.id}/notes`);
|
||||
expect(response2.length).toBe(0);
|
||||
|
||||
|
@ -27,8 +27,8 @@ process.on('unhandledRejection', (reason, p) => {
|
||||
jasmine.DEFAULT_TIMEOUT_INTERVAL = 60000 + 30000; // The first test is slow because the database needs to be built
|
||||
|
||||
async function allNotesFolders() {
|
||||
let folders = await Folder.all();
|
||||
let notes = await Note.all();
|
||||
const folders = await Folder.all();
|
||||
const notes = await Note.all();
|
||||
return folders.concat(notes);
|
||||
}
|
||||
|
||||
@ -66,9 +66,9 @@ async function localNotesFoldersSameAsRemote(locals, expect) {
|
||||
expect(locals.length).toBe(nf.length);
|
||||
|
||||
for (let i = 0; i < locals.length; i++) {
|
||||
let dbItem = locals[i];
|
||||
let path = BaseItem.systemPath(dbItem);
|
||||
let remote = await fileApi().stat(path);
|
||||
const dbItem = locals[i];
|
||||
const path = BaseItem.systemPath(dbItem);
|
||||
const remote = await fileApi().stat(path);
|
||||
|
||||
expect(!!remote).toBe(true);
|
||||
if (!remote) continue;
|
||||
@ -101,10 +101,10 @@ describe('synchronizer', function() {
|
||||
});
|
||||
|
||||
it('should create remote items', asyncTest(async () => {
|
||||
let folder = await Folder.save({ title: 'folder1' });
|
||||
const folder = await Folder.save({ title: 'folder1' });
|
||||
await Note.save({ title: 'un', parent_id: folder.id });
|
||||
|
||||
let all = await allNotesFolders();
|
||||
const all = await allNotesFolders();
|
||||
|
||||
await synchronizer().start();
|
||||
|
||||
@ -112,20 +112,20 @@ describe('synchronizer', function() {
|
||||
}));
|
||||
|
||||
it('should update remote items', asyncTest(async () => {
|
||||
let folder = await Folder.save({ title: 'folder1' });
|
||||
let note = await Note.save({ title: 'un', parent_id: folder.id });
|
||||
const folder = await Folder.save({ title: 'folder1' });
|
||||
const note = await Note.save({ title: 'un', parent_id: folder.id });
|
||||
await synchronizer().start();
|
||||
|
||||
await Note.save({ title: 'un UPDATE', id: note.id });
|
||||
|
||||
let all = await allNotesFolders();
|
||||
const all = await allNotesFolders();
|
||||
await synchronizer().start();
|
||||
|
||||
await localNotesFoldersSameAsRemote(all, expect);
|
||||
}));
|
||||
|
||||
it('should create local items', asyncTest(async () => {
|
||||
let folder = await Folder.save({ title: 'folder1' });
|
||||
const folder = await Folder.save({ title: 'folder1' });
|
||||
await Note.save({ title: 'un', parent_id: folder.id });
|
||||
await synchronizer().start();
|
||||
|
||||
@ -133,14 +133,14 @@ describe('synchronizer', function() {
|
||||
|
||||
await synchronizer().start();
|
||||
|
||||
let all = await allNotesFolders();
|
||||
const all = await allNotesFolders();
|
||||
|
||||
await localNotesFoldersSameAsRemote(all, expect);
|
||||
}));
|
||||
|
||||
it('should update local items', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'un', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'un', parent_id: folder1.id });
|
||||
await synchronizer().start();
|
||||
|
||||
await switchClient(2);
|
||||
@ -160,14 +160,14 @@ describe('synchronizer', function() {
|
||||
|
||||
await synchronizer().start();
|
||||
|
||||
let all = await allNotesFolders();
|
||||
const all = await allNotesFolders();
|
||||
|
||||
await localNotesFoldersSameAsRemote(all, expect);
|
||||
}));
|
||||
|
||||
it('should resolve note conflicts', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'un', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'un', parent_id: folder1.id });
|
||||
await synchronizer().start();
|
||||
|
||||
await switchClient(2);
|
||||
@ -186,29 +186,29 @@ describe('synchronizer', function() {
|
||||
await Note.save(note2conf);
|
||||
note2conf = await Note.load(note1.id);
|
||||
await synchronizer().start();
|
||||
let conflictedNotes = await Note.conflictedNotes();
|
||||
const conflictedNotes = await Note.conflictedNotes();
|
||||
expect(conflictedNotes.length).toBe(1);
|
||||
|
||||
// Other than the id (since the conflicted note is a duplicate), and the is_conflict property
|
||||
// the conflicted and original note must be the same in every way, to make sure no data has been lost.
|
||||
let conflictedNote = conflictedNotes[0];
|
||||
const conflictedNote = conflictedNotes[0];
|
||||
expect(conflictedNote.id == note2conf.id).toBe(false);
|
||||
for (let n in conflictedNote) {
|
||||
for (const n in conflictedNote) {
|
||||
if (!conflictedNote.hasOwnProperty(n)) continue;
|
||||
if (n == 'id' || n == 'is_conflict') continue;
|
||||
expect(conflictedNote[n]).toBe(note2conf[n], `Property: ${n}`);
|
||||
}
|
||||
|
||||
let noteUpdatedFromRemote = await Note.load(note1.id);
|
||||
for (let n in noteUpdatedFromRemote) {
|
||||
const noteUpdatedFromRemote = await Note.load(note1.id);
|
||||
for (const n in noteUpdatedFromRemote) {
|
||||
if (!noteUpdatedFromRemote.hasOwnProperty(n)) continue;
|
||||
expect(noteUpdatedFromRemote[n]).toBe(note2[n], `Property: ${n}`);
|
||||
}
|
||||
}));
|
||||
|
||||
it('should resolve folders conflicts', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'un', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'un', parent_id: folder1.id });
|
||||
await synchronizer().start();
|
||||
|
||||
await switchClient(2); // ----------------------------------
|
||||
@ -235,13 +235,13 @@ describe('synchronizer', function() {
|
||||
|
||||
await synchronizer().start();
|
||||
|
||||
let folder1_final = await Folder.load(folder1.id);
|
||||
const folder1_final = await Folder.load(folder1.id);
|
||||
expect(folder1_final.title).toBe(folder1_modRemote.title);
|
||||
}));
|
||||
|
||||
it('should delete remote notes', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'un', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'un', parent_id: folder1.id });
|
||||
await synchronizer().start();
|
||||
|
||||
await switchClient(2);
|
||||
@ -258,13 +258,13 @@ describe('synchronizer', function() {
|
||||
expect(remotes.length).toBe(1);
|
||||
expect(remotes[0].id).toBe(folder1.id);
|
||||
|
||||
let deletedItems = await BaseItem.deletedItems(syncTargetId());
|
||||
const deletedItems = await BaseItem.deletedItems(syncTargetId());
|
||||
expect(deletedItems.length).toBe(0);
|
||||
}));
|
||||
|
||||
it('should not created deleted_items entries for items deleted via sync', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'un', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'un', parent_id: folder1.id });
|
||||
await synchronizer().start();
|
||||
|
||||
await switchClient(2);
|
||||
@ -276,7 +276,7 @@ describe('synchronizer', function() {
|
||||
await switchClient(1);
|
||||
|
||||
await synchronizer().start();
|
||||
let deletedItems = await BaseItem.deletedItems(syncTargetId());
|
||||
const deletedItems = await BaseItem.deletedItems(syncTargetId());
|
||||
expect(deletedItems.length).toBe(0);
|
||||
}));
|
||||
|
||||
@ -285,9 +285,9 @@ describe('synchronizer', function() {
|
||||
// property of the basicDelta() function is cleared properly at the end of a sync operation. If it is not cleared
|
||||
// it means items will no longer be deleted locally via sync.
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'un', parent_id: folder1.id });
|
||||
let note2 = await Note.save({ title: 'deux', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'un', parent_id: folder1.id });
|
||||
const note2 = await Note.save({ title: 'deux', parent_id: folder1.id });
|
||||
let context1 = await synchronizer().start();
|
||||
|
||||
await switchClient(2);
|
||||
@ -299,17 +299,17 @@ describe('synchronizer', function() {
|
||||
await switchClient(1);
|
||||
|
||||
context1 = await synchronizer().start({ context: context1 });
|
||||
let items = await allNotesFolders();
|
||||
const items = await allNotesFolders();
|
||||
expect(items.length).toBe(2);
|
||||
let deletedItems = await BaseItem.deletedItems(syncTargetId());
|
||||
const deletedItems = await BaseItem.deletedItems(syncTargetId());
|
||||
expect(deletedItems.length).toBe(0);
|
||||
await Note.delete(note2.id);
|
||||
context1 = await synchronizer().start({ context: context1 });
|
||||
}));
|
||||
|
||||
it('should delete remote folder', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let folder2 = await Folder.save({ title: 'folder2' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder2 = await Folder.save({ title: 'folder2' });
|
||||
await synchronizer().start();
|
||||
|
||||
await switchClient(2);
|
||||
@ -322,30 +322,30 @@ describe('synchronizer', function() {
|
||||
|
||||
await synchronizer().start();
|
||||
|
||||
let all = await allNotesFolders();
|
||||
const all = await allNotesFolders();
|
||||
await localNotesFoldersSameAsRemote(all, expect);
|
||||
}));
|
||||
|
||||
it('should delete local folder', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let folder2 = await Folder.save({ title: 'folder2' });
|
||||
let context1 = await synchronizer().start();
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder2 = await Folder.save({ title: 'folder2' });
|
||||
const context1 = await synchronizer().start();
|
||||
|
||||
await switchClient(2);
|
||||
|
||||
let context2 = await synchronizer().start();
|
||||
const context2 = await synchronizer().start();
|
||||
await Folder.delete(folder2.id);
|
||||
await synchronizer().start({ context: context2 });
|
||||
|
||||
await switchClient(1);
|
||||
|
||||
await synchronizer().start({ context: context1 });
|
||||
let items = await allNotesFolders();
|
||||
const items = await allNotesFolders();
|
||||
await localNotesFoldersSameAsRemote(items, expect);
|
||||
}));
|
||||
|
||||
it('should resolve conflict if remote folder has been deleted, but note has been added to folder locally', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
await synchronizer().start();
|
||||
|
||||
await switchClient(2);
|
||||
@ -356,17 +356,17 @@ describe('synchronizer', function() {
|
||||
|
||||
await switchClient(1);
|
||||
|
||||
let note = await Note.save({ title: 'note1', parent_id: folder1.id });
|
||||
const note = await Note.save({ title: 'note1', parent_id: folder1.id });
|
||||
await synchronizer().start();
|
||||
let items = await allNotesFolders();
|
||||
const items = await allNotesFolders();
|
||||
expect(items.length).toBe(1);
|
||||
expect(items[0].title).toBe('note1');
|
||||
expect(items[0].is_conflict).toBe(1);
|
||||
}));
|
||||
|
||||
it('should resolve conflict if note has been deleted remotely and locally', asyncTest(async () => {
|
||||
let folder = await Folder.save({ title: 'folder' });
|
||||
let note = await Note.save({ title: 'note', parent_id: folder.title });
|
||||
const folder = await Folder.save({ title: 'folder' });
|
||||
const note = await Note.save({ title: 'note', parent_id: folder.title });
|
||||
await synchronizer().start();
|
||||
|
||||
await switchClient(2);
|
||||
@ -380,7 +380,7 @@ describe('synchronizer', function() {
|
||||
await Note.delete(note.id);
|
||||
await synchronizer().start();
|
||||
|
||||
let items = await allNotesFolders();
|
||||
const items = await allNotesFolders();
|
||||
expect(items.length).toBe(1);
|
||||
expect(items[0].title).toBe('folder');
|
||||
|
||||
@ -391,8 +391,8 @@ describe('synchronizer', function() {
|
||||
// If client1 and 2 have two folders, client 1 deletes item 1 and client
|
||||
// 2 deletes item 2, they should both end up with no items after sync.
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let folder2 = await Folder.save({ title: 'folder2' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder2 = await Folder.save({ title: 'folder2' });
|
||||
await synchronizer().start();
|
||||
|
||||
await switchClient(2);
|
||||
@ -413,21 +413,21 @@ describe('synchronizer', function() {
|
||||
|
||||
await synchronizer().start();
|
||||
|
||||
let items2 = await allNotesFolders();
|
||||
const items2 = await allNotesFolders();
|
||||
|
||||
await switchClient(1);
|
||||
|
||||
await synchronizer().start();
|
||||
|
||||
let items1 = await allNotesFolders();
|
||||
const items1 = await allNotesFolders();
|
||||
|
||||
expect(items1.length).toBe(0);
|
||||
expect(items1.length).toBe(items2.length);
|
||||
}));
|
||||
|
||||
it('should handle conflict when remote note is deleted then local note is modified', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'un', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'un', parent_id: folder1.id });
|
||||
await synchronizer().start();
|
||||
|
||||
await switchClient(2);
|
||||
@ -442,25 +442,25 @@ describe('synchronizer', function() {
|
||||
|
||||
await switchClient(1);
|
||||
|
||||
let newTitle = 'Modified after having been deleted';
|
||||
const newTitle = 'Modified after having been deleted';
|
||||
await Note.save({ id: note1.id, title: newTitle });
|
||||
|
||||
await synchronizer().start();
|
||||
|
||||
let conflictedNotes = await Note.conflictedNotes();
|
||||
const conflictedNotes = await Note.conflictedNotes();
|
||||
|
||||
expect(conflictedNotes.length).toBe(1);
|
||||
expect(conflictedNotes[0].title).toBe(newTitle);
|
||||
|
||||
let unconflictedNotes = await Note.unconflictedNotes();
|
||||
const unconflictedNotes = await Note.unconflictedNotes();
|
||||
|
||||
expect(unconflictedNotes.length).toBe(0);
|
||||
}));
|
||||
|
||||
it('should handle conflict when remote folder is deleted then local folder is renamed', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let folder2 = await Folder.save({ title: 'folder2' });
|
||||
let note1 = await Note.save({ title: 'un', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder2 = await Folder.save({ title: 'folder2' });
|
||||
const note1 = await Note.save({ title: 'un', parent_id: folder1.id });
|
||||
await synchronizer().start();
|
||||
|
||||
await switchClient(2);
|
||||
@ -477,18 +477,18 @@ describe('synchronizer', function() {
|
||||
|
||||
await sleep(0.1);
|
||||
|
||||
let newTitle = 'Modified after having been deleted';
|
||||
const newTitle = 'Modified after having been deleted';
|
||||
await Folder.save({ id: folder1.id, title: newTitle });
|
||||
|
||||
await synchronizer().start();
|
||||
|
||||
let items = await allNotesFolders();
|
||||
const items = await allNotesFolders();
|
||||
|
||||
expect(items.length).toBe(1);
|
||||
}));
|
||||
|
||||
it('should allow duplicate folder titles', asyncTest(async () => {
|
||||
let localF1 = await Folder.save({ title: 'folder' });
|
||||
const localF1 = await Folder.save({ title: 'folder' });
|
||||
|
||||
await switchClient(2);
|
||||
|
||||
@ -501,7 +501,7 @@ describe('synchronizer', function() {
|
||||
|
||||
await synchronizer().start();
|
||||
|
||||
let localF2 = await Folder.load(remoteF2.id);
|
||||
const localF2 = await Folder.load(remoteF2.id);
|
||||
|
||||
expect(localF2.title == remoteF2.title).toBe(true);
|
||||
|
||||
@ -528,10 +528,10 @@ describe('synchronizer', function() {
|
||||
masterKey = await loadEncryptionMasterKey();
|
||||
}
|
||||
|
||||
let f1 = await Folder.save({ title: 'folder' });
|
||||
let n1 = await Note.save({ title: 'mynote' });
|
||||
let n2 = await Note.save({ title: 'mynote2' });
|
||||
let tag = await Tag.save({ title: 'mytag' });
|
||||
const f1 = await Folder.save({ title: 'folder' });
|
||||
const n1 = await Note.save({ title: 'mynote' });
|
||||
const n2 = await Note.save({ title: 'mynote2' });
|
||||
const tag = await Tag.save({ title: 'mytag' });
|
||||
let context1 = await synchronizer().start();
|
||||
|
||||
await switchClient(2);
|
||||
@ -540,10 +540,10 @@ describe('synchronizer', function() {
|
||||
if (withEncryption) {
|
||||
const masterKey_2 = await MasterKey.load(masterKey.id);
|
||||
await encryptionService().loadMasterKey_(masterKey_2, '123456', true);
|
||||
let t = await Tag.load(tag.id);
|
||||
const t = await Tag.load(tag.id);
|
||||
await Tag.decrypt(t);
|
||||
}
|
||||
let remoteTag = await Tag.loadByTitle(tag.title);
|
||||
const remoteTag = await Tag.loadByTitle(tag.title);
|
||||
expect(!!remoteTag).toBe(true);
|
||||
expect(remoteTag.id).toBe(tag.id);
|
||||
await Tag.addNote(remoteTag.id, n1.id);
|
||||
@ -579,22 +579,22 @@ describe('synchronizer', function() {
|
||||
}));
|
||||
|
||||
it('should not sync notes with conflicts', asyncTest(async () => {
|
||||
let f1 = await Folder.save({ title: 'folder' });
|
||||
let n1 = await Note.save({ title: 'mynote', parent_id: f1.id, is_conflict: 1 });
|
||||
const f1 = await Folder.save({ title: 'folder' });
|
||||
const n1 = await Note.save({ title: 'mynote', parent_id: f1.id, is_conflict: 1 });
|
||||
await synchronizer().start();
|
||||
|
||||
await switchClient(2);
|
||||
|
||||
await synchronizer().start();
|
||||
let notes = await Note.all();
|
||||
let folders = await Folder.all();
|
||||
const notes = await Note.all();
|
||||
const folders = await Folder.all();
|
||||
expect(notes.length).toBe(0);
|
||||
expect(folders.length).toBe(1);
|
||||
}));
|
||||
|
||||
it('should not try to delete on remote conflicted notes that have been deleted', asyncTest(async () => {
|
||||
let f1 = await Folder.save({ title: 'folder' });
|
||||
let n1 = await Note.save({ title: 'mynote', parent_id: f1.id });
|
||||
const f1 = await Folder.save({ title: 'folder' });
|
||||
const n1 = await Note.save({ title: 'mynote', parent_id: f1.id });
|
||||
await synchronizer().start();
|
||||
|
||||
await switchClient(2);
|
||||
@ -613,8 +613,8 @@ describe('synchronizer', function() {
|
||||
await loadEncryptionMasterKey();
|
||||
}
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'un', is_todo: 1, parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'un', is_todo: 1, parent_id: folder1.id });
|
||||
await synchronizer().start();
|
||||
|
||||
await switchClient(2);
|
||||
@ -625,7 +625,7 @@ describe('synchronizer', function() {
|
||||
await decryptionWorker().start();
|
||||
}
|
||||
let note2 = await Note.load(note1.id);
|
||||
note2.todo_completed = time.unixMs()-1;
|
||||
note2.todo_completed = time.unixMs() - 1;
|
||||
await Note.save(note2);
|
||||
note2 = await Note.load(note2.id);
|
||||
await synchronizer().start();
|
||||
@ -646,10 +646,10 @@ describe('synchronizer', function() {
|
||||
// but in practice it doesn't matter, we can just take the date when the
|
||||
// todo was marked as "done" the first time.
|
||||
|
||||
let conflictedNotes = await Note.conflictedNotes();
|
||||
const conflictedNotes = await Note.conflictedNotes();
|
||||
expect(conflictedNotes.length).toBe(0);
|
||||
|
||||
let notes = await Note.all();
|
||||
const notes = await Note.all();
|
||||
expect(notes.length).toBe(1);
|
||||
expect(notes[0].id).toBe(note1.id);
|
||||
expect(notes[0].todo_completed).toBe(note2.todo_completed);
|
||||
@ -658,10 +658,10 @@ describe('synchronizer', function() {
|
||||
// smart conflict resolving since we don't know the content, so in that
|
||||
// case it's handled as a regular conflict.
|
||||
|
||||
let conflictedNotes = await Note.conflictedNotes();
|
||||
const conflictedNotes = await Note.conflictedNotes();
|
||||
expect(conflictedNotes.length).toBe(1);
|
||||
|
||||
let notes = await Note.all();
|
||||
const notes = await Note.all();
|
||||
expect(notes.length).toBe(2);
|
||||
}
|
||||
}
|
||||
@ -675,14 +675,14 @@ describe('synchronizer', function() {
|
||||
}));
|
||||
|
||||
it('items should be downloaded again when user cancels in the middle of delta operation', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'un', is_todo: 1, parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'un', is_todo: 1, parent_id: folder1.id });
|
||||
await synchronizer().start();
|
||||
|
||||
await switchClient(2);
|
||||
|
||||
synchronizer().testingHooks_ = ['cancelDeltaLoop2'];
|
||||
let context = await synchronizer().start();
|
||||
const context = await synchronizer().start();
|
||||
let notes = await Note.all();
|
||||
expect(notes.length).toBe(0);
|
||||
|
||||
@ -693,8 +693,8 @@ describe('synchronizer', function() {
|
||||
}));
|
||||
|
||||
it('should skip items that cannot be synced', asyncTest(async () => {
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'un', is_todo: 1, parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'un', is_todo: 1, parent_id: folder1.id });
|
||||
const noteId = note1.id;
|
||||
await synchronizer().start();
|
||||
let disabledItems = await BaseItem.syncDisabledItems(syncTargetId());
|
||||
@ -708,7 +708,7 @@ describe('synchronizer', function() {
|
||||
await switchClient(2);
|
||||
|
||||
await synchronizer().start();
|
||||
let notes = await Note.all();
|
||||
const notes = await Note.all();
|
||||
expect(notes.length).toBe(1);
|
||||
expect(notes[0].title).toBe('un');
|
||||
|
||||
@ -721,7 +721,7 @@ describe('synchronizer', function() {
|
||||
it('notes and folders should get encrypted when encryption is enabled', asyncTest(async () => {
|
||||
Setting.setValue('encryption.enabled', true);
|
||||
const masterKey = await loadEncryptionMasterKey();
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'un', body: 'to be encrypted', parent_id: folder1.id });
|
||||
await synchronizer().start();
|
||||
// After synchronisation, remote items should be encrypted but local ones remain plain text
|
||||
@ -733,7 +733,7 @@ describe('synchronizer', function() {
|
||||
await synchronizer().start();
|
||||
let folder1_2 = await Folder.load(folder1.id);
|
||||
let note1_2 = await Note.load(note1.id);
|
||||
let masterKey_2 = await MasterKey.load(masterKey.id);
|
||||
const masterKey_2 = await MasterKey.load(masterKey.id);
|
||||
// On this side however it should be received encrypted
|
||||
expect(!note1_2.title).toBe(true);
|
||||
expect(!folder1_2.title).toBe(true);
|
||||
@ -820,7 +820,7 @@ describe('synchronizer', function() {
|
||||
|
||||
it('should encrypt existing notes too when enabling E2EE', asyncTest(async () => {
|
||||
// First create a folder, without encryption enabled, and sync it
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
await synchronizer().start();
|
||||
let files = await fileApi().list();
|
||||
let content = await fileApi().get(files.items[0].path);
|
||||
@ -848,18 +848,18 @@ describe('synchronizer', function() {
|
||||
it('should sync resources', asyncTest(async () => {
|
||||
while (insideBeforeEach) await time.msleep(500);
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
await shim.attachFileToNote(note1, `${__dirname}/../tests/support/photo.jpg`);
|
||||
let resource1 = (await Resource.all())[0];
|
||||
let resourcePath1 = Resource.fullPath(resource1);
|
||||
const resource1 = (await Resource.all())[0];
|
||||
const resourcePath1 = Resource.fullPath(resource1);
|
||||
await synchronizer().start();
|
||||
expect((await remoteNotesFoldersResources()).length).toBe(3);
|
||||
|
||||
await switchClient(2);
|
||||
|
||||
await synchronizer().start();
|
||||
let allResources = await Resource.all();
|
||||
const allResources = await Resource.all();
|
||||
expect(allResources.length).toBe(1);
|
||||
let resource1_2 = allResources[0];
|
||||
let ls = await Resource.localState(resource1_2);
|
||||
@ -874,18 +874,18 @@ describe('synchronizer', function() {
|
||||
ls = await Resource.localState(resource1_2);
|
||||
expect(ls.fetch_status).toBe(Resource.FETCH_STATUS_DONE);
|
||||
|
||||
let resourcePath1_2 = Resource.fullPath(resource1_2);
|
||||
const resourcePath1_2 = Resource.fullPath(resource1_2);
|
||||
expect(fileContentEqual(resourcePath1, resourcePath1_2)).toBe(true);
|
||||
}));
|
||||
|
||||
it('should handle resource download errors', asyncTest(async () => {
|
||||
while (insideBeforeEach) await time.msleep(500);
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
await shim.attachFileToNote(note1, `${__dirname}/../tests/support/photo.jpg`);
|
||||
let resource1 = (await Resource.all())[0];
|
||||
let resourcePath1 = Resource.fullPath(resource1);
|
||||
const resourcePath1 = Resource.fullPath(resource1);
|
||||
await synchronizer().start();
|
||||
|
||||
await switchClient(2);
|
||||
@ -902,7 +902,7 @@ describe('synchronizer', function() {
|
||||
await fetcher.waitForAllFinished();
|
||||
|
||||
resource1 = await Resource.load(resource1.id);
|
||||
let ls = await Resource.localState(resource1);
|
||||
const ls = await Resource.localState(resource1);
|
||||
expect(ls.fetch_status).toBe(Resource.FETCH_STATUS_ERROR);
|
||||
expect(ls.fetch_error).toBe('did not work');
|
||||
}));
|
||||
@ -910,8 +910,8 @@ describe('synchronizer', function() {
|
||||
it('should set the resource file size if it is missing', asyncTest(async () => {
|
||||
while (insideBeforeEach) await time.msleep(500);
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
await shim.attachFileToNote(note1, `${__dirname}/../tests/support/photo.jpg`);
|
||||
await synchronizer().start();
|
||||
|
||||
@ -933,11 +933,11 @@ describe('synchronizer', function() {
|
||||
it('should delete resources', asyncTest(async () => {
|
||||
while (insideBeforeEach) await time.msleep(500);
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
await shim.attachFileToNote(note1, `${__dirname}/../tests/support/photo.jpg`);
|
||||
let resource1 = (await Resource.all())[0];
|
||||
let resourcePath1 = Resource.fullPath(resource1);
|
||||
const resource1 = (await Resource.all())[0];
|
||||
const resourcePath1 = Resource.fullPath(resource1);
|
||||
await synchronizer().start();
|
||||
|
||||
await switchClient(2);
|
||||
@ -945,7 +945,7 @@ describe('synchronizer', function() {
|
||||
await synchronizer().start();
|
||||
let allResources = await Resource.all();
|
||||
expect(allResources.length).toBe(1);
|
||||
let all = await fileApi().list();
|
||||
const all = await fileApi().list();
|
||||
expect((await remoteNotesFoldersResources()).length).toBe(3);
|
||||
await Resource.delete(resource1.id);
|
||||
await synchronizer().start();
|
||||
@ -967,11 +967,11 @@ describe('synchronizer', function() {
|
||||
Setting.setValue('encryption.enabled', true);
|
||||
const masterKey = await loadEncryptionMasterKey();
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
await shim.attachFileToNote(note1, `${__dirname}/../tests/support/photo.jpg`);
|
||||
let resource1 = (await Resource.all())[0];
|
||||
let resourcePath1 = Resource.fullPath(resource1);
|
||||
const resource1 = (await Resource.all())[0];
|
||||
const resourcePath1 = Resource.fullPath(resource1);
|
||||
await synchronizer().start();
|
||||
|
||||
await switchClient(2);
|
||||
@ -986,7 +986,7 @@ describe('synchronizer', function() {
|
||||
|
||||
let resource1_2 = (await Resource.all())[0];
|
||||
resource1_2 = await Resource.decrypt(resource1_2);
|
||||
let resourcePath1_2 = Resource.fullPath(resource1_2);
|
||||
const resourcePath1_2 = Resource.fullPath(resource1_2);
|
||||
|
||||
expect(fileContentEqual(resourcePath1, resourcePath1_2)).toBe(true);
|
||||
}));
|
||||
@ -995,7 +995,7 @@ describe('synchronizer', function() {
|
||||
Setting.setValue('encryption.enabled', true);
|
||||
const masterKey = await loadEncryptionMasterKey();
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
await synchronizer().start();
|
||||
|
||||
let allEncrypted = await allSyncTargetItemsEncrypted();
|
||||
@ -1016,7 +1016,7 @@ describe('synchronizer', function() {
|
||||
Setting.setValue('encryption.enabled', true);
|
||||
const masterKey = await loadEncryptionMasterKey();
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
await synchronizer().start();
|
||||
|
||||
await switchClient(2);
|
||||
@ -1049,12 +1049,12 @@ describe('synchronizer', function() {
|
||||
Setting.setValue('encryption.enabled', true);
|
||||
const masterKey = await loadEncryptionMasterKey();
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
await shim.attachFileToNote(note1, `${__dirname}/../tests/support/photo.jpg`);
|
||||
let resource1 = (await Resource.all())[0];
|
||||
const resource1 = (await Resource.all())[0];
|
||||
await Resource.setFileSizeOnly(resource1.id, -1);
|
||||
let resourcePath1 = Resource.fullPath(resource1);
|
||||
const resourcePath1 = Resource.fullPath(resource1);
|
||||
await synchronizer().start();
|
||||
|
||||
await switchClient(2);
|
||||
@ -1075,8 +1075,8 @@ describe('synchronizer', function() {
|
||||
it('should encrypt remote resources after encryption has been enabled', asyncTest(async () => {
|
||||
while (insideBeforeEach) await time.msleep(100);
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
await shim.attachFileToNote(note1, `${__dirname}/../tests/support/photo.jpg`);
|
||||
await synchronizer().start();
|
||||
|
||||
@ -1094,22 +1094,22 @@ describe('synchronizer', function() {
|
||||
it('should upload encrypted resource, but it should not mark the blob as encrypted locally', asyncTest(async () => {
|
||||
while (insideBeforeEach) await time.msleep(100);
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'ma note', parent_id: folder1.id });
|
||||
await shim.attachFileToNote(note1, `${__dirname}/../tests/support/photo.jpg`);
|
||||
const masterKey = await loadEncryptionMasterKey();
|
||||
await encryptionService().enableEncryption(masterKey, '123456');
|
||||
await encryptionService().loadMasterKeysFromSettings();
|
||||
await synchronizer().start();
|
||||
|
||||
let resource1 = (await Resource.all())[0];
|
||||
const resource1 = (await Resource.all())[0];
|
||||
expect(resource1.encryption_blob_encrypted).toBe(0);
|
||||
}));
|
||||
|
||||
it('should create remote items with UTF-8 content', asyncTest(async () => {
|
||||
let folder = await Folder.save({ title: 'Fahrräder' });
|
||||
const folder = await Folder.save({ title: 'Fahrräder' });
|
||||
await Note.save({ title: 'Fahrräder', body: 'Fahrräder', parent_id: folder.id });
|
||||
let all = await allNotesFolders();
|
||||
const all = await allNotesFolders();
|
||||
|
||||
await synchronizer().start();
|
||||
|
||||
@ -1117,8 +1117,8 @@ describe('synchronizer', function() {
|
||||
}));
|
||||
|
||||
it('should update remote items but not pull remote changes', asyncTest(async () => {
|
||||
let folder = await Folder.save({ title: 'folder1' });
|
||||
let note = await Note.save({ title: 'un', parent_id: folder.id });
|
||||
const folder = await Folder.save({ title: 'folder1' });
|
||||
const note = await Note.save({ title: 'un', parent_id: folder.id });
|
||||
await synchronizer().start();
|
||||
|
||||
await switchClient(2);
|
||||
@ -1131,13 +1131,13 @@ describe('synchronizer', function() {
|
||||
|
||||
await Note.save({ title: 'un UPDATE', id: note.id });
|
||||
await synchronizer().start({ syncSteps: ['update_remote'] });
|
||||
let all = await allNotesFolders();
|
||||
const all = await allNotesFolders();
|
||||
expect(all.length).toBe(2);
|
||||
|
||||
await switchClient(2);
|
||||
|
||||
await synchronizer().start();
|
||||
let note2 = await Note.load(note.id);
|
||||
const note2 = await Note.load(note.id);
|
||||
expect(note2.title).toBe('un UPDATE');
|
||||
}));
|
||||
|
||||
@ -1544,8 +1544,8 @@ describe('synchronizer', function() {
|
||||
Setting.setValue('encryption.enabled', true);
|
||||
await loadEncryptionMasterKey();
|
||||
|
||||
let folder1 = await Folder.save({ title: 'folder1' });
|
||||
let note1 = await Note.save({ title: 'un', parent_id: folder1.id });
|
||||
const folder1 = await Folder.save({ title: 'folder1' });
|
||||
const note1 = await Note.save({ title: 'un', parent_id: folder1.id });
|
||||
let note2 = await Note.save({ title: 'deux', parent_id: folder1.id });
|
||||
await synchronizer().start();
|
||||
|
||||
@ -1570,12 +1570,12 @@ describe('synchronizer', function() {
|
||||
await synchronizer().start();
|
||||
|
||||
// The shared note should be decrypted
|
||||
let note2_2 = await Note.load(note2.id);
|
||||
const note2_2 = await Note.load(note2.id);
|
||||
expect(note2_2.title).toBe('deux');
|
||||
expect(note2_2.is_shared).toBe(1);
|
||||
|
||||
// The non-shared note should be encrypted
|
||||
let note1_2 = await Note.load(note1.id);
|
||||
const note1_2 = await Note.load(note1.id);
|
||||
expect(note1_2.title).toBe('');
|
||||
}));
|
||||
|
||||
|
@ -3,7 +3,7 @@
|
||||
const fs = require('fs-extra');
|
||||
const { JoplinDatabase } = require('lib/joplin-database.js');
|
||||
const { DatabaseDriverNode } = require('lib/database-driver-node.js');
|
||||
const { BaseApplication }= require('lib/BaseApplication.js');
|
||||
const { BaseApplication } = require('lib/BaseApplication.js');
|
||||
const BaseModel = require('lib/BaseModel.js');
|
||||
const Folder = require('lib/models/Folder.js');
|
||||
const Note = require('lib/models/Note.js');
|
||||
@ -41,13 +41,13 @@ const KvStore = require('lib/services/KvStore.js');
|
||||
const WebDavApi = require('lib/WebDavApi');
|
||||
const DropboxApi = require('lib/DropboxApi');
|
||||
|
||||
let databases_ = [];
|
||||
let synchronizers_ = [];
|
||||
let encryptionServices_ = [];
|
||||
let revisionServices_ = [];
|
||||
let decryptionWorkers_ = [];
|
||||
let resourceServices_ = [];
|
||||
let kvStores_ = [];
|
||||
const databases_ = [];
|
||||
const synchronizers_ = [];
|
||||
const encryptionServices_ = [];
|
||||
const revisionServices_ = [];
|
||||
const decryptionWorkers_ = [];
|
||||
const resourceServices_ = [];
|
||||
const kvStores_ = [];
|
||||
let fileApi_ = null;
|
||||
let currentClient_ = 1;
|
||||
|
||||
@ -341,7 +341,7 @@ function fileApi() {
|
||||
|
||||
function objectsEqual(o1, o2) {
|
||||
if (Object.getOwnPropertyNames(o1).length !== Object.getOwnPropertyNames(o2).length) return false;
|
||||
for (let n in o1) {
|
||||
for (const n in o1) {
|
||||
if (!o1.hasOwnProperty(n)) continue;
|
||||
if (o1[n] !== o2[n]) return false;
|
||||
}
|
||||
@ -427,7 +427,7 @@ function sortedIds(a) {
|
||||
}
|
||||
|
||||
function at(a, indexes) {
|
||||
let out = [];
|
||||
const out = [];
|
||||
for (let i = 0; i < indexes.length; i++) {
|
||||
out.push(a[indexes[i]]);
|
||||
}
|
||||
@ -435,19 +435,19 @@ function at(a, indexes) {
|
||||
}
|
||||
|
||||
async function createNTestFolders(n) {
|
||||
let folders = [];
|
||||
const folders = [];
|
||||
for (let i = 0; i < n; i++) {
|
||||
let folder = await Folder.save({ title: 'folder' });
|
||||
const folder = await Folder.save({ title: 'folder' });
|
||||
folders.push(folder);
|
||||
}
|
||||
return folders;
|
||||
}
|
||||
|
||||
async function createNTestNotes(n, folder, tagIds = null, title = 'note') {
|
||||
let notes = [];
|
||||
const notes = [];
|
||||
for (let i = 0; i < n; i++) {
|
||||
let title_ = n > 1 ? `${title}${i}` : title;
|
||||
let note = await Note.save({ title: title_, parent_id: folder.id, is_conflict: 0 });
|
||||
const title_ = n > 1 ? `${title}${i}` : title;
|
||||
const note = await Note.save({ title: title_, parent_id: folder.id, is_conflict: 0 });
|
||||
notes.push(note);
|
||||
}
|
||||
if (tagIds) {
|
||||
@ -459,9 +459,9 @@ async function createNTestNotes(n, folder, tagIds = null, title = 'note') {
|
||||
}
|
||||
|
||||
async function createNTestTags(n) {
|
||||
let tags = [];
|
||||
const tags = [];
|
||||
for (let i = 0; i < n; i++) {
|
||||
let tag = await Tag.save({ title: 'tag' });
|
||||
const tag = await Tag.save({ title: 'tag' });
|
||||
tags.push(tag);
|
||||
}
|
||||
return tags;
|
||||
|
@ -290,8 +290,8 @@
|
||||
// option to clip pages as HTML.
|
||||
function getStyleSheets(doc) {
|
||||
const output = [];
|
||||
for (var i=0; i<doc.styleSheets.length; i++) {
|
||||
var sheet = doc.styleSheets[i];
|
||||
for (let i = 0; i < doc.styleSheets.length; i++) {
|
||||
const sheet = doc.styleSheets[i];
|
||||
try {
|
||||
for (const cssRule of sheet.cssRules) {
|
||||
output.push({ type: 'text', value: cssRule.cssText });
|
||||
@ -530,7 +530,7 @@
|
||||
|
||||
} else if (command.name === 'pageUrl') {
|
||||
|
||||
let url = pageLocationOrigin() + location.pathname + location.search;
|
||||
const url = pageLocationOrigin() + location.pathname + location.search;
|
||||
return clippedContentResponse(pageTitle(), url, getImageSizes(document), getAnchorNames(document));
|
||||
|
||||
} else {
|
||||
|
@ -18,7 +18,7 @@ require('../config/env');
|
||||
|
||||
const jest = require('jest');
|
||||
const execSync = require('child_process').execSync;
|
||||
let argv = process.argv.slice(2);
|
||||
const argv = process.argv.slice(2);
|
||||
|
||||
function isInGitRepository() {
|
||||
try {
|
||||
|
@ -85,7 +85,7 @@ class Application extends BaseApplication {
|
||||
const currentRoute = state.route;
|
||||
|
||||
newState = Object.assign({}, state);
|
||||
let newNavHistory = state.navHistory.slice();
|
||||
const newNavHistory = state.navHistory.slice();
|
||||
|
||||
if (goingBack) {
|
||||
let newAction = null;
|
||||
@ -115,7 +115,7 @@ class Application extends BaseApplication {
|
||||
|
||||
{
|
||||
newState = Object.assign({}, state);
|
||||
let command = Object.assign({}, action);
|
||||
const command = Object.assign({}, action);
|
||||
delete command.type;
|
||||
newState.windowCommand = command.name ? command : null;
|
||||
}
|
||||
@ -143,13 +143,13 @@ class Application extends BaseApplication {
|
||||
const currentLayoutIndex = paneOptions.indexOf(currentLayout);
|
||||
const nextLayoutIndex = currentLayoutIndex === paneOptions.length - 1 ? 0 : currentLayoutIndex + 1;
|
||||
|
||||
let nextLayout = paneOptions[nextLayoutIndex];
|
||||
const nextLayout = paneOptions[nextLayoutIndex];
|
||||
return nextLayout === 'both' ? ['editor', 'viewer'] : [nextLayout];
|
||||
};
|
||||
|
||||
newState = Object.assign({}, state);
|
||||
|
||||
let panes = state.noteVisiblePanes.slice();
|
||||
const panes = state.noteVisiblePanes.slice();
|
||||
newState.noteVisiblePanes = getNextLayout(panes);
|
||||
}
|
||||
break;
|
||||
@ -328,7 +328,7 @@ class Application extends BaseApplication {
|
||||
const sortNoteFolderItems = (type) => {
|
||||
const sortItems = [];
|
||||
const sortOptions = Setting.enumOptions(`${type}.sortOrder.field`);
|
||||
for (let field in sortOptions) {
|
||||
for (const field in sortOptions) {
|
||||
if (!sortOptions.hasOwnProperty(field)) continue;
|
||||
sortItems.push({
|
||||
label: sortOptions[field],
|
||||
@ -650,7 +650,7 @@ class Application extends BaseApplication {
|
||||
gitInfo = _('Revision: %s (%s)', p.git.hash, p.git.branch);
|
||||
}
|
||||
const copyrightText = 'Copyright © 2016-YYYY Laurent Cozic';
|
||||
let message = [
|
||||
const message = [
|
||||
p.description,
|
||||
'',
|
||||
copyrightText.replace('YYYY', new Date().getFullYear()),
|
||||
@ -1119,7 +1119,7 @@ class Application extends BaseApplication {
|
||||
|
||||
const pluginMenuItems = PluginManager.instance().menuItems();
|
||||
for (const item of pluginMenuItems) {
|
||||
let itemParent = rootMenus[item.parent] ? rootMenus[item.parent] : 'tools';
|
||||
const itemParent = rootMenus[item.parent] ? rootMenus[item.parent] : 'tools';
|
||||
itemParent.submenu.push(item);
|
||||
}
|
||||
|
||||
@ -1155,7 +1155,7 @@ class Application extends BaseApplication {
|
||||
}
|
||||
|
||||
// Remove empty separator for now empty sections
|
||||
let temp = [];
|
||||
const temp = [];
|
||||
let previous = null;
|
||||
for (let i = 0; i < output.length; i++) {
|
||||
const t = Object.assign({}, output[i]);
|
||||
@ -1171,7 +1171,7 @@ class Application extends BaseApplication {
|
||||
return output;
|
||||
}
|
||||
|
||||
let screenTemplate = removeUnwantedItems(template, screen);
|
||||
const screenTemplate = removeUnwantedItems(template, screen);
|
||||
|
||||
const menu = Menu.buildFromTemplate(screenTemplate);
|
||||
Menu.setApplicationMenu(menu);
|
||||
|
@ -57,7 +57,7 @@ class ClipperConfigScreenComponent extends React.Component {
|
||||
backgroundColor: theme.backgroundColor,
|
||||
};
|
||||
|
||||
let webClipperStatusComps = [];
|
||||
const webClipperStatusComps = [];
|
||||
|
||||
if (this.props.clipperServerAutoStart) {
|
||||
webClipperStatusComps.push(
|
||||
|
@ -92,8 +92,8 @@ class ConfigScreenComponent extends React.Component {
|
||||
}
|
||||
|
||||
keyValueToArray(kv) {
|
||||
let output = [];
|
||||
for (let k in kv) {
|
||||
const output = [];
|
||||
for (const k in kv) {
|
||||
if (!kv.hasOwnProperty(k)) continue;
|
||||
output.push({
|
||||
key: k,
|
||||
@ -205,7 +205,7 @@ class ConfigScreenComponent extends React.Component {
|
||||
}
|
||||
|
||||
let advancedSettingsButton = null;
|
||||
let advancedSettingsSectionStyle = { display: 'none' };
|
||||
const advancedSettingsSectionStyle = { display: 'none' };
|
||||
|
||||
if (advancedSettingComps.length) {
|
||||
const iconName = this.state.showAdvancedSettings ? 'fa fa-toggle-up' : 'fa fa-toggle-down';
|
||||
@ -227,7 +227,7 @@ class ConfigScreenComponent extends React.Component {
|
||||
settingToComponent(key, value) {
|
||||
const theme = themeStyle(this.props.theme);
|
||||
|
||||
let output = null;
|
||||
const output = null;
|
||||
|
||||
const rowStyle = this.rowStyle_;
|
||||
|
||||
@ -283,9 +283,9 @@ class ConfigScreenComponent extends React.Component {
|
||||
const descriptionComp = descriptionText ? <div style={descriptionStyle}>{descriptionText}</div> : null;
|
||||
|
||||
if (md.isEnum) {
|
||||
let items = [];
|
||||
const items = [];
|
||||
const settingOptions = md.options();
|
||||
let array = this.keyValueToArray(settingOptions);
|
||||
const array = this.keyValueToArray(settingOptions);
|
||||
for (let i = 0; i < array.length; i++) {
|
||||
const e = array[i];
|
||||
items.push(
|
||||
@ -547,7 +547,7 @@ class ConfigScreenComponent extends React.Component {
|
||||
}
|
||||
);
|
||||
|
||||
let settings = this.state.settings;
|
||||
const settings = this.state.settings;
|
||||
|
||||
const containerStyle = Object.assign({}, theme.containerStyle, { padding: 10, paddingTop: 0, display: 'flex', flex: 1 });
|
||||
|
||||
|
@ -149,7 +149,7 @@ class EncryptionConfigScreenComponent extends React.Component {
|
||||
});
|
||||
|
||||
const mkComps = [];
|
||||
let nonExistingMasterKeyIds = this.props.notLoadedMasterKeys.slice();
|
||||
const nonExistingMasterKeyIds = this.props.notLoadedMasterKeys.slice();
|
||||
|
||||
for (let i = 0; i < masterKeys.length; i++) {
|
||||
const mk = masterKeys[i];
|
||||
|
@ -149,7 +149,7 @@ class HeaderComponent extends React.Component {
|
||||
}
|
||||
|
||||
const isEnabled = !('enabled' in options) || options.enabled;
|
||||
let classes = ['button'];
|
||||
const classes = ['button'];
|
||||
if (!isEnabled) classes.push('disabled');
|
||||
|
||||
const finalStyle = Object.assign({}, style, {
|
||||
|
@ -15,7 +15,7 @@ class HelpButtonComponent extends React.Component {
|
||||
|
||||
render() {
|
||||
const theme = themeStyle(this.props.theme);
|
||||
let style = Object.assign({}, this.props.style, { color: theme.color, textDecoration: 'none' });
|
||||
const style = Object.assign({}, this.props.style, { color: theme.color, textDecoration: 'none' });
|
||||
const helpIconStyle = { flex: 0, width: 16, height: 16, marginLeft: 10 };
|
||||
const extraProps = {};
|
||||
if (this.props.tip) extraProps['data-tip'] = this.props.tip;
|
||||
|
@ -46,9 +46,9 @@ class ImportScreenComponent extends React.Component {
|
||||
}
|
||||
|
||||
uniqueMessages() {
|
||||
let output = [];
|
||||
const output = [];
|
||||
const messages = this.state.messages.slice();
|
||||
let foundKeys = [];
|
||||
const foundKeys = [];
|
||||
for (let i = messages.length - 1; i >= 0; i--) {
|
||||
const msg = messages[i];
|
||||
if (foundKeys.indexOf(msg.key) >= 0) continue;
|
||||
@ -68,7 +68,7 @@ class ImportScreenComponent extends React.Component {
|
||||
|
||||
const options = {
|
||||
onProgress: progressState => {
|
||||
let line = [];
|
||||
const line = [];
|
||||
line.push(_('Found: %d.', progressState.loaded));
|
||||
line.push(_('Created: %d.', progressState.created));
|
||||
if (progressState.updated) line.push(_('Updated: %d.', progressState.updated));
|
||||
|
@ -83,7 +83,7 @@ class ItemList extends React.Component {
|
||||
return <div key={key} style={{ height: height }}></div>;
|
||||
};
|
||||
|
||||
let itemComps = [blankItem('top', this.state.topItemIndex * this.props.itemHeight)];
|
||||
const itemComps = [blankItem('top', this.state.topItemIndex * this.props.itemHeight)];
|
||||
|
||||
for (let i = this.state.topItemIndex; i <= this.state.bottomItemIndex; i++) {
|
||||
const itemComp = this.props.itemRenderer(items[i]);
|
||||
@ -92,7 +92,7 @@ class ItemList extends React.Component {
|
||||
|
||||
itemComps.push(blankItem('bottom', (items.length - this.state.bottomItemIndex - 1) * this.props.itemHeight));
|
||||
|
||||
let classes = ['item-list'];
|
||||
const classes = ['item-list'];
|
||||
if (this.props.className) classes.push(this.props.className);
|
||||
|
||||
return (
|
||||
|
@ -324,7 +324,7 @@ class MainScreenComponent extends React.Component {
|
||||
} else if (command.name === 'editAlarm') {
|
||||
const note = await Note.load(command.noteId);
|
||||
|
||||
let defaultDate = new Date(Date.now() + 2 * 3600 * 1000);
|
||||
const defaultDate = new Date(Date.now() + 2 * 3600 * 1000);
|
||||
defaultDate.setMinutes(0);
|
||||
defaultDate.setSeconds(0);
|
||||
|
||||
|
@ -7,7 +7,7 @@ class NavigatorComponent extends Component {
|
||||
UNSAFE_componentWillReceiveProps(newProps) {
|
||||
if (newProps.route) {
|
||||
const screenInfo = this.props.screens[newProps.route.routeName];
|
||||
let windowTitle = ['Joplin'];
|
||||
const windowTitle = ['Joplin'];
|
||||
if (screenInfo.title) {
|
||||
windowTitle.push(screenInfo.title());
|
||||
}
|
||||
|
@ -64,7 +64,7 @@ export default function NoteContentPropertiesDialog(props:NoteContentPropertiesD
|
||||
};
|
||||
|
||||
if (textProperties) {
|
||||
for (let key in textProperties) {
|
||||
for (const key in textProperties) {
|
||||
if (!textProperties.hasOwnProperty(key)) continue;
|
||||
const comp = createItemField(key, textProperties[key]);
|
||||
textComps.push(comp);
|
||||
|
@ -34,7 +34,7 @@ class NoteListComponent extends React.Component {
|
||||
// Pull request: https://github.com/laurent22/joplin/pull/2062
|
||||
const itemWidth = '100%';
|
||||
|
||||
let style = {
|
||||
const style = {
|
||||
root: {
|
||||
backgroundColor: theme.backgroundColor,
|
||||
},
|
||||
@ -184,7 +184,7 @@ class NoteListComponent extends React.Component {
|
||||
listItemTitleStyle.paddingLeft = !checkbox ? hPadding : 4;
|
||||
if (item.is_todo && !!item.todo_completed) listItemTitleStyle = Object.assign(listItemTitleStyle, this.style().listItemTitleCompleted);
|
||||
|
||||
let displayTitle = Note.displayTitle(item);
|
||||
const displayTitle = Note.displayTitle(item);
|
||||
let titleComp = null;
|
||||
|
||||
if (highlightedWords.length) {
|
||||
@ -435,7 +435,7 @@ class NoteListComponent extends React.Component {
|
||||
render() {
|
||||
const theme = themeStyle(this.props.theme);
|
||||
const style = this.props.style;
|
||||
let notes = this.props.notes.slice();
|
||||
const notes = this.props.notes.slice();
|
||||
|
||||
if (!notes.length) {
|
||||
const padding = 10;
|
||||
|
@ -361,7 +361,7 @@ class NotePropertiesDialog extends React.Component {
|
||||
const noteComps = [];
|
||||
|
||||
if (formNote) {
|
||||
for (let key in formNote) {
|
||||
for (const key in formNote) {
|
||||
if (!formNote.hasOwnProperty(key)) continue;
|
||||
const comp = this.createNoteField(key, formNote[key]);
|
||||
noteComps.push(comp);
|
||||
|
@ -40,7 +40,7 @@ class NoteRevisionViewerComponent extends React.PureComponent {
|
||||
style() {
|
||||
const theme = themeStyle(this.props.theme);
|
||||
|
||||
let style = {
|
||||
const style = {
|
||||
root: {
|
||||
backgroundColor: theme.backgroundColor,
|
||||
display: 'flex',
|
||||
|
@ -19,7 +19,7 @@ class NoteSearchBarComponent extends React.Component {
|
||||
style() {
|
||||
const theme = themeStyle(this.props.theme);
|
||||
|
||||
let style = {
|
||||
const style = {
|
||||
root: Object.assign({}, theme.textStyle, {
|
||||
backgroundColor: theme.backgroundColor,
|
||||
color: theme.colorFaded,
|
||||
@ -130,7 +130,7 @@ class NoteSearchBarComponent extends React.Component {
|
||||
if (this.backgroundColor === undefined) {
|
||||
this.backgroundColor = theme.backgroundColor;
|
||||
}
|
||||
let buttonEnabled = (this.backgroundColor === theme.backgroundColor);
|
||||
const buttonEnabled = (this.backgroundColor === theme.backgroundColor);
|
||||
|
||||
const closeButton = this.buttonIconComponent('fa-times', this.closeButton_click, true);
|
||||
const previousButton = this.buttonIconComponent('fa-chevron-up', this.previousButton_click, buttonEnabled);
|
||||
|
@ -7,7 +7,7 @@ class NoteStatusBarComponent extends React.Component {
|
||||
style() {
|
||||
const theme = themeStyle(this.props.theme);
|
||||
|
||||
let style = {
|
||||
const style = {
|
||||
root: Object.assign({}, theme.textStyle, {
|
||||
backgroundColor: theme.backgroundColor,
|
||||
color: theme.colorFaded,
|
||||
|
@ -543,22 +543,22 @@ class NoteTextComponent extends React.Component {
|
||||
this.setState({ loading: true });
|
||||
|
||||
const stateNoteId = this.state.note ? this.state.note.id : null;
|
||||
let noteId = props.noteId;
|
||||
const noteId = props.noteId;
|
||||
let parentFolder = null;
|
||||
const isProvisionalNote = this.props.provisionalNoteIds.includes(noteId);
|
||||
|
||||
let scrollPercent = this.props.lastEditorScrollPercents[noteId];
|
||||
if (!scrollPercent) scrollPercent = 0;
|
||||
|
||||
let loadingNewNote = stateNoteId !== noteId;
|
||||
const loadingNewNote = stateNoteId !== noteId;
|
||||
this.lastLoadedNoteId_ = noteId;
|
||||
let note = noteId ? await Note.load(noteId) : null;
|
||||
const note = noteId ? await Note.load(noteId) : null;
|
||||
if (noteId !== this.lastLoadedNoteId_) return defer(); // Race condition - current note was changed while this one was loading
|
||||
if (options.noReloadIfLocalChanges && this.isModified()) return defer();
|
||||
|
||||
// If the note hasn't been changed, exit now
|
||||
if (this.state.note && note) {
|
||||
let diff = Note.diffObjects(this.state.note, note);
|
||||
const diff = Note.diffObjects(this.state.note, note);
|
||||
delete diff.type_;
|
||||
if (!Object.getOwnPropertyNames(diff).length) return defer();
|
||||
}
|
||||
@ -622,7 +622,7 @@ class NoteTextComponent extends React.Component {
|
||||
parentFolder = Folder.byId(props.folders, note.parent_id);
|
||||
}
|
||||
|
||||
let newState = {
|
||||
const newState = {
|
||||
note: note,
|
||||
lastSavedNote: Object.assign({}, note),
|
||||
webviewReady: webviewReady,
|
||||
@ -686,9 +686,9 @@ class NoteTextComponent extends React.Component {
|
||||
|
||||
for (let i = 0; i < newTags.length; ++i) {
|
||||
let found = false;
|
||||
let currNewTag = newTags[i];
|
||||
const currNewTag = newTags[i];
|
||||
for (let j = 0; j < oldTags.length; ++j) {
|
||||
let currOldTag = oldTags[j];
|
||||
const currOldTag = oldTags[j];
|
||||
if (currOldTag.id === currNewTag.id) {
|
||||
found = true;
|
||||
if (currOldTag.updated_time !== currNewTag.updated_time) {
|
||||
@ -1299,7 +1299,7 @@ class NoteTextComponent extends React.Component {
|
||||
try {
|
||||
if (!this.state.note && !args.noteIds) throw new Error('No notes selected for pdf export');
|
||||
|
||||
let noteIds = args.noteIds ? args.noteIds : [this.state.note.id];
|
||||
const noteIds = args.noteIds ? args.noteIds : [this.state.note.id];
|
||||
|
||||
let path = null;
|
||||
if (noteIds.length === 1) {
|
||||
@ -1452,14 +1452,14 @@ class NoteTextComponent extends React.Component {
|
||||
|
||||
if (selection && selection.start !== selection.end) {
|
||||
const selectedLines = replacementText !== null ? replacementText : this.state.note.body.substr(selection.start, selection.end - selection.start);
|
||||
let selectedStrings = byLine ? selectedLines.split(/\r?\n/) : [selectedLines];
|
||||
const selectedStrings = byLine ? selectedLines.split(/\r?\n/) : [selectedLines];
|
||||
|
||||
newBody = this.state.note.body.substr(0, selection.start);
|
||||
|
||||
for (let i = 0; i < selectedStrings.length; i++) {
|
||||
if (byLine == false) {
|
||||
let start = selectedStrings[i].search(/[^\s]/);
|
||||
let end = selectedStrings[i].search(/[^\s](?=[\s]*$)/);
|
||||
const start = selectedStrings[i].search(/[^\s]/);
|
||||
const end = selectedStrings[i].search(/[^\s](?=[\s]*$)/);
|
||||
newBody += selectedStrings[i].substr(0, start) + string1 + selectedStrings[i].substr(start, end - start + 1) + string2 + selectedStrings[i].substr(end + 1);
|
||||
if (this.state.note.body.substr(selection.end) === '') newBody = newBody.trim();
|
||||
} else { newBody += string1 + selectedStrings[i] + string2; }
|
||||
@ -1498,7 +1498,7 @@ class NoteTextComponent extends React.Component {
|
||||
editor.focus();
|
||||
});
|
||||
} else {
|
||||
let middleText = replacementText !== null ? replacementText : defaultText;
|
||||
const middleText = replacementText !== null ? replacementText : defaultText;
|
||||
const textOffset = this.currentTextOffset();
|
||||
const s1 = this.state.note.body.substr(0, textOffset);
|
||||
const s2 = this.state.note.body.substr(textOffset);
|
||||
@ -1541,9 +1541,9 @@ class NoteTextComponent extends React.Component {
|
||||
|
||||
toggleWrapSelection(strings1, strings2, defaultText) {
|
||||
const selection = this.textOffsetSelection();
|
||||
let string = this.state.note.body.substr(selection.start, selection.end - selection.start);
|
||||
const string = this.state.note.body.substr(selection.start, selection.end - selection.start);
|
||||
let replaced = false;
|
||||
for (var i = 0; i < strings1.length; i++) {
|
||||
for (let i = 0; i < strings1.length; i++) {
|
||||
if (string.startsWith(strings1[i]) && string.endsWith(strings1[i])) {
|
||||
this.wrapSelectionWithStrings('', '', '', string.substr(strings1[i].length, selection.end - selection.start - (2 * strings1[i].length)));
|
||||
replaced = true;
|
||||
@ -1570,10 +1570,10 @@ class NoteTextComponent extends React.Component {
|
||||
|
||||
commandTextCode() {
|
||||
const selection = this.textOffsetSelection();
|
||||
let string = this.state.note.body.substr(selection.start, selection.end - selection.start);
|
||||
const string = this.state.note.body.substr(selection.start, selection.end - selection.start);
|
||||
|
||||
// Look for newlines
|
||||
let match = string.match(/\r?\n/);
|
||||
const match = string.match(/\r?\n/);
|
||||
|
||||
if (match && match.length > 0) {
|
||||
// Follow the same newline style
|
||||
@ -1591,7 +1591,7 @@ class NoteTextComponent extends React.Component {
|
||||
this.wrapSelectionWithStrings(TemplateUtils.render(value));
|
||||
}
|
||||
|
||||
addListItem(string1, string2 = '', defaultText = '', byLine=false) {
|
||||
addListItem(string1, string2 = '', defaultText = '', byLine = false) {
|
||||
let newLine = '\n';
|
||||
const range = this.selectionRange_;
|
||||
if (!range || (range.start.row === range.end.row && !this.selectionRangeCurrentLine())) {
|
||||
@ -1949,7 +1949,7 @@ class NoteTextComponent extends React.Component {
|
||||
const theme = themeStyle(this.props.theme);
|
||||
const visiblePanes = this.props.visiblePanes || ['editor', 'viewer'];
|
||||
const isTodo = note && !!note.is_todo;
|
||||
var keyboardMode = this.props.keyboardMode;
|
||||
let keyboardMode = this.props.keyboardMode;
|
||||
if (keyboardMode === 'default' || !keyboardMode) {
|
||||
keyboardMode = null;
|
||||
}
|
||||
@ -2006,7 +2006,7 @@ class NoteTextComponent extends React.Component {
|
||||
paddingRight: 8,
|
||||
marginRight: rootStyle.paddingLeft,
|
||||
color: theme.textStyle.color,
|
||||
fontSize: theme.textStyle.fontSize * 1.25 *1.5,
|
||||
fontSize: theme.textStyle.fontSize * 1.25 * 1.5,
|
||||
backgroundColor: theme.backgroundColor,
|
||||
border: '1px solid',
|
||||
borderColor: theme.dividerColor,
|
||||
@ -2083,11 +2083,11 @@ class NoteTextComponent extends React.Component {
|
||||
}
|
||||
|
||||
if (this.state.webviewReady && this.webviewRef_.current) {
|
||||
let html = this.state.bodyHtml;
|
||||
const html = this.state.bodyHtml;
|
||||
|
||||
const htmlHasChanged = this.lastSetHtml_ !== html;
|
||||
if (htmlHasChanged) {
|
||||
let options = {
|
||||
const options = {
|
||||
pluginAssets: this.state.lastRenderPluginAssets,
|
||||
downloadResources: Setting.value('sync.resourceDownloadMode'),
|
||||
};
|
||||
|
@ -57,7 +57,7 @@ class NoteTextViewerComponent extends React.Component {
|
||||
};
|
||||
}
|
||||
|
||||
for (let n in this.webviewListeners_) {
|
||||
for (const n in this.webviewListeners_) {
|
||||
if (!this.webviewListeners_.hasOwnProperty(n)) continue;
|
||||
const fn = this.webviewListeners_[n];
|
||||
wv.addEventListener(n, fn);
|
||||
@ -70,7 +70,7 @@ class NoteTextViewerComponent extends React.Component {
|
||||
const wv = this.webviewRef_.current;
|
||||
if (!wv || !this.initialized_) return;
|
||||
|
||||
for (let n in this.webviewListeners_) {
|
||||
for (const n in this.webviewListeners_) {
|
||||
if (!this.webviewListeners_.hasOwnProperty(n)) continue;
|
||||
const fn = this.webviewListeners_[n];
|
||||
wv.removeEventListener(n, fn);
|
||||
|
@ -73,7 +73,7 @@ export default function ShareNoteDialog(props:ShareNoteDialogProps) {
|
||||
useEffect(() => {
|
||||
async function fetchNotes() {
|
||||
const result = [];
|
||||
for (let noteId of props.noteIds) {
|
||||
for (const noteId of props.noteIds) {
|
||||
result.push(await Note.load(noteId));
|
||||
}
|
||||
setNotes(result);
|
||||
@ -180,7 +180,7 @@ export default function ShareNoteDialog(props:ShareNoteDialogProps) {
|
||||
|
||||
const renderNoteList = (notes:any) => {
|
||||
const noteComps = [];
|
||||
for (let noteId of Object.keys(notes)) {
|
||||
for (const noteId of Object.keys(notes)) {
|
||||
noteComps.push(renderNote(notes[noteId]));
|
||||
}
|
||||
return <div style={styles.noteList}>{noteComps}</div>;
|
||||
|
@ -107,7 +107,7 @@ class SideBarComponent extends React.Component {
|
||||
|
||||
const itemHeight = 25;
|
||||
|
||||
let style = {
|
||||
const style = {
|
||||
root: {
|
||||
backgroundColor: theme.backgroundColor2,
|
||||
},
|
||||
@ -459,8 +459,8 @@ class SideBarComponent extends React.Component {
|
||||
let containerStyle = Object.assign({}, this.style(depth).listItemContainer);
|
||||
if (selected) containerStyle = Object.assign(containerStyle, this.style().listItemSelected);
|
||||
|
||||
let expandLinkStyle = Object.assign({}, this.style().listItemExpandIcon);
|
||||
let expandIconStyle = {
|
||||
const expandLinkStyle = Object.assign({}, this.style().listItemExpandIcon);
|
||||
const expandIconStyle = {
|
||||
visibility: hasChildren ? 'visible' : 'hidden',
|
||||
paddingLeft: 8 + depth * 10,
|
||||
};
|
||||
@ -562,18 +562,18 @@ class SideBarComponent extends React.Component {
|
||||
style.cursor = 'pointer';
|
||||
}
|
||||
|
||||
let headerClick = extraProps.onClick || null;
|
||||
const headerClick = extraProps.onClick || null;
|
||||
delete extraProps.onClick;
|
||||
|
||||
// check if toggling option is set.
|
||||
let toggleIcon = null;
|
||||
const toggleKey = `${key}IsExpanded`;
|
||||
if (extraProps.toggleblock) {
|
||||
let isExpanded = this.state[toggleKey];
|
||||
const isExpanded = this.state[toggleKey];
|
||||
toggleIcon = <i className={`fa ${isExpanded ? 'fa-chevron-down' : 'fa-chevron-left'}`} style={{ fontSize: style.fontSize * 0.75, marginRight: 12, marginLeft: 5, marginTop: style.fontSize * 0.125 }}></i>;
|
||||
}
|
||||
if (extraProps.selected) {
|
||||
style.backgroundColor =this.style().listItemSelected.backgroundColor;
|
||||
style.backgroundColor = this.style().listItemSelected.backgroundColor;
|
||||
}
|
||||
|
||||
const ref = this.anchorItemRef('headers', key);
|
||||
@ -645,7 +645,7 @@ class SideBarComponent extends React.Component {
|
||||
|
||||
const focusItem = focusItems[newIndex];
|
||||
|
||||
let actionName = `${focusItem.type.toUpperCase()}_SELECT`;
|
||||
const actionName = `${focusItem.type.toUpperCase()}_SELECT`;
|
||||
|
||||
this.props.dispatch({
|
||||
type: actionName,
|
||||
@ -712,7 +712,7 @@ class SideBarComponent extends React.Component {
|
||||
const style = Object.assign({}, this.style().button, { marginBottom: 5 });
|
||||
const iconName = 'fa-refresh';
|
||||
const label = type === 'sync' ? _('Synchronise') : _('Cancel');
|
||||
let iconStyle = { fontSize: style.fontSize, marginRight: 5 };
|
||||
const iconStyle = { fontSize: style.fontSize, marginRight: 5 };
|
||||
|
||||
if (type !== 'sync') {
|
||||
iconStyle.animation = 'icon-infinite-rotation 1s linear infinite';
|
||||
@ -743,7 +743,7 @@ class SideBarComponent extends React.Component {
|
||||
flexDirection: 'column',
|
||||
});
|
||||
|
||||
let items = [];
|
||||
const items = [];
|
||||
items.push(
|
||||
this.makeHeader('allNotesHeader', _('All notes'), 'fa-clone', {
|
||||
onClick: this.onAllNotesClick_,
|
||||
@ -798,7 +798,7 @@ class SideBarComponent extends React.Component {
|
||||
resourceFetcherText = _('Fetching resources: %d/%d', this.props.resourceFetcher.fetchingCount, this.props.resourceFetcher.toFetchCount);
|
||||
}
|
||||
|
||||
let lines = Synchronizer.reportToLines(this.props.syncReport);
|
||||
const lines = Synchronizer.reportToLines(this.props.syncReport);
|
||||
if (resourceFetcherText) lines.push(resourceFetcherText);
|
||||
if (decryptionReportText) lines.push(decryptionReportText);
|
||||
const syncReportText = [];
|
||||
|
@ -64,13 +64,13 @@ class StatusScreenComponent extends React.Component {
|
||||
}
|
||||
|
||||
const renderSectionHtml = (key, section) => {
|
||||
let itemsHtml = [];
|
||||
const itemsHtml = [];
|
||||
|
||||
itemsHtml.push(renderSectionTitleHtml(section.title, section.title));
|
||||
|
||||
for (let n in section.body) {
|
||||
for (const n in section.body) {
|
||||
if (!section.body.hasOwnProperty(n)) continue;
|
||||
let item = section.body[n];
|
||||
const item = section.body[n];
|
||||
let text = '';
|
||||
|
||||
let retryLink = null;
|
||||
@ -106,10 +106,10 @@ class StatusScreenComponent extends React.Component {
|
||||
};
|
||||
|
||||
function renderBodyHtml(report) {
|
||||
let sectionsHtml = [];
|
||||
const sectionsHtml = [];
|
||||
|
||||
for (let i = 0; i < report.length; i++) {
|
||||
let section = report[i];
|
||||
const section = report[i];
|
||||
if (!section.body.length) continue;
|
||||
sectionsHtml.push(renderSectionHtml(i, section));
|
||||
}
|
||||
@ -117,7 +117,7 @@ class StatusScreenComponent extends React.Component {
|
||||
return <div>{sectionsHtml}</div>;
|
||||
}
|
||||
|
||||
let body = renderBodyHtml(this.state.report);
|
||||
const body = renderBodyHtml(this.state.report);
|
||||
|
||||
return (
|
||||
<div style={style}>
|
||||
|
@ -21,7 +21,7 @@ class ToolbarButton extends React.Component {
|
||||
}
|
||||
|
||||
const isEnabled = !('enabled' in this.props) || this.props.enabled === true;
|
||||
let classes = ['button'];
|
||||
const classes = ['button'];
|
||||
if (!isEnabled) classes.push('disabled');
|
||||
|
||||
const finalStyle = Object.assign({}, style, {
|
||||
|
@ -100,7 +100,7 @@ app().start(bridge().processArgv()).then(() => {
|
||||
} else {
|
||||
// If something goes wrong at this stage we don't have a console or a log file
|
||||
// so display the error in a message box.
|
||||
let msg = ['Fatal error:', error.message];
|
||||
const msg = ['Fatal error:', error.message];
|
||||
if (error.fileName) msg.push(error.fileName);
|
||||
if (error.lineNumber) msg.push(error.lineNumber);
|
||||
if (error.stack) msg.push(error.stack);
|
||||
|
@ -385,13 +385,13 @@ function addExtraStyles(style) {
|
||||
return style;
|
||||
}
|
||||
|
||||
let themeCache_ = {};
|
||||
const themeCache_ = {};
|
||||
|
||||
function themeStyle(theme) {
|
||||
if (!theme) throw new Error('Theme must be specified');
|
||||
|
||||
var zoomRatio = 1; // Setting.value('style.zoom') / 100;
|
||||
var editorFontSize = Setting.value('style.editor.fontSize');
|
||||
const zoomRatio = 1; // Setting.value('style.zoom') / 100;
|
||||
const editorFontSize = Setting.value('style.editor.fontSize');
|
||||
|
||||
const cacheKey = [theme, zoomRatio, editorFontSize].join('-');
|
||||
if (themeCache_[cacheKey]) return themeCache_[cacheKey];
|
||||
@ -399,7 +399,7 @@ function themeStyle(theme) {
|
||||
// Font size are not theme specific, but they must be referenced
|
||||
// and computed here to allow them to respond to settings changes
|
||||
// without the need to restart
|
||||
let fontSizes = {
|
||||
const fontSizes = {
|
||||
fontSize: Math.round(globalStyle.fontSize * zoomRatio),
|
||||
editorFontSize: editorFontSize,
|
||||
textAreaLineHeight: Math.round(globalStyle.textAreaLineHeight * editorFontSize / 12),
|
||||
|
@ -7,7 +7,7 @@ const execSync = require('child_process').execSync;
|
||||
const packageInfo = require(`${__dirname}/../package.json`);
|
||||
|
||||
module.exports = async function() {
|
||||
let removeKeys = ['scripts', 'devDependencies', 'optionalDependencies', 'dependencies'];
|
||||
const removeKeys = ['scripts', 'devDependencies', 'optionalDependencies', 'dependencies'];
|
||||
|
||||
for (let i = 0; i < removeKeys.length; i++) {
|
||||
delete packageInfo[removeKeys[i]];
|
||||
|
@ -36,7 +36,7 @@ export default class PluginAssetsLoader {
|
||||
this.logger().info(`PluginAssetsLoader: Importing assets to ${destDir}`);
|
||||
|
||||
try {
|
||||
for (let name in pluginAssets.files) {
|
||||
for (const name in pluginAssets.files) {
|
||||
const dataBase64 = pluginAssets.files[name].data;
|
||||
const destPath = `${destDir}/${name}`;
|
||||
await shim.fsDriver().mkdir(dirname(destPath));
|
||||
|
@ -16,7 +16,7 @@ ArrayUtils.removeElement = function(array, element) {
|
||||
|
||||
// https://stackoverflow.com/a/10264318/561309
|
||||
ArrayUtils.binarySearch = function(items, value) {
|
||||
var startIndex = 0,
|
||||
let startIndex = 0,
|
||||
stopIndex = items.length - 1,
|
||||
middle = Math.floor((stopIndex + startIndex) / 2);
|
||||
|
||||
|
@ -111,13 +111,13 @@ class BaseApplication {
|
||||
// Handles the initial flags passed to main script and
|
||||
// returns the remaining args.
|
||||
async handleStartFlags_(argv, setDefaults = true) {
|
||||
let matched = {};
|
||||
const matched = {};
|
||||
argv = argv.slice(0);
|
||||
argv.splice(0, 2); // First arguments are the node executable, and the node JS file
|
||||
|
||||
while (argv.length) {
|
||||
let arg = argv[0];
|
||||
let nextArg = argv.length >= 2 ? argv[1] : null;
|
||||
const arg = argv[0];
|
||||
const nextArg = argv.length >= 2 ? argv[1] : null;
|
||||
|
||||
if (arg == '--profile') {
|
||||
if (!nextArg) throw new JoplinError(_('Usage: %s', '--profile <dir-path>'), 'flagError');
|
||||
@ -245,7 +245,7 @@ class BaseApplication {
|
||||
|
||||
this.logger().debug('Refreshing notes:', parentType, parentId);
|
||||
|
||||
let options = {
|
||||
const options = {
|
||||
order: stateUtils.notesOrder(state.settings),
|
||||
uncompletedTodosOnTop: Setting.value('uncompletedTodosOnTop'),
|
||||
showCompletedTodos: Setting.value('showCompletedTodos'),
|
||||
@ -333,7 +333,7 @@ class BaseApplication {
|
||||
}
|
||||
|
||||
reducerActionToString(action) {
|
||||
let o = [action.type];
|
||||
const o = [action.type];
|
||||
if ('id' in action) o.push(action.id);
|
||||
if ('noteId' in action) o.push(action.noteId);
|
||||
if ('folderId' in action) o.push(action.folderId);
|
||||
@ -580,7 +580,7 @@ class BaseApplication {
|
||||
}
|
||||
|
||||
async start(argv) {
|
||||
let startFlags = await this.handleStartFlags_(argv);
|
||||
const startFlags = await this.handleStartFlags_(argv);
|
||||
|
||||
argv = startFlags.argv;
|
||||
let initArgs = startFlags.matched;
|
||||
@ -712,7 +712,7 @@ class BaseApplication {
|
||||
SearchEngine.instance().setLogger(reg.logger());
|
||||
SearchEngine.instance().scheduleSyncTables();
|
||||
|
||||
let currentFolderId = Setting.value('activeFolderId');
|
||||
const currentFolderId = Setting.value('activeFolderId');
|
||||
let currentFolder = null;
|
||||
if (currentFolderId) currentFolder = await Folder.load(currentFolderId);
|
||||
if (!currentFolder) currentFolder = await Folder.defaultFolder();
|
||||
|
@ -16,7 +16,7 @@ class BaseModel {
|
||||
if (!model) return model;
|
||||
|
||||
if (Array.isArray(model)) {
|
||||
let output = [];
|
||||
const output = [];
|
||||
for (let i = 0; i < model.length; i++) {
|
||||
output.push(this.addModelMd(model[i]));
|
||||
}
|
||||
@ -87,16 +87,16 @@ class BaseModel {
|
||||
}
|
||||
|
||||
static hasField(name) {
|
||||
let fields = this.fieldNames();
|
||||
const fields = this.fieldNames();
|
||||
return fields.indexOf(name) >= 0;
|
||||
}
|
||||
|
||||
static fieldNames(withPrefix = false) {
|
||||
let output = this.db().tableFieldNames(this.tableName());
|
||||
const output = this.db().tableFieldNames(this.tableName());
|
||||
if (!withPrefix) return output;
|
||||
|
||||
let p = withPrefix === true ? this.tableName() : withPrefix;
|
||||
let temp = [];
|
||||
const p = withPrefix === true ? this.tableName() : withPrefix;
|
||||
const temp = [];
|
||||
for (let i = 0; i < output.length; i++) {
|
||||
temp.push(`${p}.${output[i]}`);
|
||||
}
|
||||
@ -105,7 +105,7 @@ class BaseModel {
|
||||
}
|
||||
|
||||
static fieldType(name, defaultValue = null) {
|
||||
let fields = this.fields();
|
||||
const fields = this.fields();
|
||||
for (let i = 0; i < fields.length; i++) {
|
||||
if (fields[i].name == name) return fields[i].type;
|
||||
}
|
||||
@ -119,7 +119,7 @@ class BaseModel {
|
||||
|
||||
static removeUnknownFields(model) {
|
||||
const newModel = {};
|
||||
for (let n in model) {
|
||||
for (const n in model) {
|
||||
if (!model.hasOwnProperty(n)) continue;
|
||||
if (!this.hasField(n) && n !== 'type_') continue;
|
||||
newModel[n] = model[n];
|
||||
@ -128,10 +128,10 @@ class BaseModel {
|
||||
}
|
||||
|
||||
static new() {
|
||||
let fields = this.fields();
|
||||
let output = {};
|
||||
const fields = this.fields();
|
||||
const output = {};
|
||||
for (let i = 0; i < fields.length; i++) {
|
||||
let f = fields[i];
|
||||
const f = fields[i];
|
||||
output[f.name] = f.default;
|
||||
}
|
||||
return output;
|
||||
@ -175,7 +175,7 @@ class BaseModel {
|
||||
if (!options) options = {};
|
||||
|
||||
if (options.order && options.order.length) {
|
||||
let items = [];
|
||||
const items = [];
|
||||
for (let i = 0; i < options.order.length; i++) {
|
||||
const o = options.order[i];
|
||||
let item = o.by;
|
||||
@ -192,7 +192,7 @@ class BaseModel {
|
||||
}
|
||||
|
||||
static async allIds(options = null) {
|
||||
let q = this.applySqlOptions(options, `SELECT id FROM \`${this.tableName()}\``);
|
||||
const q = this.applySqlOptions(options, `SELECT id FROM \`${this.tableName()}\``);
|
||||
const rows = await this.db().selectAll(q.sql, q.params);
|
||||
return rows.map(r => r.id);
|
||||
}
|
||||
@ -208,7 +208,7 @@ class BaseModel {
|
||||
if (options.whereParams) params = params.concat(options.whereParams);
|
||||
}
|
||||
|
||||
let q = this.applySqlOptions(options, sql, params);
|
||||
const q = this.applySqlOptions(options, sql, params);
|
||||
return this.modelSelectAll(q.sql, q.params);
|
||||
}
|
||||
|
||||
@ -219,7 +219,7 @@ class BaseModel {
|
||||
|
||||
let sql = `SELECT ${this.db().escapeFields(options.fields)} FROM \`${this.tableName()}\``;
|
||||
sql += ` WHERE id IN ("${ids.join('","')}")`;
|
||||
let q = this.applySqlOptions(options, sql);
|
||||
const q = this.applySqlOptions(options, sql);
|
||||
return this.modelSelectAll(q.sql);
|
||||
}
|
||||
|
||||
@ -227,11 +227,11 @@ class BaseModel {
|
||||
if (!options) options = {};
|
||||
if (!options.fields) options.fields = '*';
|
||||
|
||||
let conditions = options.conditions ? options.conditions.slice(0) : [];
|
||||
let params = options.conditionsParams ? options.conditionsParams.slice(0) : [];
|
||||
const conditions = options.conditions ? options.conditions.slice(0) : [];
|
||||
const params = options.conditionsParams ? options.conditionsParams.slice(0) : [];
|
||||
|
||||
if (options.titlePattern) {
|
||||
let pattern = options.titlePattern.replace(/\*/g, '%');
|
||||
const pattern = options.titlePattern.replace(/\*/g, '%');
|
||||
conditions.push('title LIKE ?');
|
||||
params.push(pattern);
|
||||
}
|
||||
@ -241,7 +241,7 @@ class BaseModel {
|
||||
let sql = `SELECT ${this.db().escapeFields(options.fields)} FROM \`${this.tableName()}\``;
|
||||
if (conditions.length) sql += ` WHERE ${conditions.join(' AND ')}`;
|
||||
|
||||
let query = this.applySqlOptions(options, sql, params);
|
||||
const query = this.applySqlOptions(options, sql, params);
|
||||
return this.modelSelectAll(query.sql, query.params);
|
||||
}
|
||||
|
||||
@ -277,7 +277,7 @@ class BaseModel {
|
||||
}
|
||||
|
||||
static diffObjects(oldModel, newModel) {
|
||||
let output = {};
|
||||
const output = {};
|
||||
const fields = this.diffObjectsFields(oldModel, newModel);
|
||||
for (let i = 0; i < fields.length; i++) {
|
||||
output[fields[i]] = newModel[fields[i]];
|
||||
@ -287,8 +287,8 @@ class BaseModel {
|
||||
}
|
||||
|
||||
static diffObjectsFields(oldModel, newModel) {
|
||||
let output = [];
|
||||
for (let n in newModel) {
|
||||
const output = [];
|
||||
for (const n in newModel) {
|
||||
if (!newModel.hasOwnProperty(n)) continue;
|
||||
if (n == 'type_') continue;
|
||||
if (!(n in oldModel) || newModel[n] !== oldModel[n]) {
|
||||
@ -313,7 +313,7 @@ class BaseModel {
|
||||
|
||||
if (!modelOrId) return noLockMutex;
|
||||
|
||||
let modelId = typeof modelOrId === 'string' ? modelOrId : modelOrId.id;
|
||||
const modelId = typeof modelOrId === 'string' ? modelOrId : modelOrId.id;
|
||||
|
||||
if (!modelId) return noLockMutex;
|
||||
|
||||
@ -329,11 +329,11 @@ class BaseModel {
|
||||
if (!release) return;
|
||||
if (!modelOrId) return release();
|
||||
|
||||
let modelId = typeof modelOrId === 'string' ? modelOrId : modelOrId.id;
|
||||
const modelId = typeof modelOrId === 'string' ? modelOrId : modelOrId.id;
|
||||
|
||||
if (!modelId) return release();
|
||||
|
||||
let mutex = BaseModel.saveMutexes_[modelId];
|
||||
const mutex = BaseModel.saveMutexes_[modelId];
|
||||
if (!mutex) return release();
|
||||
|
||||
delete BaseModel.saveMutexes_[modelId];
|
||||
@ -342,9 +342,9 @@ class BaseModel {
|
||||
|
||||
static saveQuery(o, options) {
|
||||
let temp = {};
|
||||
let fieldNames = this.fieldNames();
|
||||
const fieldNames = this.fieldNames();
|
||||
for (let i = 0; i < fieldNames.length; i++) {
|
||||
let n = fieldNames[i];
|
||||
const n = fieldNames[i];
|
||||
if (n in o) temp[n] = o[n];
|
||||
}
|
||||
|
||||
@ -354,7 +354,7 @@ class BaseModel {
|
||||
// id also will stay.
|
||||
if (!options.isNew && options.fields) {
|
||||
const filtered = {};
|
||||
for (let k in temp) {
|
||||
for (const k in temp) {
|
||||
if (!temp.hasOwnProperty(k)) continue;
|
||||
if (k !== 'id' && options.fields.indexOf(k) < 0) continue;
|
||||
filtered[k] = temp[k];
|
||||
@ -404,8 +404,8 @@ class BaseModel {
|
||||
|
||||
query = Database.insertQuery(this.tableName(), o);
|
||||
} else {
|
||||
let where = { id: o.id };
|
||||
let temp = Object.assign({}, o);
|
||||
const where = { id: o.id };
|
||||
const temp = Object.assign({}, o);
|
||||
delete temp.id;
|
||||
|
||||
query = Database.updateQuery(this.tableName(), temp, where);
|
||||
@ -445,8 +445,8 @@ class BaseModel {
|
||||
o = this.filter(o);
|
||||
|
||||
let queries = [];
|
||||
let saveQuery = this.saveQuery(o, options);
|
||||
let modelId = saveQuery.id;
|
||||
const saveQuery = this.saveQuery(o, options);
|
||||
const modelId = saveQuery.id;
|
||||
|
||||
queries.push(saveQuery);
|
||||
|
||||
@ -473,7 +473,7 @@ class BaseModel {
|
||||
o = this.addModelMd(o);
|
||||
|
||||
if (isDiffSaving) {
|
||||
for (let n in options.oldItem) {
|
||||
for (const n in options.oldItem) {
|
||||
if (!options.oldItem.hasOwnProperty(n)) continue;
|
||||
if (n in o) continue;
|
||||
o[n] = options.oldItem[n];
|
||||
@ -499,7 +499,7 @@ class BaseModel {
|
||||
}
|
||||
|
||||
static filterArray(models) {
|
||||
let output = [];
|
||||
const output = [];
|
||||
for (let i = 0; i < models.length; i++) {
|
||||
output.push(this.filter(models[i]));
|
||||
}
|
||||
@ -509,8 +509,8 @@ class BaseModel {
|
||||
static filter(model) {
|
||||
if (!model) return model;
|
||||
|
||||
let output = Object.assign({}, model);
|
||||
for (let n in output) {
|
||||
const output = Object.assign({}, model);
|
||||
for (const n in output) {
|
||||
if (!output.hasOwnProperty(n)) continue;
|
||||
|
||||
// The SQLite database doesn't have booleans so cast everything to int
|
||||
|
@ -51,11 +51,11 @@ class DropboxApi {
|
||||
}
|
||||
|
||||
requestToCurl_(url, options) {
|
||||
let output = [];
|
||||
const output = [];
|
||||
output.push('curl');
|
||||
if (options.method) output.push(`-X ${options.method}`);
|
||||
if (options.headers) {
|
||||
for (let n in options.headers) {
|
||||
for (const n in options.headers) {
|
||||
if (!options.headers.hasOwnProperty(n)) continue;
|
||||
output.push(`${'-H ' + '\''}${n}: ${options.headers[n]}'`);
|
||||
}
|
||||
@ -74,10 +74,10 @@ class DropboxApi {
|
||||
client_secret: this.clientSecret(),
|
||||
};
|
||||
|
||||
var formBody = [];
|
||||
for (var property in postData) {
|
||||
var encodedKey = encodeURIComponent(property);
|
||||
var encodedValue = encodeURIComponent(postData[property]);
|
||||
let formBody = [];
|
||||
for (const property in postData) {
|
||||
const encodedKey = encodeURIComponent(property);
|
||||
const encodedValue = encodeURIComponent(postData[property]);
|
||||
formBody.push(`${encodedKey}=${encodedValue}`);
|
||||
}
|
||||
formBody = formBody.join('&');
|
||||
|
@ -6,7 +6,7 @@ class EventDispatcher {
|
||||
dispatch(eventName, event = null) {
|
||||
if (!this.listeners_[eventName]) return;
|
||||
|
||||
let ls = this.listeners_[eventName];
|
||||
const ls = this.listeners_[eventName];
|
||||
for (let i = 0; i < ls.length; i++) {
|
||||
ls[i](event);
|
||||
}
|
||||
@ -20,7 +20,7 @@ class EventDispatcher {
|
||||
off(eventName, callback) {
|
||||
if (!this.listeners_[eventName]) return;
|
||||
|
||||
let ls = this.listeners_[eventName];
|
||||
const ls = this.listeners_[eventName];
|
||||
for (let i = 0; i < ls.length; i++) {
|
||||
if (ls[i] === callback) {
|
||||
ls.splice(i, 1);
|
||||
|
@ -83,12 +83,12 @@ export default class JoplinServerApi {
|
||||
}
|
||||
|
||||
requestToCurl_(url:string, options:any) {
|
||||
let output = [];
|
||||
const output = [];
|
||||
output.push('curl');
|
||||
output.push('-v');
|
||||
if (options.method) output.push(`-X ${options.method}`);
|
||||
if (options.headers) {
|
||||
for (let n in options.headers) {
|
||||
for (const n in options.headers) {
|
||||
if (!options.headers.hasOwnProperty(n)) continue;
|
||||
output.push(`${'-H ' + '"'}${n}: ${options.headers[n]}"`);
|
||||
}
|
||||
@ -129,7 +129,7 @@ export default class JoplinServerApi {
|
||||
|
||||
const responseText = await response.text();
|
||||
|
||||
let responseJson_:any = null;
|
||||
const responseJson_:any = null;
|
||||
const loadResponseJson = async () => {
|
||||
if (!responseText) return null;
|
||||
if (responseJson_) return responseJson_;
|
||||
|
@ -2,7 +2,7 @@ const ObjectUtils = {};
|
||||
|
||||
ObjectUtils.sortByValue = function(object) {
|
||||
const temp = [];
|
||||
for (let k in object) {
|
||||
for (const k in object) {
|
||||
if (!object.hasOwnProperty(k)) continue;
|
||||
temp.push({
|
||||
key: k,
|
||||
@ -31,7 +31,7 @@ ObjectUtils.sortByValue = function(object) {
|
||||
ObjectUtils.fieldsEqual = function(o1, o2) {
|
||||
if ((!o1 || !o2) && o1 !== o2) return false;
|
||||
|
||||
for (let k in o1) {
|
||||
for (const k in o1) {
|
||||
if (!o1.hasOwnProperty(k)) continue;
|
||||
if (o1[k] !== o2[k]) return false;
|
||||
}
|
||||
@ -46,7 +46,7 @@ ObjectUtils.fieldsEqual = function(o1, o2) {
|
||||
|
||||
ObjectUtils.convertValuesToFunctions = function(o) {
|
||||
const output = {};
|
||||
for (let n in o) {
|
||||
for (const n in o) {
|
||||
if (!o.hasOwnProperty(n)) continue;
|
||||
output[n] = () => {
|
||||
return typeof o[n] === 'function' ? o[n]() : o[n];
|
||||
|
@ -16,7 +16,7 @@ class SyncTargetRegistry {
|
||||
}
|
||||
|
||||
static nameToId(name) {
|
||||
for (let n in this.reg_) {
|
||||
for (const n in this.reg_) {
|
||||
if (!this.reg_.hasOwnProperty(n)) continue;
|
||||
if (this.reg_[n].name === name) return this.reg_[n].id;
|
||||
}
|
||||
@ -24,7 +24,7 @@ class SyncTargetRegistry {
|
||||
}
|
||||
|
||||
static idToMetadata(id) {
|
||||
for (let n in this.reg_) {
|
||||
for (const n in this.reg_) {
|
||||
if (!this.reg_.hasOwnProperty(n)) continue;
|
||||
if (this.reg_[n].id === id) return this.reg_[n];
|
||||
}
|
||||
@ -36,8 +36,8 @@ class SyncTargetRegistry {
|
||||
}
|
||||
|
||||
static idAndLabelPlainObject(os) {
|
||||
let output = {};
|
||||
for (let n in this.reg_) {
|
||||
const output = {};
|
||||
for (const n in this.reg_) {
|
||||
if (!this.reg_.hasOwnProperty(n)) continue;
|
||||
const info = this.reg_[n];
|
||||
if (info.classRef.unsupportedPlatforms().indexOf(os) >= 0) {
|
||||
|
@ -30,7 +30,7 @@ TemplateUtils.render = function(input) {
|
||||
};
|
||||
|
||||
TemplateUtils.loadTemplates = async function(filePath) {
|
||||
let templates = [];
|
||||
const templates = [];
|
||||
let files = [];
|
||||
|
||||
if (await shim.fsDriver().exists(filePath)) {
|
||||
@ -50,7 +50,7 @@ TemplateUtils.loadTemplates = async function(filePath) {
|
||||
files.forEach(async file => {
|
||||
if (file.path.endsWith('.md')) {
|
||||
try {
|
||||
let fileString = await shim.fsDriver().readFile(`${filePath}/${file.path}`, 'utf-8');
|
||||
const fileString = await shim.fsDriver().readFile(`${filePath}/${file.path}`, 'utf-8');
|
||||
templates.push({ label: file.path, value: fileString });
|
||||
} catch (error) {
|
||||
let msg = error.message ? error.message : '';
|
||||
|
@ -83,7 +83,7 @@ class WebDavApi {
|
||||
}
|
||||
|
||||
async xmlToJson(xml) {
|
||||
let davNamespaces = []; // Yes, there can be more than one... xmlns:a="DAV:" xmlns:D="DAV:"
|
||||
const davNamespaces = []; // Yes, there can be more than one... xmlns:a="DAV:" xmlns:D="DAV:"
|
||||
|
||||
const nameProcessor = name => {
|
||||
if (name.indexOf('xmlns') !== 0) {
|
||||
@ -247,12 +247,12 @@ class WebDavApi {
|
||||
}
|
||||
|
||||
requestToCurl_(url, options) {
|
||||
let output = [];
|
||||
const output = [];
|
||||
output.push('curl');
|
||||
output.push('-v');
|
||||
if (options.method) output.push(`-X ${options.method}`);
|
||||
if (options.headers) {
|
||||
for (let n in options.headers) {
|
||||
for (const n in options.headers) {
|
||||
if (!options.headers.hasOwnProperty(n)) continue;
|
||||
output.push(`${'-H ' + '"'}${n}: ${options.headers[n]}"`);
|
||||
}
|
||||
|
@ -30,7 +30,7 @@ class WelcomeUtils {
|
||||
|
||||
let noteBody = noteAsset.body;
|
||||
|
||||
for (let resourceUrl in noteAsset.resources) {
|
||||
for (const resourceUrl in noteAsset.resources) {
|
||||
if (!noteAsset.resources.hasOwnProperty(resourceUrl)) continue;
|
||||
const resourceAsset = noteAsset.resources[resourceUrl];
|
||||
const ext = fileExtension(resourceUrl);
|
||||
|
@ -107,10 +107,10 @@ class CameraView extends Component {
|
||||
}
|
||||
|
||||
fitRectIntoBounds(rect, bounds) {
|
||||
var rectRatio = rect.width / rect.height;
|
||||
var boundsRatio = bounds.width / bounds.height;
|
||||
const rectRatio = rect.width / rect.height;
|
||||
const boundsRatio = bounds.width / bounds.height;
|
||||
|
||||
var newDimensions = {};
|
||||
const newDimensions = {};
|
||||
|
||||
// Rect is more landscape than bounds - fit to width
|
||||
if (rectRatio > boundsRatio) {
|
||||
|
@ -16,7 +16,7 @@ class ModalDialog extends React.Component {
|
||||
if (this.styles_[themeId]) return this.styles_[themeId];
|
||||
this.styles_ = {};
|
||||
|
||||
let styles = {
|
||||
const styles = {
|
||||
modalWrapper: {
|
||||
flex: 1,
|
||||
justifyContent: 'center',
|
||||
|
@ -56,7 +56,7 @@ class ActionButtonComponent extends React.Component {
|
||||
}
|
||||
|
||||
render() {
|
||||
let buttons = this.props.buttons ? this.props.buttons : [];
|
||||
const buttons = this.props.buttons ? this.props.buttons : [];
|
||||
|
||||
if (this.props.addFolderNoteButtons) {
|
||||
if (this.props.folders.length) {
|
||||
@ -80,11 +80,11 @@ class ActionButtonComponent extends React.Component {
|
||||
}
|
||||
}
|
||||
|
||||
let buttonComps = [];
|
||||
const buttonComps = [];
|
||||
for (let i = 0; i < buttons.length; i++) {
|
||||
let button = buttons[i];
|
||||
let buttonTitle = button.title ? button.title : '';
|
||||
let key = `${buttonTitle.replace(/\s/g, '_')}_${button.icon}`;
|
||||
const button = buttons[i];
|
||||
const buttonTitle = button.title ? button.title : '';
|
||||
const key = `${buttonTitle.replace(/\s/g, '_')}_${button.icon}`;
|
||||
buttonComps.push(
|
||||
<ReactNativeActionButton.Item key={key} buttonColor={button.color} title={buttonTitle} onPress={button.onPress}>
|
||||
<Icon name={button.icon} style={styles.actionButtonIcon} />
|
||||
@ -96,14 +96,14 @@ class ActionButtonComponent extends React.Component {
|
||||
return <ReactNativeActionButton style={{ display: 'none' }} />;
|
||||
}
|
||||
|
||||
let mainButton = this.props.mainButton ? this.props.mainButton : {};
|
||||
let mainIcon = mainButton.icon ? <Icon name={mainButton.icon} style={styles.actionButtonIcon} /> : <Icon name="md-add" style={styles.actionButtonIcon} />;
|
||||
const mainButton = this.props.mainButton ? this.props.mainButton : {};
|
||||
const mainIcon = mainButton.icon ? <Icon name={mainButton.icon} style={styles.actionButtonIcon} /> : <Icon name="md-add" style={styles.actionButtonIcon} />;
|
||||
|
||||
if (this.props.multiStates) {
|
||||
if (!this.props.buttons || !this.props.buttons.length) throw new Error('Multi-state button requires at least one state');
|
||||
if (this.state.buttonIndex < 0 || this.state.buttonIndex >= this.props.buttons.length) throw new Error(`Button index out of bounds: ${this.state.buttonIndex}/${this.props.buttons.length}`);
|
||||
let button = this.props.buttons[this.state.buttonIndex];
|
||||
let mainIcon = <Icon name={button.icon} style={styles.actionButtonIcon} />;
|
||||
const button = this.props.buttons[this.state.buttonIndex];
|
||||
const mainIcon = <Icon name={button.icon} style={styles.actionButtonIcon} />;
|
||||
return (
|
||||
<ReactNativeActionButton
|
||||
icon={mainIcon}
|
||||
|
@ -43,7 +43,7 @@ class AppNavComponent extends Component {
|
||||
// Note: certain screens are kept into memory, in particular Notes and Search
|
||||
// so that the scroll position is not lost when the user navigate away from them.
|
||||
|
||||
let route = this.props.route;
|
||||
const route = this.props.route;
|
||||
let Screen = null;
|
||||
let notesScreenVisible = false;
|
||||
let searchScreenVisible = false;
|
||||
@ -59,7 +59,7 @@ class AppNavComponent extends Component {
|
||||
// Keep the search screen loaded if the user is viewing a note from that search screen
|
||||
// so that if the back button is pressed, the screen is still loaded. However, unload
|
||||
// it if navigating away.
|
||||
let searchScreenLoaded = searchScreenVisible || (this.previousRouteName_ == 'Search' && route.routeName == 'Note');
|
||||
const searchScreenLoaded = searchScreenVisible || (this.previousRouteName_ == 'Search' && route.routeName == 'Note');
|
||||
|
||||
this.previousRouteName_ = route.routeName;
|
||||
|
||||
|
@ -12,7 +12,7 @@ const styleObject_ = {
|
||||
|
||||
const styles_ = StyleSheet.create(styleObject_);
|
||||
|
||||
let rootStyles_ = {};
|
||||
const rootStyles_ = {};
|
||||
|
||||
class BaseScreenComponent extends React.Component {
|
||||
styles() {
|
||||
|
@ -31,7 +31,7 @@ class Checkbox extends Component {
|
||||
}
|
||||
|
||||
onPress() {
|
||||
let newChecked = !this.state.checked;
|
||||
const newChecked = !this.state.checked;
|
||||
this.setState({ checked: newChecked });
|
||||
if (this.props.onChange) this.props.onChange(newChecked);
|
||||
}
|
||||
@ -39,11 +39,11 @@ class Checkbox extends Component {
|
||||
render() {
|
||||
const iconName = this.state.checked ? 'md-checkbox-outline' : 'md-square-outline';
|
||||
|
||||
let style = this.props.style ? Object.assign({}, this.props.style) : {};
|
||||
const style = this.props.style ? Object.assign({}, this.props.style) : {};
|
||||
style.justifyContent = 'center';
|
||||
style.alignItems = 'center';
|
||||
|
||||
let checkboxIconStyle = Object.assign({}, styles.checkboxIcon);
|
||||
const checkboxIconStyle = Object.assign({}, styles.checkboxIcon);
|
||||
if (style.color) checkboxIconStyle.color = style.color;
|
||||
|
||||
if (style.paddingTop) checkboxIconStyle.marginTop = style.paddingTop;
|
||||
|
@ -47,7 +47,7 @@ globalStyle.marginTop = globalStyle.margin;
|
||||
globalStyle.marginBottom = globalStyle.margin;
|
||||
globalStyle.htmlMarginLeft = `${((globalStyle.marginLeft / 10) * 0.6).toFixed(2)}em`;
|
||||
|
||||
let themeCache_ = {};
|
||||
const themeCache_ = {};
|
||||
|
||||
function addExtraStyles(style) {
|
||||
style.icon = {
|
||||
@ -122,7 +122,7 @@ function themeStyle(theme) {
|
||||
|
||||
if (themeCache_[theme]) return themeCache_[theme];
|
||||
|
||||
let output = Object.assign({}, globalStyle);
|
||||
const output = Object.assign({}, globalStyle);
|
||||
if (theme == Setting.THEME_LIGHT) return addExtraStyles(output);
|
||||
else if (theme == Setting.THEME_OLED_DARK) {
|
||||
output.backgroundColor = '#000000';
|
||||
|
@ -62,7 +62,7 @@ class NoteBodyViewer extends Component {
|
||||
postMessageSyntax: 'window.ReactNativeWebView.postMessage',
|
||||
};
|
||||
|
||||
let result = await this.markupToHtml_.render(note.markup_language, bodyToRender, this.props.webViewStyle, mdOptions);
|
||||
const result = await this.markupToHtml_.render(note.markup_language, bodyToRender, this.props.webViewStyle, mdOptions);
|
||||
let html = result.html;
|
||||
|
||||
const resourceDownloadMode = Setting.value('sync.resourceDownloadMode');
|
||||
@ -188,7 +188,7 @@ class NoteBodyViewer extends Component {
|
||||
// https://github.com/react-native-community/react-native-webview/issues/312#issuecomment-503754654
|
||||
|
||||
|
||||
let webViewStyle = { backgroundColor: this.props.webViewStyle.backgroundColor };
|
||||
const webViewStyle = { backgroundColor: this.props.webViewStyle.backgroundColor };
|
||||
// On iOS, the onLoadEnd() event is never fired so always
|
||||
// display the webview (don't do the little trick
|
||||
// to avoid the white flash).
|
||||
|
@ -27,7 +27,7 @@ class NoteItemComponent extends Component {
|
||||
if (this.styles_[this.props.theme]) return this.styles_[this.props.theme];
|
||||
this.styles_ = {};
|
||||
|
||||
let styles = {
|
||||
const styles = {
|
||||
listItem: {
|
||||
flexDirection: 'row',
|
||||
// height: 40,
|
||||
@ -110,7 +110,7 @@ class NoteItemComponent extends Component {
|
||||
const theme = themeStyle(this.props.theme);
|
||||
|
||||
// IOS: display: none crashes the app
|
||||
let checkboxStyle = !isTodo ? { display: 'none' } : { color: theme.color };
|
||||
const checkboxStyle = !isTodo ? { display: 'none' } : { color: theme.color };
|
||||
|
||||
if (isTodo) {
|
||||
checkboxStyle.paddingRight = 10;
|
||||
|
@ -28,7 +28,7 @@ class NoteListComponent extends Component {
|
||||
if (this.styles_[themeId]) return this.styles_[themeId];
|
||||
this.styles_ = {};
|
||||
|
||||
let styles = {
|
||||
const styles = {
|
||||
noItemMessage: {
|
||||
paddingLeft: theme.marginLeft,
|
||||
paddingRight: theme.marginRight,
|
||||
@ -63,7 +63,7 @@ class NoteListComponent extends Component {
|
||||
const maxInterval = 1000 * 60 * 60 * 24;
|
||||
const notRecentTime = now - maxInterval;
|
||||
|
||||
let output = [];
|
||||
const output = [];
|
||||
for (let i = 0; i < notes.length; i++) {
|
||||
const note = notes[i];
|
||||
if (note.is_todo) {
|
||||
|
@ -36,7 +36,7 @@ class ScreenHeaderComponent extends React.PureComponent {
|
||||
|
||||
const theme = themeStyle(themeId);
|
||||
|
||||
let styleObject = {
|
||||
const styleObject = {
|
||||
container: {
|
||||
flexDirection: 'column',
|
||||
backgroundColor: theme.raisedBackgroundColor,
|
||||
@ -299,11 +299,11 @@ class ScreenHeaderComponent extends React.PureComponent {
|
||||
}
|
||||
|
||||
let key = 0;
|
||||
let menuOptionComponents = [];
|
||||
const menuOptionComponents = [];
|
||||
|
||||
if (!this.props.noteSelectionEnabled) {
|
||||
for (let i = 0; i < this.props.menuOptions.length; i++) {
|
||||
let o = this.props.menuOptions[i];
|
||||
const o = this.props.menuOptions[i];
|
||||
|
||||
if (o.isDivider) {
|
||||
menuOptionComponents.push(<View key={`menuOption_${key++}`} style={this.styles().divider} />);
|
||||
@ -408,7 +408,7 @@ class ScreenHeaderComponent extends React.PureComponent {
|
||||
/>
|
||||
);
|
||||
} else {
|
||||
let title = 'title' in this.props && this.props.title !== null ? this.props.title : '';
|
||||
const title = 'title' in this.props && this.props.title !== null ? this.props.title : '';
|
||||
return <Text style={this.styles().titleText}>{title}</Text>;
|
||||
}
|
||||
};
|
||||
|
@ -122,7 +122,7 @@ class NoteTagsDialogComponent extends React.Component {
|
||||
if (this.styles_[themeId]) return this.styles_[themeId];
|
||||
this.styles_ = {};
|
||||
|
||||
let styles = {
|
||||
const styles = {
|
||||
tag: {
|
||||
padding: 10,
|
||||
borderBottomWidth: 1,
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user