mirror of
				https://github.com/zadam/trilium.git
				synced 2025-10-31 18:36:30 +01:00 
			
		
		
		
	added querying by children
This commit is contained in:
		| @@ -17,11 +17,9 @@ describe("Search", () => { | |||||||
|     }); |     }); | ||||||
|  |  | ||||||
|     it("simple path match", async () => { |     it("simple path match", async () => { | ||||||
|         rootNote.child( |         rootNote | ||||||
|             note("Europe") |             .child(note("Europe") | ||||||
|                 .child( |                 .child(note("Austria")) | ||||||
|                     note("Austria") |  | ||||||
|                 ) |  | ||||||
|         ); |         ); | ||||||
|  |  | ||||||
|         const parsingContext = new ParsingContext(); |         const parsingContext = new ParsingContext(); | ||||||
| @@ -32,11 +30,9 @@ describe("Search", () => { | |||||||
|     }); |     }); | ||||||
|  |  | ||||||
|     it("only end leafs are results", async () => { |     it("only end leafs are results", async () => { | ||||||
|         rootNote.child( |         rootNote | ||||||
|             note("Europe") |             .child(note("Europe") | ||||||
|                 .child( |                 .child(note("Austria")) | ||||||
|                     note("Austria") |  | ||||||
|                 ) |  | ||||||
|         ); |         ); | ||||||
|  |  | ||||||
|         const parsingContext = new ParsingContext(); |         const parsingContext = new ParsingContext(); | ||||||
| @@ -47,12 +43,10 @@ describe("Search", () => { | |||||||
|     }); |     }); | ||||||
|  |  | ||||||
|     it("only end leafs are results", async () => { |     it("only end leafs are results", async () => { | ||||||
|         rootNote.child( |         rootNote | ||||||
|             note("Europe") |             .child(note("Europe") | ||||||
|                 .child( |                 .child(note("Austria") | ||||||
|                     note("Austria") |                     .label('capital', 'Vienna')) | ||||||
|                         .label('capital', 'Vienna') |  | ||||||
|                 ) |  | ||||||
|         ); |         ); | ||||||
|  |  | ||||||
|         const parsingContext = new ParsingContext(); |         const parsingContext = new ParsingContext(); | ||||||
| @@ -63,17 +57,13 @@ describe("Search", () => { | |||||||
|     }); |     }); | ||||||
|  |  | ||||||
|     it("numeric label comparison", async () => { |     it("numeric label comparison", async () => { | ||||||
|         rootNote.child( |         rootNote | ||||||
|             note("Europe") |             .child(note("Europe") | ||||||
|                 .label('country', '', true) |                 .label('country', '', true) | ||||||
|                 .child( |                 .child(note("Austria") | ||||||
|                     note("Austria") |                     .label('population', '8859000')) | ||||||
|                         .label('population', '8859000') |                 .child(note("Czech Republic") | ||||||
|                 ) |                     .label('population', '10650000')) | ||||||
|                 .child( |  | ||||||
|                     note("Czech Republic") |  | ||||||
|                         .label('population', '10650000') |  | ||||||
|                 ) |  | ||||||
|         ); |         ); | ||||||
|  |  | ||||||
|         const parsingContext = new ParsingContext(); |         const parsingContext = new ParsingContext(); | ||||||
| @@ -84,21 +74,15 @@ describe("Search", () => { | |||||||
|     }); |     }); | ||||||
|  |  | ||||||
|     it("numeric label comparison fallback to string comparison", async () => { |     it("numeric label comparison fallback to string comparison", async () => { | ||||||
|         rootNote.child( |         rootNote | ||||||
|             note("Europe") |             .child(note("Europe") | ||||||
|                 .label('country', '', true) |                 .label('country', '', true) | ||||||
|                 .child( |                 .child(note("Austria") | ||||||
|                     note("Austria") |                     .label('established', '1955-07-27')) | ||||||
|                         .label('established', '1955-07-27') |                 .child(note("Czech Republic") | ||||||
|                 ) |                     .label('established', '1993-01-01')) | ||||||
|                 .child( |                 .child(note("Hungary") | ||||||
|                     note("Czech Republic") |                     .label('established', '..wrong..')) | ||||||
|                         .label('established', '1993-01-01') |  | ||||||
|                 ) |  | ||||||
|                 .child( |  | ||||||
|                     note("Hungary") |  | ||||||
|                         .label('established', '..wrong..') |  | ||||||
|                 ) |  | ||||||
|         ); |         ); | ||||||
|  |  | ||||||
|         const parsingContext = new ParsingContext(); |         const parsingContext = new ParsingContext(); | ||||||
| @@ -109,21 +93,15 @@ describe("Search", () => { | |||||||
|     }); |     }); | ||||||
|  |  | ||||||
|     it("logical or", async () => { |     it("logical or", async () => { | ||||||
|         rootNote.child( |         rootNote | ||||||
|             note("Europe") |             .child(note("Europe") | ||||||
|                 .label('country', '', true) |                 .label('country', '', true) | ||||||
|                 .child( |                 .child(note("Austria") | ||||||
|                     note("Austria") |                     .label('languageFamily', 'germanic')) | ||||||
|                         .label('languageFamily', 'germanic') |                 .child(note("Czech Republic") | ||||||
|                 ) |                     .label('languageFamily', 'slavic')) | ||||||
|                 .child( |                 .child(note("Hungary") | ||||||
|                     note("Czech Republic") |                     .label('languageFamily', 'finnougric')) | ||||||
|                         .label('languageFamily', 'slavic') |  | ||||||
|                 ) |  | ||||||
|                 .child( |  | ||||||
|                     note("Hungary") |  | ||||||
|                         .label('languageFamily', 'finnougric') |  | ||||||
|                 ) |  | ||||||
|             ); |             ); | ||||||
|  |  | ||||||
|         const parsingContext = new ParsingContext(); |         const parsingContext = new ParsingContext(); | ||||||
| @@ -135,18 +113,13 @@ describe("Search", () => { | |||||||
|     }); |     }); | ||||||
|  |  | ||||||
|     it("fuzzy attribute search", async () => { |     it("fuzzy attribute search", async () => { | ||||||
|         rootNote.child( |         rootNote | ||||||
|             note("Europe") |             .child(note("Europe") | ||||||
|                 .label('country', '', true) |                 .label('country', '', true) | ||||||
|                 .child( |                 .child(note("Austria") | ||||||
|                     note("Austria") |                     .label('languageFamily', 'germanic')) | ||||||
|                         .label('languageFamily', 'germanic') |                 .child(note("Czech Republic") | ||||||
|                 ) |                     .label('languageFamily', 'slavic'))); | ||||||
|                 .child( |  | ||||||
|                     note("Czech Republic") |  | ||||||
|                         .label('languageFamily', 'slavic') |  | ||||||
|                 ) |  | ||||||
|         ); |  | ||||||
|  |  | ||||||
|         let parsingContext = new ParsingContext({fuzzyAttributeSearch: false}); |         let parsingContext = new ParsingContext({fuzzyAttributeSearch: false}); | ||||||
|  |  | ||||||
| @@ -167,15 +140,10 @@ describe("Search", () => { | |||||||
|     }); |     }); | ||||||
|  |  | ||||||
|     it("filter by note property", async () => { |     it("filter by note property", async () => { | ||||||
|         rootNote.child( |         rootNote | ||||||
|             note("Europe") |             .child(note("Europe") | ||||||
|                 .child( |                 .child(note("Austria")) | ||||||
|                     note("Austria") |                 .child(note("Czech Republic"))); | ||||||
|                 ) |  | ||||||
|                 .child( |  | ||||||
|                     note("Czech Republic") |  | ||||||
|                 ) |  | ||||||
|         ); |  | ||||||
|  |  | ||||||
|         const parsingContext = new ParsingContext(); |         const parsingContext = new ParsingContext(); | ||||||
|  |  | ||||||
| @@ -185,19 +153,12 @@ describe("Search", () => { | |||||||
|     }); |     }); | ||||||
|  |  | ||||||
|     it("filter by note's parent", async () => { |     it("filter by note's parent", async () => { | ||||||
|         rootNote.child( |         rootNote | ||||||
|             note("Europe") |             .child(note("Europe") | ||||||
|                 .child( |                 .child(note("Austria")) | ||||||
|                     note("Austria") |                 .child(note("Czech Republic"))) | ||||||
|                 ) |             .child(note("Asia") | ||||||
|                 .child( |                 .child(note('Taiwan'))); | ||||||
|                     note("Czech Republic") |  | ||||||
|                 ) |  | ||||||
|         ) |  | ||||||
|             .child( |  | ||||||
|                 note("Asia") |  | ||||||
|                     .child(note('Taiwan')) |  | ||||||
|             ); |  | ||||||
|  |  | ||||||
|         const parsingContext = new ParsingContext(); |         const parsingContext = new ParsingContext(); | ||||||
|  |  | ||||||
| @@ -210,6 +171,26 @@ describe("Search", () => { | |||||||
|         expect(searchResults.length).toEqual(1); |         expect(searchResults.length).toEqual(1); | ||||||
|         expect(findNoteByTitle(searchResults, "Taiwan")).toBeTruthy(); |         expect(findNoteByTitle(searchResults, "Taiwan")).toBeTruthy(); | ||||||
|     }); |     }); | ||||||
|  |  | ||||||
|  |     it("filter by note's child", async () => { | ||||||
|  |         rootNote | ||||||
|  |             .child(note("Europe") | ||||||
|  |                 .child(note("Austria")) | ||||||
|  |                 .child(note("Czech Republic"))) | ||||||
|  |             .child(note("Oceania") | ||||||
|  |                 .child(note('Australia'))); | ||||||
|  |  | ||||||
|  |         const parsingContext = new ParsingContext(); | ||||||
|  |  | ||||||
|  |         let searchResults = await searchService.findNotesWithQuery('# note.child.title =* Aust', parsingContext); | ||||||
|  |         expect(searchResults.length).toEqual(2); | ||||||
|  |         expect(findNoteByTitle(searchResults, "Europe")).toBeTruthy(); | ||||||
|  |         expect(findNoteByTitle(searchResults, "Oceania")).toBeTruthy(); | ||||||
|  |  | ||||||
|  |         searchResults = await searchService.findNotesWithQuery('# note.child.title =* Aust AND note.child.title *= republic', parsingContext); | ||||||
|  |         expect(searchResults.length).toEqual(1); | ||||||
|  |         expect(findNoteByTitle(searchResults, "Europe")).toBeTruthy(); | ||||||
|  |     }); | ||||||
| }); | }); | ||||||
|  |  | ||||||
| /** @return {Note} */ | /** @return {Note} */ | ||||||
|   | |||||||
							
								
								
									
										36
									
								
								src/services/search/expressions/parent_of.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										36
									
								
								src/services/search/expressions/parent_of.js
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,36 @@ | |||||||
|  | "use strict"; | ||||||
|  |  | ||||||
|  | const Expression = require('./expression'); | ||||||
|  | const NoteSet = require('../note_set'); | ||||||
|  |  | ||||||
|  | class ParentOfExp extends Expression { | ||||||
|  |     constructor(subExpression) { | ||||||
|  |         super(); | ||||||
|  |  | ||||||
|  |         this.subExpression = subExpression; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |     execute(inputNoteSet, searchContext) { | ||||||
|  |         const subInputNoteSet = new NoteSet(); | ||||||
|  |  | ||||||
|  |         for (const note of inputNoteSet.notes) { | ||||||
|  |             subInputNoteSet.addAll(note.children); | ||||||
|  |         } | ||||||
|  |  | ||||||
|  |         const subResNoteSet = this.subExpression.execute(subInputNoteSet, searchContext); | ||||||
|  |  | ||||||
|  |         const resNoteSet = new NoteSet(); | ||||||
|  |  | ||||||
|  |         for (const childNote of subResNoteSet.notes) { | ||||||
|  |             for (const parentNote of childNote.parents) { | ||||||
|  |                 if (inputNoteSet.hasNote(parentNote)) { | ||||||
|  |                     resNoteSet.add(parentNote); | ||||||
|  |                 } | ||||||
|  |             } | ||||||
|  |         } | ||||||
|  |  | ||||||
|  |         return resNoteSet; | ||||||
|  |     } | ||||||
|  | } | ||||||
|  |  | ||||||
|  | module.exports = ParentOfExp; | ||||||
| @@ -4,6 +4,7 @@ const AndExp = require('./expressions/and'); | |||||||
| const OrExp = require('./expressions/or'); | const OrExp = require('./expressions/or'); | ||||||
| const NotExp = require('./expressions/not'); | const NotExp = require('./expressions/not'); | ||||||
| const ChildOfExp = require('./expressions/child_of'); | const ChildOfExp = require('./expressions/child_of'); | ||||||
|  | const ParentOfExp = require('./expressions/parent_of'); | ||||||
| const PropertyComparisonExp = require('./expressions/property_comparison'); | const PropertyComparisonExp = require('./expressions/property_comparison'); | ||||||
| const AttributeExistsExp = require('./expressions/attribute_exists'); | const AttributeExistsExp = require('./expressions/attribute_exists'); | ||||||
| const LabelComparisonExp = require('./expressions/label_comparison'); | const LabelComparisonExp = require('./expressions/label_comparison'); | ||||||
| @@ -56,6 +57,12 @@ function getExpression(tokens, parsingContext) { | |||||||
|             return new ChildOfExp(parseNoteProperty()); |             return new ChildOfExp(parseNoteProperty()); | ||||||
|         } |         } | ||||||
|  |  | ||||||
|  |         if (tokens[i] === 'child') { | ||||||
|  |             i += 1; | ||||||
|  |  | ||||||
|  |             return new ParentOfExp(parseNoteProperty()); | ||||||
|  |         } | ||||||
|  |  | ||||||
|         if (tokens[i] === 'title') { |         if (tokens[i] === 'title') { | ||||||
|             const propertyName = tokens[i]; |             const propertyName = tokens[i]; | ||||||
|             const operator = tokens[i + 1]; |             const operator = tokens[i + 1]; | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user