mirror of
https://github.com/zadam/trilium.git
synced 2025-06-06 18:08:33 +02:00
basic note creation with becca
This commit is contained in:
parent
8d8d654fe8
commit
6c5b1420d2
@ -1,5 +1,9 @@
|
|||||||
"use strict";
|
"use strict";
|
||||||
|
|
||||||
|
const utils = require('../../utils');
|
||||||
|
|
||||||
|
let repo = null;
|
||||||
|
|
||||||
class AbstractEntity {
|
class AbstractEntity {
|
||||||
beforeSaving() {
|
beforeSaving() {
|
||||||
this.generateIdIfNecessary();
|
this.generateIdIfNecessary();
|
||||||
@ -27,7 +31,7 @@ class AbstractEntity {
|
|||||||
|
|
||||||
get repository() {
|
get repository() {
|
||||||
if (!repo) {
|
if (!repo) {
|
||||||
repo = require('../services/repository');
|
repo = require('../../repository');
|
||||||
}
|
}
|
||||||
|
|
||||||
return repo;
|
return repo;
|
||||||
|
@ -113,7 +113,7 @@ class Attribute extends AbstractEntity {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
get pojo() {
|
getPojo() {
|
||||||
return {
|
return {
|
||||||
attributeId: this.attributeId,
|
attributeId: this.attributeId,
|
||||||
noteId: this.noteId,
|
noteId: this.noteId,
|
||||||
|
@ -65,15 +65,25 @@ class Branch extends AbstractEntity {
|
|||||||
return this.becca.notes[this.parentNoteId];
|
return this.becca.notes[this.parentNoteId];
|
||||||
}
|
}
|
||||||
|
|
||||||
get pojo() {
|
getPojo() {
|
||||||
return {
|
const pojo = {
|
||||||
branchId: this.branchId,
|
branchId: this.branchId,
|
||||||
noteId: this.noteId,
|
noteId: this.noteId,
|
||||||
parentNoteId: this.parentNoteId,
|
parentNoteId: this.parentNoteId,
|
||||||
prefix: this.prefix,
|
prefix: this.prefix,
|
||||||
notePosition: this.notePosition,
|
notePosition: this.notePosition,
|
||||||
isExpanded: this.isExpanded
|
isExpanded: this.isExpanded,
|
||||||
|
utcDateModified: dateUtils.utcNowDateTime()
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// FIXME
|
||||||
|
if (true || !pojo.branchId) {
|
||||||
|
pojo.utcDateCreated = dateUtils.utcNowDateTime();
|
||||||
|
}
|
||||||
|
|
||||||
|
this.utcDateModified = dateUtils.utcNowDateTime();
|
||||||
|
|
||||||
|
return pojo;
|
||||||
}
|
}
|
||||||
|
|
||||||
createClone(parentNoteId, notePosition) {
|
createClone(parentNoteId, notePosition) {
|
||||||
@ -96,13 +106,7 @@ class Branch extends AbstractEntity {
|
|||||||
this.isExpanded = false;
|
this.isExpanded = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!this.branchId) {
|
|
||||||
this.utcDateCreated = dateUtils.utcNowDateTime();
|
|
||||||
}
|
|
||||||
|
|
||||||
super.beforeSaving();
|
super.beforeSaving();
|
||||||
|
|
||||||
this.utcDateModified = dateUtils.utcNowDateTime();
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -34,7 +34,7 @@ class Note extends AbstractEntity {
|
|||||||
this.ownedAttributes = [];
|
this.ownedAttributes = [];
|
||||||
|
|
||||||
/** @param {Attribute[]|null} */
|
/** @param {Attribute[]|null} */
|
||||||
this.attributeCache = null;
|
this.__attributeCache = null;
|
||||||
/** @param {Attribute[]|null} */
|
/** @param {Attribute[]|null} */
|
||||||
this.inheritableAttributeCache = null;
|
this.inheritableAttributeCache = null;
|
||||||
|
|
||||||
@ -89,6 +89,18 @@ class Note extends AbstractEntity {
|
|||||||
this.flatTextCache = null;
|
this.flatTextCache = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
getParentBranches() {
|
||||||
|
return this.parentBranches;
|
||||||
|
}
|
||||||
|
|
||||||
|
getParentNotes() {
|
||||||
|
return this.parents;
|
||||||
|
}
|
||||||
|
|
||||||
|
getChildrenNotes() {
|
||||||
|
return this.children;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Note content has quite special handling - it's not a separate entity, but a lazily loaded
|
* Note content has quite special handling - it's not a separate entity, but a lazily loaded
|
||||||
* part of Note entity with it's own sync. Reasons behind this hybrid design has been:
|
* part of Note entity with it's own sync. Reasons behind this hybrid design has been:
|
||||||
@ -245,9 +257,26 @@ class Note extends AbstractEntity {
|
|||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** @return {Attribute[]} */
|
/**
|
||||||
get attributes() {
|
* @param {string} [type] - (optional) attribute type to filter
|
||||||
return this.__getAttributes([]);
|
* @param {string} [name] - (optional) attribute name to filter
|
||||||
|
* @returns {Attribute[]} all note's attributes, including inherited ones
|
||||||
|
*/
|
||||||
|
getAttributes(type, name) {
|
||||||
|
this.__getAttributes([]);
|
||||||
|
|
||||||
|
if (type && name) {
|
||||||
|
return this.__attributeCache.filter(attr => attr.type === type && attr.name === name);
|
||||||
|
}
|
||||||
|
else if (type) {
|
||||||
|
return this.__attributeCache.filter(attr => attr.type === type);
|
||||||
|
}
|
||||||
|
else if (name) {
|
||||||
|
return this.__attributeCache.filter(attr => attr.name === name);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
return this.__attributeCache.slice();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
__getAttributes(path) {
|
__getAttributes(path) {
|
||||||
@ -255,7 +284,7 @@ class Note extends AbstractEntity {
|
|||||||
return [];
|
return [];
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!this.attributeCache) {
|
if (!this.__attributeCache) {
|
||||||
const parentAttributes = this.ownedAttributes.slice();
|
const parentAttributes = this.ownedAttributes.slice();
|
||||||
const newPath = [...path, this.noteId];
|
const newPath = [...path, this.noteId];
|
||||||
|
|
||||||
@ -277,7 +306,7 @@ class Note extends AbstractEntity {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
this.attributeCache = [];
|
this.__attributeCache = [];
|
||||||
|
|
||||||
const addedAttributeIds = new Set();
|
const addedAttributeIds = new Set();
|
||||||
|
|
||||||
@ -285,20 +314,20 @@ class Note extends AbstractEntity {
|
|||||||
if (!addedAttributeIds.has(attr.attributeId)) {
|
if (!addedAttributeIds.has(attr.attributeId)) {
|
||||||
addedAttributeIds.add(attr.attributeId);
|
addedAttributeIds.add(attr.attributeId);
|
||||||
|
|
||||||
this.attributeCache.push(attr);
|
this.__attributeCache.push(attr);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
this.inheritableAttributeCache = [];
|
this.inheritableAttributeCache = [];
|
||||||
|
|
||||||
for (const attr of this.attributeCache) {
|
for (const attr of this.__attributeCache) {
|
||||||
if (attr.isInheritable) {
|
if (attr.isInheritable) {
|
||||||
this.inheritableAttributeCache.push(attr);
|
this.inheritableAttributeCache.push(attr);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return this.attributeCache;
|
return this.__attributeCache;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** @return {Attribute[]} */
|
/** @return {Attribute[]} */
|
||||||
@ -315,21 +344,21 @@ class Note extends AbstractEntity {
|
|||||||
}
|
}
|
||||||
|
|
||||||
hasAttribute(type, name) {
|
hasAttribute(type, name) {
|
||||||
return !!this.attributes.find(attr => attr.type === type && attr.name === name);
|
return !!this.getAttributes().find(attr => attr.type === type && attr.name === name);
|
||||||
}
|
}
|
||||||
|
|
||||||
getAttributeCaseInsensitive(type, name, value) {
|
getAttributeCaseInsensitive(type, name, value) {
|
||||||
name = name.toLowerCase();
|
name = name.toLowerCase();
|
||||||
value = value ? value.toLowerCase() : null;
|
value = value ? value.toLowerCase() : null;
|
||||||
|
|
||||||
return this.attributes.find(
|
return this.getAttributes().find(
|
||||||
attr => attr.type === type
|
attr => attr.type === type
|
||||||
&& attr.name.toLowerCase() === name
|
&& attr.name.toLowerCase() === name
|
||||||
&& (!value || attr.value.toLowerCase() === value));
|
&& (!value || attr.value.toLowerCase() === value));
|
||||||
}
|
}
|
||||||
|
|
||||||
getRelationTarget(name) {
|
getRelationTarget(name) {
|
||||||
const relation = this.attributes.find(attr => attr.type === 'relation' && attr.name === name);
|
const relation = this.getAttributes().find(attr => attr.type === 'relation' && attr.name === name);
|
||||||
|
|
||||||
return relation ? relation.targetNote : null;
|
return relation ? relation.targetNote : null;
|
||||||
}
|
}
|
||||||
@ -448,6 +477,54 @@ class Note extends AbstractEntity {
|
|||||||
return attr ? attr.value : null;
|
return attr ? attr.value : null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param {string} [name] - label name to filter
|
||||||
|
* @returns {Attribute[]} all note's labels (attributes with type label), including inherited ones
|
||||||
|
*/
|
||||||
|
getLabels(name) {
|
||||||
|
return this.getAttributes(LABEL, name);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param {string} [name] - label name to filter
|
||||||
|
* @returns {string[]} all note's label values, including inherited ones
|
||||||
|
*/
|
||||||
|
getLabelValues(name) {
|
||||||
|
return this.getLabels(name).map(l => l.value);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param {string} [name] - label name to filter
|
||||||
|
* @returns {Attribute[]} all note's labels (attributes with type label), excluding inherited ones
|
||||||
|
*/
|
||||||
|
getOwnedLabels(name) {
|
||||||
|
return this.getOwnedAttributes(LABEL, name);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param {string} [name] - label name to filter
|
||||||
|
* @returns {string[]} all note's label values, excluding inherited ones
|
||||||
|
*/
|
||||||
|
getOwnedLabelValues(name) {
|
||||||
|
return this.getOwnedAttributes(LABEL, name).map(l => l.value);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param {string} [name] - relation name to filter
|
||||||
|
* @returns {Attribute[]} all note's relations (attributes with type relation), including inherited ones
|
||||||
|
*/
|
||||||
|
getRelations(name) {
|
||||||
|
return this.getAttributes(RELATION, name);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param {string} [name] - relation name to filter
|
||||||
|
* @returns {Attribute[]} all note's relations (attributes with type relation), excluding inherited ones
|
||||||
|
*/
|
||||||
|
getOwnedRelations(name) {
|
||||||
|
return this.getOwnedAttributes(RELATION, name);
|
||||||
|
}
|
||||||
|
|
||||||
get isArchived() {
|
get isArchived() {
|
||||||
return this.hasAttribute('label', 'archived');
|
return this.hasAttribute('label', 'archived');
|
||||||
}
|
}
|
||||||
@ -485,7 +562,7 @@ class Note extends AbstractEntity {
|
|||||||
|
|
||||||
this.flatTextCache += this.title + ' ';
|
this.flatTextCache += this.title + ' ';
|
||||||
|
|
||||||
for (const attr of this.attributes) {
|
for (const attr of this.getAttributes()) {
|
||||||
// it's best to use space as separator since spaces are filtered from the search string by the tokenization into words
|
// it's best to use space as separator since spaces are filtered from the search string by the tokenization into words
|
||||||
this.flatTextCache += (attr.type === 'label' ? '#' : '~') + attr.name;
|
this.flatTextCache += (attr.type === 'label' ? '#' : '~') + attr.name;
|
||||||
|
|
||||||
@ -505,7 +582,7 @@ class Note extends AbstractEntity {
|
|||||||
invalidateThisCache() {
|
invalidateThisCache() {
|
||||||
this.flatTextCache = null;
|
this.flatTextCache = null;
|
||||||
|
|
||||||
this.attributeCache = null;
|
this.__attributeCache = null;
|
||||||
this.inheritableAttributeCache = null;
|
this.inheritableAttributeCache = null;
|
||||||
this.ancestorCache = null;
|
this.ancestorCache = null;
|
||||||
}
|
}
|
||||||
@ -604,7 +681,7 @@ class Note extends AbstractEntity {
|
|||||||
}
|
}
|
||||||
|
|
||||||
get labelCount() {
|
get labelCount() {
|
||||||
return this.attributes.filter(attr => attr.type === 'label').length;
|
return this.getAttributes().filter(attr => attr.type === 'label').length;
|
||||||
}
|
}
|
||||||
|
|
||||||
get ownedLabelCount() {
|
get ownedLabelCount() {
|
||||||
@ -612,11 +689,11 @@ class Note extends AbstractEntity {
|
|||||||
}
|
}
|
||||||
|
|
||||||
get relationCount() {
|
get relationCount() {
|
||||||
return this.attributes.filter(attr => attr.type === 'relation' && !attr.isAutoLink()).length;
|
return this.getAttributes().filter(attr => attr.type === 'relation' && !attr.isAutoLink()).length;
|
||||||
}
|
}
|
||||||
|
|
||||||
get relationCountIncludingLinks() {
|
get relationCountIncludingLinks() {
|
||||||
return this.attributes.filter(attr => attr.type === 'relation').length;
|
return this.getAttributes().filter(attr => attr.type === 'relation').length;
|
||||||
}
|
}
|
||||||
|
|
||||||
get ownedRelationCount() {
|
get ownedRelationCount() {
|
||||||
@ -636,11 +713,11 @@ class Note extends AbstractEntity {
|
|||||||
}
|
}
|
||||||
|
|
||||||
get attributeCount() {
|
get attributeCount() {
|
||||||
return this.attributes.length;
|
return this.getAttributes().length;
|
||||||
}
|
}
|
||||||
|
|
||||||
get ownedAttributeCount() {
|
get ownedAttributeCount() {
|
||||||
return this.attributes.length;
|
return this.getAttributes().length;
|
||||||
}
|
}
|
||||||
|
|
||||||
get ancestors() {
|
get ancestors() {
|
||||||
@ -715,8 +792,8 @@ class Note extends AbstractEntity {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
get pojo() {
|
getPojo() {
|
||||||
return {
|
const pojo = {
|
||||||
noteId: this.noteId,
|
noteId: this.noteId,
|
||||||
title: this.title,
|
title: this.title,
|
||||||
isProtected: this.isProtected,
|
isProtected: this.isProtected,
|
||||||
@ -727,6 +804,18 @@ class Note extends AbstractEntity {
|
|||||||
utcDateCreated: this.utcDateCreated,
|
utcDateCreated: this.utcDateCreated,
|
||||||
utcDateModified: this.utcDateModified
|
utcDateModified: this.utcDateModified
|
||||||
};
|
};
|
||||||
|
|
||||||
|
if (pojo.isProtected) {
|
||||||
|
if (this.isDecrypted) {
|
||||||
|
pojo.title = protectedSessionService.encrypt(pojo.title);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
// updating protected note outside of protected session means we will keep original ciphertexts
|
||||||
|
delete pojo.title;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return pojo;
|
||||||
}
|
}
|
||||||
|
|
||||||
beforeSaving() {
|
beforeSaving() {
|
||||||
@ -744,16 +833,8 @@ class Note extends AbstractEntity {
|
|||||||
this.utcDateModified = dateUtils.utcNowDateTime();
|
this.utcDateModified = dateUtils.utcNowDateTime();
|
||||||
}
|
}
|
||||||
|
|
||||||
updatePojo(pojo) {
|
markAsDeleted() {
|
||||||
if (pojo.isProtected) {
|
sql.execute("UPDATE notes SET isDeleted = 1 WHERE noteId = ?", [this.noteId]);
|
||||||
if (this.isDecrypted) {
|
|
||||||
pojo.title = protectedSessionService.encrypt(pojo.title);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
// updating protected note outside of protected session means we will keep original ciphertexts
|
|
||||||
delete pojo.title;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -73,7 +73,7 @@ function buildRewardMap(note) {
|
|||||||
addToRewardMap(ancestorNote.title, 0.3);
|
addToRewardMap(ancestorNote.title, 0.3);
|
||||||
}
|
}
|
||||||
|
|
||||||
for (const branch of ancestorNote.parentBranches) {
|
for (const branch of ancestorNote.getParentBranches()) {
|
||||||
addToRewardMap(branch.prefix, 0.3);
|
addToRewardMap(branch.prefix, 0.3);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -84,11 +84,11 @@ function buildRewardMap(note) {
|
|||||||
addToRewardMap(note.title, 1);
|
addToRewardMap(note.title, 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
for (const branch of note.parentBranches) {
|
for (const branch of note.getParentBranches()) {
|
||||||
addToRewardMap(branch.prefix, 1);
|
addToRewardMap(branch.prefix, 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
for (const attr of note.attributes) {
|
for (const attr of note.getAttributes()) {
|
||||||
if (attr.name.startsWith('child:')
|
if (attr.name.startsWith('child:')
|
||||||
|| attr.name.startsWith('relation:')
|
|| attr.name.startsWith('relation:')
|
||||||
|| attr.name.startsWith('label:')) {
|
|| attr.name.startsWith('label:')) {
|
||||||
@ -222,7 +222,7 @@ function splitToWords(text) {
|
|||||||
* that it doesn't actually need to be shown to the user.
|
* that it doesn't actually need to be shown to the user.
|
||||||
*/
|
*/
|
||||||
function hasConnectingRelation(sourceNote, targetNote) {
|
function hasConnectingRelation(sourceNote, targetNote) {
|
||||||
return sourceNote.attributes.find(attr => attr.type === 'relation'
|
return sourceNote.getAttributes().find(attr => attr.type === 'relation'
|
||||||
&& ['includenotelink', 'imagelink'].includes(attr.name)
|
&& ['includenotelink', 'imagelink'].includes(attr.name)
|
||||||
&& attr.value === targetNote.noteId);
|
&& attr.value === targetNote.noteId);
|
||||||
}
|
}
|
||||||
@ -243,7 +243,7 @@ async function findSimilarNotes(noteId) {
|
|||||||
dateLimits = buildDateLimits(baseNote);
|
dateLimits = buildDateLimits(baseNote);
|
||||||
}
|
}
|
||||||
catch (e) {
|
catch (e) {
|
||||||
throw new Error(`Date limits failed with ${e.message}, entity: ${JSON.stringify(baseNote.pojo)}`);
|
throw new Error(`Date limits failed with ${e.message}, entity: ${JSON.stringify(baseNote.getPojo())}`);
|
||||||
}
|
}
|
||||||
|
|
||||||
const rewardMap = buildRewardMap(baseNote);
|
const rewardMap = buildRewardMap(baseNote);
|
||||||
@ -298,7 +298,7 @@ async function findSimilarNotes(noteId) {
|
|||||||
score += gatherRewards(parentNote.title, 0.3);
|
score += gatherRewards(parentNote.title, 0.3);
|
||||||
}
|
}
|
||||||
|
|
||||||
for (const branch of parentNote.parentBranches) {
|
for (const branch of parentNote.getParentBranches()) {
|
||||||
score += gatherRewards(branch.prefix, 0.3)
|
score += gatherRewards(branch.prefix, 0.3)
|
||||||
+ gatherAncestorRewards(branch.parentNote);
|
+ gatherAncestorRewards(branch.parentNote);
|
||||||
}
|
}
|
||||||
@ -319,11 +319,11 @@ async function findSimilarNotes(noteId) {
|
|||||||
score += gatherRewards(candidateNote.title);
|
score += gatherRewards(candidateNote.title);
|
||||||
}
|
}
|
||||||
|
|
||||||
for (const branch of candidateNote.parentBranches) {
|
for (const branch of candidateNote.getParentBranches()) {
|
||||||
score += gatherRewards(branch.prefix);
|
score += gatherRewards(branch.prefix);
|
||||||
}
|
}
|
||||||
|
|
||||||
for (const attr of candidateNote.attributes) {
|
for (const attr of candidateNote.getAttributes()) {
|
||||||
if (attr.name.startsWith('child:')
|
if (attr.name.startsWith('child:')
|
||||||
|| attr.name.startsWith('relation:')
|
|| attr.name.startsWith('relation:')
|
||||||
|| attr.name.startsWith('label:')) {
|
|| attr.name.startsWith('label:')) {
|
||||||
@ -342,7 +342,7 @@ async function findSimilarNotes(noteId) {
|
|||||||
let factor = 1;
|
let factor = 1;
|
||||||
|
|
||||||
if (!value.startsWith) {
|
if (!value.startsWith) {
|
||||||
log.info(`Unexpected falsy value for attribute ${JSON.stringify(attr.pojo)}`);
|
log.info(`Unexpected falsy value for attribute ${JSON.stringify(attr.getPojo())}`);
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
else if (value.startsWith('http')) {
|
else if (value.startsWith('http')) {
|
||||||
@ -434,8 +434,6 @@ async function findSimilarNotes(noteId) {
|
|||||||
for (const {noteId} of results) {
|
for (const {noteId} of results) {
|
||||||
const note = becca.notes[noteId];
|
const note = becca.notes[noteId];
|
||||||
|
|
||||||
console.log("NOTE", note.pojo);
|
|
||||||
|
|
||||||
displayRewards = true;
|
displayRewards = true;
|
||||||
ancestorRewardCache = {}; // reset cache
|
ancestorRewardCache = {}; // reset cache
|
||||||
const totalReward = computeScore(note);
|
const totalReward = computeScore(note);
|
||||||
|
@ -7,8 +7,11 @@ const eventService = require('./events');
|
|||||||
const repository = require('./repository');
|
const repository = require('./repository');
|
||||||
const cls = require('../services/cls');
|
const cls = require('../services/cls');
|
||||||
const Note = require('../entities/note');
|
const Note = require('../entities/note');
|
||||||
|
const BeccaNote = require('../services/becca/entities/note.js');
|
||||||
const Branch = require('../entities/branch');
|
const Branch = require('../entities/branch');
|
||||||
|
const BeccaBranch = require('../services/becca/entities/branch.js');
|
||||||
const Attribute = require('../entities/attribute');
|
const Attribute = require('../entities/attribute');
|
||||||
|
const BeccaAttribute = require('../services/becca/entities/attribute.js');
|
||||||
const protectedSessionService = require('../services/protected_session');
|
const protectedSessionService = require('../services/protected_session');
|
||||||
const log = require('../services/log');
|
const log = require('../services/log');
|
||||||
const utils = require('../services/utils');
|
const utils = require('../services/utils');
|
||||||
@ -67,7 +70,7 @@ function deriveMime(type, mime) {
|
|||||||
function copyChildAttributes(parentNote, childNote) {
|
function copyChildAttributes(parentNote, childNote) {
|
||||||
for (const attr of parentNote.getAttributes()) {
|
for (const attr of parentNote.getAttributes()) {
|
||||||
if (attr.name.startsWith("child:")) {
|
if (attr.name.startsWith("child:")) {
|
||||||
new Attribute({
|
new BeccaAttribute({
|
||||||
noteId: childNote.noteId,
|
noteId: childNote.noteId,
|
||||||
type: attr.type,
|
type: attr.type,
|
||||||
name: attr.name.substr(6),
|
name: attr.name.substr(6),
|
||||||
@ -75,8 +78,6 @@ function copyChildAttributes(parentNote, childNote) {
|
|||||||
position: attr.position,
|
position: attr.position,
|
||||||
isInheritable: attr.isInheritable
|
isInheritable: attr.isInheritable
|
||||||
}).save();
|
}).save();
|
||||||
|
|
||||||
childNote.invalidateAttributeCache();
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -99,7 +100,7 @@ function copyChildAttributes(parentNote, childNote) {
|
|||||||
* @return {{note: Note, branch: Branch}}
|
* @return {{note: Note, branch: Branch}}
|
||||||
*/
|
*/
|
||||||
function createNewNote(params) {
|
function createNewNote(params) {
|
||||||
const parentNote = repository.getNote(params.parentNoteId);
|
const parentNote = becca.notes[params.parentNoteId];
|
||||||
|
|
||||||
if (!parentNote) {
|
if (!parentNote) {
|
||||||
throw new Error(`Parent note "${params.parentNoteId}" not found.`);
|
throw new Error(`Parent note "${params.parentNoteId}" not found.`);
|
||||||
@ -110,7 +111,7 @@ function createNewNote(params) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
return sql.transactional(() => {
|
return sql.transactional(() => {
|
||||||
const note = new Note({
|
const note = new BeccaNote(becca,{
|
||||||
noteId: params.noteId, // optionally can force specific noteId
|
noteId: params.noteId, // optionally can force specific noteId
|
||||||
title: params.title,
|
title: params.title,
|
||||||
isProtected: !!params.isProtected,
|
isProtected: !!params.isProtected,
|
||||||
@ -120,7 +121,7 @@ function createNewNote(params) {
|
|||||||
|
|
||||||
note.setContent(params.content);
|
note.setContent(params.content);
|
||||||
|
|
||||||
const branch = new Branch({
|
const branch = new BeccaBranch(becca,{
|
||||||
noteId: note.noteId,
|
noteId: note.noteId,
|
||||||
parentNoteId: params.parentNoteId,
|
parentNoteId: params.parentNoteId,
|
||||||
notePosition: params.notePosition !== undefined ? params.notePosition : getNewNotePosition(params.parentNoteId),
|
notePosition: params.notePosition !== undefined ? params.notePosition : getNewNotePosition(params.parentNoteId),
|
||||||
@ -416,11 +417,12 @@ function saveLinks(note, content) {
|
|||||||
throw new Error("Unrecognized type " + note.type);
|
throw new Error("Unrecognized type " + note.type);
|
||||||
}
|
}
|
||||||
|
|
||||||
const existingLinks = note.getLinks();
|
const existingLinks = note.getRelations().filter(rel =>
|
||||||
|
['internalLink', 'imageLink', 'relationMapLink', 'includeNoteLink'].includes(rel.name));
|
||||||
|
|
||||||
for (const foundLink of foundLinks) {
|
for (const foundLink of foundLinks) {
|
||||||
const targetNote = repository.getNote(foundLink.value);
|
const targetNote = becca.notes[foundLink.value];
|
||||||
if (!targetNote || targetNote.isDeleted) {
|
if (!targetNote) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -429,7 +431,7 @@ function saveLinks(note, content) {
|
|||||||
&& existingLink.name === foundLink.name);
|
&& existingLink.name === foundLink.name);
|
||||||
|
|
||||||
if (!existingLink) {
|
if (!existingLink) {
|
||||||
const newLink = new Attribute({
|
const newLink = new BeccaAttribute({
|
||||||
noteId: note.noteId,
|
noteId: note.noteId,
|
||||||
type: 'relation',
|
type: 'relation',
|
||||||
name: foundLink.name,
|
name: foundLink.name,
|
||||||
@ -438,10 +440,6 @@ function saveLinks(note, content) {
|
|||||||
|
|
||||||
existingLinks.push(newLink);
|
existingLinks.push(newLink);
|
||||||
}
|
}
|
||||||
else if (existingLink.isDeleted) {
|
|
||||||
existingLink.isDeleted = false;
|
|
||||||
existingLink.save();
|
|
||||||
}
|
|
||||||
// else the link exists so we don't need to do anything
|
// else the link exists so we don't need to do anything
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -451,8 +449,7 @@ function saveLinks(note, content) {
|
|||||||
&& existingLink.name === foundLink.name));
|
&& existingLink.name === foundLink.name));
|
||||||
|
|
||||||
for (const unusedLink of unusedLinks) {
|
for (const unusedLink of unusedLinks) {
|
||||||
unusedLink.isDeleted = true;
|
unusedLink.markAsDeleted();
|
||||||
unusedLink.save();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return content;
|
return content;
|
||||||
|
@ -94,11 +94,19 @@ function updateEntity(entity) {
|
|||||||
entity.beforeSaving();
|
entity.beforeSaving();
|
||||||
}
|
}
|
||||||
|
|
||||||
const clone = Object.assign({}, entity);
|
let clone;
|
||||||
|
|
||||||
// this check requires that updatePojo is not static
|
if (entity.getPojo) {
|
||||||
if (entity.updatePojo) {
|
clone = entity.getPojo();
|
||||||
entity.updatePojo(clone);
|
}
|
||||||
|
else {
|
||||||
|
// FIXME: delete this branch after migration to becca
|
||||||
|
clone = Object.assign({}, entity);
|
||||||
|
|
||||||
|
// this check requires that updatePojo is not static
|
||||||
|
if (entity.updatePojo) {
|
||||||
|
entity.updatePojo(clone);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
for (const key in clone) {
|
for (const key in clone) {
|
||||||
|
Loading…
x
Reference in New Issue
Block a user