refactoring

This commit is contained in:
zadam 2021-04-17 20:52:46 +02:00
parent 42510fda5c
commit 1fdf889ccf
11 changed files with 213 additions and 90 deletions

View file

@ -138,7 +138,7 @@ function BackendScriptApi(currentNote, apiParams) {
searchParams.ignoreHoistedNote = true;
}
const noteIds = searchService.findNotesWithQuery(query, new SearchContext(searchParams))
const noteIds = searchService.findResultsWithQuery(query, new SearchContext(searchParams))
.map(sr => sr.noteId);
return repository.getNotes(noteIds);

View file

@ -23,7 +23,7 @@ describe("Search", () => {
);
const searchContext = new SearchContext();
const searchResults = searchService.findNotesWithQuery('europe austria', searchContext);
const searchResults = searchService.findResultsWithQuery('europe austria', searchContext);
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Austria")).toBeTruthy();
@ -40,12 +40,12 @@ describe("Search", () => {
.label('inhabitants', '1888776'));
const searchContext = new SearchContext();
let searchResults = searchService.findNotesWithQuery('capital', searchContext);
let searchResults = searchService.findResultsWithQuery('capital', searchContext);
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Austria")).toBeTruthy();
searchResults = searchService.findNotesWithQuery('inhabitants', searchContext);
searchResults = searchService.findResultsWithQuery('inhabitants', searchContext);
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Vienna")).toBeTruthy();
@ -57,17 +57,17 @@ describe("Search", () => {
.child(note("Hello World.java", {type: 'code', mime: 'text/x-java'}));
const searchContext = new SearchContext();
let searchResults = searchService.findNotesWithQuery('book', searchContext);
let searchResults = searchService.findResultsWithQuery('book', searchContext);
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Effective Java")).toBeTruthy();
searchResults = searchService.findNotesWithQuery('text', searchContext); // should match mime
searchResults = searchService.findResultsWithQuery('text', searchContext); // should match mime
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Hello World.java")).toBeTruthy();
searchResults = searchService.findNotesWithQuery('java', searchContext);
searchResults = searchService.findResultsWithQuery('java', searchContext);
expect(searchResults.length).toEqual(2);
});
@ -79,7 +79,7 @@ describe("Search", () => {
);
const searchContext = new SearchContext();
const searchResults = searchService.findNotesWithQuery('europe', searchContext);
const searchResults = searchService.findResultsWithQuery('europe', searchContext);
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Europe")).toBeTruthy();
@ -94,7 +94,7 @@ describe("Search", () => {
const searchContext = new SearchContext();
const searchResults = searchService.findNotesWithQuery('Vienna', searchContext);
const searchResults = searchService.findResultsWithQuery('Vienna', searchContext);
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Austria")).toBeTruthy();
});
@ -110,16 +110,16 @@ describe("Search", () => {
const searchContext = new SearchContext();
let searchResults = searchService.findNotesWithQuery('#capital=Vienna', searchContext);
let searchResults = searchService.findResultsWithQuery('#capital=Vienna', searchContext);
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Austria")).toBeTruthy();
// case sensitivity:
searchResults = searchService.findNotesWithQuery('#CAPITAL=VIENNA', searchContext);
searchResults = searchService.findResultsWithQuery('#CAPITAL=VIENNA', searchContext);
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Austria")).toBeTruthy();
searchResults = searchService.findNotesWithQuery('#caPItal=vienNa', searchContext);
searchResults = searchService.findResultsWithQuery('#caPItal=vienNa', searchContext);
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Austria")).toBeTruthy();
});
@ -135,7 +135,7 @@ describe("Search", () => {
const searchContext = new SearchContext();
let searchResults = searchService.findNotesWithQuery('# note.labels.capital=Prague', searchContext);
let searchResults = searchService.findResultsWithQuery('# note.labels.capital=Prague', searchContext);
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Czech Republic")).toBeTruthy();
});
@ -152,7 +152,7 @@ describe("Search", () => {
const searchContext = new SearchContext();
const searchResults = searchService.findNotesWithQuery('#country #population >= 10000000', searchContext);
const searchResults = searchService.findResultsWithQuery('#country #population >= 10000000', searchContext);
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Czech Republic")).toBeTruthy();
});
@ -173,11 +173,11 @@ describe("Search", () => {
const searchContext = new SearchContext();
let searchResults = searchService.findNotesWithQuery('#established <= "1955-01-01"', searchContext);
let searchResults = searchService.findResultsWithQuery('#established <= "1955-01-01"', searchContext);
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Hungary")).toBeTruthy();
searchResults = searchService.findNotesWithQuery('#established > "1955-01-01"', searchContext);
searchResults = searchService.findResultsWithQuery('#established > "1955-01-01"', searchContext);
expect(searchResults.length).toEqual(2);
expect(findNoteByTitle(searchResults, "Austria")).toBeTruthy();
expect(findNoteByTitle(searchResults, "Czech Republic")).toBeTruthy();
@ -197,7 +197,7 @@ describe("Search", () => {
const searchContext = new SearchContext();
function test(query, expectedResultCount) {
const searchResults = searchService.findNotesWithQuery(query, searchContext);
const searchResults = searchService.findResultsWithQuery(query, searchContext);
expect(searchResults.length).toEqual(expectedResultCount);
if (expectedResultCount === 1) {
@ -251,7 +251,7 @@ describe("Search", () => {
const searchContext = new SearchContext();
const searchResults = searchService.findNotesWithQuery('#languageFamily = slavic OR #languageFamily = germanic', searchContext);
const searchResults = searchService.findResultsWithQuery('#languageFamily = slavic OR #languageFamily = germanic', searchContext);
expect(searchResults.length).toEqual(2);
expect(findNoteByTitle(searchResults, "Czech Republic")).toBeTruthy();
expect(findNoteByTitle(searchResults, "Austria")).toBeTruthy();
@ -268,18 +268,18 @@ describe("Search", () => {
let searchContext = new SearchContext({fuzzyAttributeSearch: false});
let searchResults = searchService.findNotesWithQuery('#language', searchContext);
let searchResults = searchService.findResultsWithQuery('#language', searchContext);
expect(searchResults.length).toEqual(0);
searchResults = searchService.findNotesWithQuery('#languageFamily=ger', searchContext);
searchResults = searchService.findResultsWithQuery('#languageFamily=ger', searchContext);
expect(searchResults.length).toEqual(0);
searchContext = new SearchContext({fuzzyAttributeSearch: true});
searchResults = searchService.findNotesWithQuery('#language', searchContext);
searchResults = searchService.findResultsWithQuery('#language', searchContext);
expect(searchResults.length).toEqual(2);
searchResults = searchService.findNotesWithQuery('#languageFamily=ger', searchContext);
searchResults = searchService.findResultsWithQuery('#languageFamily=ger', searchContext);
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Austria")).toBeTruthy();
});
@ -292,7 +292,7 @@ describe("Search", () => {
const searchContext = new SearchContext();
const searchResults = searchService.findNotesWithQuery('# note.title =* czech', searchContext);
const searchResults = searchService.findResultsWithQuery('# note.title =* czech', searchContext);
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Czech Republic")).toBeTruthy();
});
@ -309,16 +309,16 @@ describe("Search", () => {
const searchContext = new SearchContext();
let searchResults = searchService.findNotesWithQuery('# note.parents.title = Europe', searchContext);
let searchResults = searchService.findResultsWithQuery('# note.parents.title = Europe', searchContext);
expect(searchResults.length).toEqual(2);
expect(findNoteByTitle(searchResults, "Austria")).toBeTruthy();
expect(findNoteByTitle(searchResults, "Czech Republic")).toBeTruthy();
searchResults = searchService.findNotesWithQuery('# note.parents.title = Asia', searchContext);
searchResults = searchService.findResultsWithQuery('# note.parents.title = Asia', searchContext);
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Taiwan")).toBeTruthy();
searchResults = searchService.findNotesWithQuery('# note.parents.parents.title = Europe', searchContext);
searchResults = searchService.findResultsWithQuery('# note.parents.parents.title = Europe', searchContext);
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Prague")).toBeTruthy();
});
@ -337,11 +337,11 @@ describe("Search", () => {
const searchContext = new SearchContext();
let searchResults = searchService.findNotesWithQuery('#city AND note.ancestors.title = Europe', searchContext);
let searchResults = searchService.findResultsWithQuery('#city AND note.ancestors.title = Europe', searchContext);
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Prague")).toBeTruthy();
searchResults = searchService.findNotesWithQuery('#city AND note.ancestors.title = Asia', searchContext);
searchResults = searchService.findResultsWithQuery('#city AND note.ancestors.title = Asia', searchContext);
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Taipei")).toBeTruthy();
});
@ -358,16 +358,16 @@ describe("Search", () => {
const searchContext = new SearchContext();
let searchResults = searchService.findNotesWithQuery('# note.children.title =* Aust', searchContext);
let searchResults = searchService.findResultsWithQuery('# note.children.title =* Aust', searchContext);
expect(searchResults.length).toEqual(2);
expect(findNoteByTitle(searchResults, "Europe")).toBeTruthy();
expect(findNoteByTitle(searchResults, "Oceania")).toBeTruthy();
searchResults = searchService.findNotesWithQuery('# note.children.title =* Aust AND note.children.title *= republic', searchContext);
searchResults = searchService.findResultsWithQuery('# note.children.title =* Aust AND note.children.title *= republic', searchContext);
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Europe")).toBeTruthy();
searchResults = searchService.findNotesWithQuery('# note.children.children.title = Prague', searchContext);
searchResults = searchService.findResultsWithQuery('# note.children.children.title = Prague', searchContext);
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Europe")).toBeTruthy();
});
@ -388,11 +388,11 @@ describe("Search", () => {
const searchContext = new SearchContext();
let searchResults = searchService.findNotesWithQuery('# ~neighbor.title = Austria', searchContext);
let searchResults = searchService.findResultsWithQuery('# ~neighbor.title = Austria', searchContext);
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Czech Republic")).toBeTruthy();
searchResults = searchService.findNotesWithQuery('# ~neighbor.title = Portugal', searchContext);
searchResults = searchService.findResultsWithQuery('# ~neighbor.title = Portugal', searchContext);
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Spain")).toBeTruthy();
});
@ -413,7 +413,7 @@ describe("Search", () => {
const searchContext = new SearchContext();
const searchResults = searchService.findNotesWithQuery('# note.relations.neighbor.title = Austria', searchContext);
const searchResults = searchService.findResultsWithQuery('# note.relations.neighbor.title = Austria', searchContext);
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Czech Republic")).toBeTruthy();
});
@ -439,11 +439,11 @@ describe("Search", () => {
const searchContext = new SearchContext();
let searchResults = searchService.findNotesWithQuery('# note.relations.neighbor.relations.neighbor.title = Italy', searchContext);
let searchResults = searchService.findResultsWithQuery('# note.relations.neighbor.relations.neighbor.title = Italy', searchContext);
expect(searchResults.length).toEqual(1);
expect(findNoteByTitle(searchResults, "Czech Republic")).toBeTruthy();
searchResults = searchService.findNotesWithQuery('# note.relations.neighbor.relations.neighbor.title = Ukraine', searchContext);
searchResults = searchService.findResultsWithQuery('# note.relations.neighbor.relations.neighbor.title = Ukraine', searchContext);
expect(searchResults.length).toEqual(2);
expect(findNoteByTitle(searchResults, "Czech Republic")).toBeTruthy();
expect(findNoteByTitle(searchResults, "Austria")).toBeTruthy();
@ -477,7 +477,7 @@ describe("Search", () => {
const searchContext = new SearchContext();
function test(propertyName, value, expectedResultCount) {
const searchResults = searchService.findNotesWithQuery(`# note.${propertyName} = ${value}`, searchContext);
const searchResults = searchService.findResultsWithQuery(`# note.${propertyName} = ${value}`, searchContext);
expect(searchResults.length).toEqual(expectedResultCount);
}
@ -536,36 +536,36 @@ describe("Search", () => {
const searchContext = new SearchContext();
let searchResults = searchService.findNotesWithQuery('# note.parents.title = Europe orderBy note.title', searchContext);
let searchResults = searchService.findResultsWithQuery('# note.parents.title = Europe orderBy note.title', searchContext);
expect(searchResults.length).toEqual(4);
expect(becca.notes[searchResults[0].noteId].title).toEqual("Austria");
expect(becca.notes[searchResults[1].noteId].title).toEqual("Italy");
expect(becca.notes[searchResults[2].noteId].title).toEqual("Slovakia");
expect(becca.notes[searchResults[3].noteId].title).toEqual("Ukraine");
searchResults = searchService.findNotesWithQuery('# note.parents.title = Europe orderBy note.labels.capital', searchContext);
searchResults = searchService.findResultsWithQuery('# note.parents.title = Europe orderBy note.labels.capital', searchContext);
expect(searchResults.length).toEqual(4);
expect(becca.notes[searchResults[0].noteId].title).toEqual("Slovakia");
expect(becca.notes[searchResults[1].noteId].title).toEqual("Ukraine");
expect(becca.notes[searchResults[2].noteId].title).toEqual("Italy");
expect(becca.notes[searchResults[3].noteId].title).toEqual("Austria");
searchResults = searchService.findNotesWithQuery('# note.parents.title = Europe orderBy note.labels.capital DESC', searchContext);
searchResults = searchService.findResultsWithQuery('# note.parents.title = Europe orderBy note.labels.capital DESC', searchContext);
expect(searchResults.length).toEqual(4);
expect(becca.notes[searchResults[0].noteId].title).toEqual("Austria");
expect(becca.notes[searchResults[1].noteId].title).toEqual("Italy");
expect(becca.notes[searchResults[2].noteId].title).toEqual("Ukraine");
expect(becca.notes[searchResults[3].noteId].title).toEqual("Slovakia");
searchResults = searchService.findNotesWithQuery('# note.parents.title = Europe orderBy note.labels.capital DESC limit 2', searchContext);
searchResults = searchService.findResultsWithQuery('# note.parents.title = Europe orderBy note.labels.capital DESC limit 2', searchContext);
expect(searchResults.length).toEqual(2);
expect(becca.notes[searchResults[0].noteId].title).toEqual("Austria");
expect(becca.notes[searchResults[1].noteId].title).toEqual("Italy");
searchResults = searchService.findNotesWithQuery('# note.parents.title = Europe orderBy #capital DESC limit 1', searchContext);
searchResults = searchService.findResultsWithQuery('# note.parents.title = Europe orderBy #capital DESC limit 1', searchContext);
expect(searchResults.length).toEqual(1);
searchResults = searchService.findNotesWithQuery('# note.parents.title = Europe orderBy #capital DESC limit 1000', searchContext);
searchResults = searchService.findResultsWithQuery('# note.parents.title = Europe orderBy #capital DESC limit 1000', searchContext);
expect(searchResults.length).toEqual(4);
});
@ -580,11 +580,11 @@ describe("Search", () => {
const searchContext = new SearchContext();
let searchResults = searchService.findNotesWithQuery('# not(#capital) and note.noteId != root', searchContext);
let searchResults = searchService.findResultsWithQuery('# not(#capital) and note.noteId != root', searchContext);
expect(searchResults.length).toEqual(1);
expect(becca.notes[searchResults[0].noteId].title).toEqual("Europe");
searchResults = searchService.findNotesWithQuery('#!capital and note.noteId != root', searchContext);
searchResults = searchService.findResultsWithQuery('#!capital and note.noteId != root', searchContext);
expect(searchResults.length).toEqual(1);
expect(becca.notes[searchResults[0].noteId].title).toEqual("Europe");
});
@ -600,7 +600,7 @@ describe("Search", () => {
const searchContext = new SearchContext();
let searchResults = searchService.findNotesWithQuery('# note.text *=* vaki and note.noteId != root', searchContext);
let searchResults = searchService.findResultsWithQuery('# note.text *=* vaki and note.noteId != root', searchContext);
expect(searchResults.length).toEqual(1);
expect(becca.notes[searchResults[0].noteId].title).toEqual("Slovakia");
});
@ -617,7 +617,7 @@ describe("Search", () => {
const searchContext = new SearchContext({excludeArchived: true});
let searchResults = searchService.findNotesWithQuery('reddit', searchContext);
let searchResults = searchService.findResultsWithQuery('reddit', searchContext);
expect(searchResults.length).toEqual(1);
expect(becca.notes[searchResults[0].noteId].title).toEqual("Reddit is bad");
});
@ -640,7 +640,7 @@ describe("Search", () => {
//
// const searchContext = new SearchContext();
//
// const searchResults = searchService.findNotesWithQuery('#capital = #largestCity', searchContext);
// const searchResults = searchService.findResultsWithQuery('#capital = #largestCity', searchContext);
// expect(searchResults.length).toEqual(2);
// expect(findNoteByTitle(searchResults, "Czech Republic")).toBeTruthy();
// expect(findNoteByTitle(searchResults, "Austria")).toBeTruthy();

View file

@ -21,6 +21,7 @@ function setupGlobs() {
window.glob.ESLINT = libraryLoader.ESLINT;
window.glob.appContext = appContext; // for debugging
window.glob.froca = froca;
window.glob.treeCache = froca; // compatibility for CKEditor builds for a while
// for CKEditor integration (button on block toolbar)
window.glob.importMarkdownInline = async () => {

View file

@ -3,6 +3,7 @@
const optionService = require('../../services/options');
const log = require('../../services/log');
const attributes = require('../../services/attributes');
const searchService = require('../../services/search/services/search');
// options allowed to be updated directly in options dialog
const ALLOWED_OPTIONS = new Set([
@ -91,8 +92,7 @@ function update(name, value) {
}
function getUserThemes() {
const notes = attributes.getNotesWithLabel('appTheme');
const notes = searchService.findNotes("#appTheme");
const ret = [];
for (const note of notes) {

View file

@ -28,7 +28,7 @@ async function searchFromNoteInt(note) {
fuzzyAttributeSearch: false
});
searchResultNoteIds = searchService.findNotesWithQuery(searchString, searchContext)
searchResultNoteIds = searchService.findResultsWithQuery(searchString, searchContext)
.map(sr => sr.noteId);
}
@ -215,7 +215,7 @@ function quickSearch(req) {
fuzzyAttributeSearch: false
});
return searchService.findNotesWithQuery(searchString, searchContext)
return searchService.findResultsWithQuery(searchString, searchContext)
.map(sr => sr.noteId);
}
@ -229,7 +229,7 @@ function search(req) {
ignoreHoistedNote: true
});
return searchService.findNotesWithQuery(searchString, searchContext)
return searchService.findResultsWithQuery(searchString, searchContext)
.map(sr => sr.noteId);
}
@ -242,8 +242,8 @@ function getRelatedNotes(req) {
fuzzyAttributeSearch: false
};
const matchingNameAndValue = searchService.findNotesWithQuery(formatAttrForSearch(attr, true), new SearchContext(searchSettings));
const matchingName = searchService.findNotesWithQuery(formatAttrForSearch(attr, false), new SearchContext(searchSettings));
const matchingNameAndValue = searchService.findResultsWithQuery(formatAttrForSearch(attr, true), new SearchContext(searchSettings));
const matchingName = searchService.findResultsWithQuery(formatAttrForSearch(attr, false), new SearchContext(searchSettings));
const results = [];

View file

@ -67,7 +67,7 @@ function getNotesWithLabel(name, value) {
params.push(value);
}
return repository.getEntities(`SELECT notes.* FROM notes JOIN attributes USING(noteId)
return repository.getEntities(`SELECT notes.* FROM notes JOIN attributes USING(noteId)
WHERE notes.isDeleted = 0 AND attributes.isDeleted = 0 AND attributes.name = ? ${valueCondition} ORDER BY position`, params);
}

View file

@ -110,7 +110,7 @@ function BackendScriptApi(currentNote, apiParams) {
searchParams.ignoreHoistedNote = true;
}
const noteIds = searchService.findNotesWithQuery(query, new SearchContext(searchParams))
const noteIds = searchService.findResultsWithQuery(query, new SearchContext(searchParams))
.map(sr => sr.noteId);
return repository.getNotes(noteIds);

View file

@ -22,7 +22,7 @@ function load() {
}
for (const row of sql.iterateRows(`SELECT branchId, noteId, parentNoteId, prefix, notePosition, isExpanded FROM branches WHERE isDeleted = 0`, [])) {
const branch = new Branch(becca, row);
new Branch(becca, row);
}
for (const row of sql.iterateRows(`SELECT attributeId, noteId, type, name, value, isInheritable, position FROM attributes WHERE isDeleted = 0`, [])) {
@ -66,7 +66,7 @@ eventService.subscribe([eventService.ENTITY_CHANGED, eventService.ENTITY_DELETED
childNote.parentBranches = childNote.parentBranches.filter(branch => branch.branchId !== branchId);
if (childNote.parents.length > 0) {
childNote.invalidateSubfrocas();
childNote.invalidateSubTree();
}
}
@ -105,7 +105,7 @@ eventService.subscribe([eventService.ENTITY_CHANGED, eventService.ENTITY_DELETED
if (note && attr) {
// first invalidate and only then remove the attribute (otherwise invalidation wouldn't be complete)
if (attr.isAffectingSubtree || note.isTemplate) {
note.invalidateSubfrocas();
note.invalidateSubTree();
} else {
note.invalidateThisCache();
}
@ -147,7 +147,7 @@ eventService.subscribe([eventService.ENTITY_CHANGED, eventService.ENTITY_DELETED
if (note) {
if (attr.isAffectingSubtree || note.isTemplate) {
note.invalidateSubfrocas();
note.invalidateSubTree();
}
else {
note.invalidateThisCache();

View file

@ -3,6 +3,9 @@
const protectedSessionService = require('../../protected_session');
const log = require('../../log');
const LABEL = 'label';
const RELATION = 'relation';
class Note {
constructor(becca, row) {
/** @param {Becca} */
@ -153,26 +156,126 @@ class Note {
&& (!value || attr.value.toLowerCase() === value));
}
hasLabel(name) {
return this.hasAttribute('label', name);
}
hasRelation(name) {
return this.hasAttribute('relation', name);
}
getLabelValue(name) {
const label = this.attributes.find(attr => attr.type === 'label' && attr.name === name);
return label ? label.value : null;
}
getRelationTarget(name) {
const relation = this.attributes.find(attr => attr.type === 'relation' && attr.name === name);
return relation ? relation.targetNote : null;
}
/**
* @param {string} name - label name
* @returns {boolean} true if label exists (including inherited)
*/
hasLabel(name) { return this.hasAttribute(LABEL, name); }
/**
* @param {string} name - label name
* @returns {boolean} true if label exists (excluding inherited)
*/
hasOwnedLabel(name) { return this.hasOwnedAttribute(LABEL, name); }
/**
* @param {string} name - relation name
* @returns {boolean} true if relation exists (including inherited)
*/
hasRelation(name) { return this.hasAttribute(RELATION, name); }
/**
* @param {string} name - relation name
* @returns {boolean} true if relation exists (excluding inherited)
*/
hasOwnedRelation(name) { return this.hasOwnedAttribute(RELATION, name); }
/**
* @param {string} name - label name
* @returns {Attribute|null} label if it exists, null otherwise
*/
getLabel(name) { return this.getAttribute(LABEL, name); }
/**
* @param {string} name - label name
* @returns {Attribute|null} label if it exists, null otherwise
*/
getOwnedLabel(name) { return this.getOwnedAttribute(LABEL, name); }
/**
* @param {string} name - relation name
* @returns {Attribute|null} relation if it exists, null otherwise
*/
getRelation(name) { return this.getAttribute(RELATION, name); }
/**
* @param {string} name - relation name
* @returns {Attribute|null} relation if it exists, null otherwise
*/
getOwnedRelation(name) { return this.getOwnedAttribute(RELATION, name); }
/**
* @param {string} name - label name
* @returns {string|null} label value if label exists, null otherwise
*/
getLabelValue(name) { return this.getAttributeValue(LABEL, name); }
/**
* @param {string} name - label name
* @returns {string|null} label value if label exists, null otherwise
*/
getOwnedLabelValue(name) { return this.getOwnedAttributeValue(LABEL, name); }
/**
* @param {string} name - relation name
* @returns {string|null} relation value if relation exists, null otherwise
*/
getRelationValue(name) { return this.getAttributeValue(RELATION, name); }
/**
* @param {string} name - relation name
* @returns {string|null} relation value if relation exists, null otherwise
*/
getOwnedRelationValue(name) { return this.getOwnedAttributeValue(RELATION, name); }
/**
* @param {string} type - attribute type (label, relation, etc.)
* @param {string} name - attribute name
* @returns {boolean} true if note has an attribute with given type and name (excluding inherited)
*/
hasOwnedAttribute(type, name) {
return !!this.getOwnedAttribute(type, name);
}
/**
* @param {string} type - attribute type (label, relation, etc.)
* @param {string} name - attribute name
* @returns {Attribute} attribute of given type and name. If there's more such attributes, first is returned. Returns null if there's no such attribute belonging to this note.
*/
getAttribute(type, name) {
const attributes = this.getAttributes();
return attributes.find(attr => attr.type === type && attr.name === name);
}
/**
* @param {string} type - attribute type (label, relation, etc.)
* @param {string} name - attribute name
* @returns {string|null} attribute value of given type and name or null if no such attribute exists.
*/
getAttributeValue(type, name) {
const attr = this.getAttribute(type, name);
return attr ? attr.value : null;
}
/**
* @param {string} type - attribute type (label, relation, etc.)
* @param {string} name - attribute name
* @returns {string|null} attribute value of given type and name or null if no such attribute exists.
*/
getOwnedAttributeValue(type, name) {
const attr = this.getOwnedAttribute(type, name);
return attr ? attr.value : null;
}
get isArchived() {
return this.hasAttribute('label', 'archived');
}
@ -235,7 +338,7 @@ class Note {
this.ancestorCache = null;
}
invalidateSubfrocas(path = []) {
invalidateSubTree(path = []) {
if (path.includes(this.noteId)) {
return;
}
@ -247,7 +350,7 @@ class Note {
}
for (const childNote of this.children) {
childNote.invalidateSubfrocas(path);
childNote.invalidateSubTree(path);
}
for (const targetRelation of this.targetRelations) {
@ -255,7 +358,7 @@ class Note {
const note = targetRelation.note;
if (note) {
note.invalidateSubfrocas(path);
note.invalidateSubTree(path);
}
}
}
@ -423,6 +526,10 @@ class Note {
return minDistance;
}
getChildBranches() {
return this.children.map(childNote => this.becca.getBranch(childNote.noteId, this.noteId));
}
decrypt() {
if (this.isProtected && !this.isDecrypted && protectedSessionService.isProtectedSessionAvailable()) {
try {

View file

@ -17,15 +17,19 @@ const attributeService = require('../services/attributes');
const request = require('./request');
const path = require('path');
const url = require('url');
const becca = require('../services/becca/becca');
function getNewNotePosition(parentNoteId) {
const maxNotePos = sql.getValue(`
SELECT MAX(notePosition)
FROM branches
WHERE parentNoteId = ?
AND isDeleted = 0`, [parentNoteId]);
const note = becca.notes[parentNoteId];
return maxNotePos === null ? 0 : maxNotePos + 10;
if (!note) {
throw new Error(`Can't find note ${parentNoteId}`);
}
const maxNotePos = note.getChildBranches()
.reduce((max, note) => Math.max(max, note.notePosition), 0);
return maxNotePos + 10;
}
function triggerChildNoteCreated(childNote, parentNote) {
@ -151,7 +155,7 @@ function createNewNoteWithTarget(target, targetBranchId, params) {
return createNewNote(params);
}
else if (target === 'after') {
const afterNote = sql.getRow('SELECT notePosition FROM branches WHERE branchId = ?', [targetBranchId]);
const afterNote = becca.branches[targetBranchId].notePosition;
// not updating utcDateModified to avoig having to sync whole rows
sql.execute('UPDATE branches SET notePosition = notePosition + 10 WHERE parentNoteId = ? AND notePosition > ? AND isDeleted = 0',

View file

@ -63,7 +63,7 @@ function loadNeededInfoFromDatabase() {
* @param {SearchContext} searchContext
* @return {SearchResult[]}
*/
function findNotesWithExpression(expression, searchContext) {
function findResultsWithExpression(expression, searchContext) {
let allNotes = Object.values(becca.notes);
if (searchContext.dbLoadNeeded) {
@ -132,12 +132,22 @@ function parseQueryToExpression(query, searchContext) {
return expression;
}
/**
* @param {string} query
* @return {Note[]}
*/
function findNotes(query) {
const searchResults = findResultsWithQuery(query, new SearchContext());
return searchResults.map(sr => becca.notes[sr.noteId]);
}
/**
* @param {string} query
* @param {SearchContext} searchContext
* @return {SearchResult[]}
*/
function findNotesWithQuery(query, searchContext) {
function findResultsWithQuery(query, searchContext) {
query = query || "";
searchContext.originalQuery = query;
@ -147,11 +157,11 @@ function findNotesWithQuery(query, searchContext) {
return [];
}
return findNotesWithExpression(expression, searchContext);
return findResultsWithExpression(expression, searchContext);
}
function searchTrimmedNotes(query, searchContext) {
const allSearchResults = findNotesWithQuery(query, searchContext);
const allSearchResults = findResultsWithQuery(query, searchContext);
const trimmedSearchResults = allSearchResults.slice(0, 200);
return {
@ -252,5 +262,6 @@ function formatAttribute(attr) {
module.exports = {
searchTrimmedNotes,
searchNotesForAutocomplete,
findNotesWithQuery
findResultsWithQuery,
findNotes
};