From 5e14cea98b9e90ad30827278b971719f49d1d3ed Mon Sep 17 00:00:00 2001 From: Seow Wen Han <106362727+swenhan@users.noreply.github.com> Date: Tue, 23 Aug 2022 13:36:57 +0800 Subject: [PATCH 1/2] Fix in-doc search not working when stopword is in title (#1) * Trying to reproduce stop-word error but couldn't * Update and add appropriate test case for stop-word testing * Implement fix for stopword in title, add unit test case Signed-off-by: Seow Wen Han --- .../src/engines/LunrSearchEngine.test.ts | 120 ++++++++++++++++++ .../src/engines/LunrSearchEngine.ts | 14 +- 2 files changed, 130 insertions(+), 4 deletions(-) diff --git a/plugins/search-backend-node/src/engines/LunrSearchEngine.test.ts b/plugins/search-backend-node/src/engines/LunrSearchEngine.test.ts index 1f69460448..521cb9ee81 100644 --- a/plugins/search-backend-node/src/engines/LunrSearchEngine.test.ts +++ b/plugins/search-backend-node/src/engines/LunrSearchEngine.test.ts @@ -1092,3 +1092,123 @@ describe('parseHighlightFields', () => { }); }); }); + +describe('stopword testing', () => { + let testLunrSearchEngine: SearchEngine; + + beforeEach(() => { + testLunrSearchEngine = new LunrSearchEngine({ logger: getVoidLogger() }); + jest.clearAllMocks(); + }); + + it('test with stopword in title', async () => { + const mockDocuments = [ + { + title: 'a home', + text: 'mary had a little lamb at home', + location: 'test/location', + }, + ]; + + const indexer = await getActualIndexer(testLunrSearchEngine, 'test-index'); + + await TestPipeline.withSubject(indexer) + .withDocuments(mockDocuments) + .execute(); + + const mockedSearchResult = await testLunrSearchEngine.query({ + term: 'mary', + filters: { + title: 'a home', + }, + }); + + expect(mockedSearchResult).toMatchObject({ + results: [ + { + document: { + title: 'a home', + text: 'mary had a little lamb at home', + location: 'test/location', + }, + rank: 1, + }, + ], + nextPageCursor: undefined, + }); + }); + + it('test with stopword connected with dash', async () => { + const mockDocuments = [ + { + title: 'a-home', + text: 'mary had a little lamb at home', + location: 'test/location', + }, + ]; + + const indexer = await getActualIndexer(testLunrSearchEngine, 'test-index'); + + await TestPipeline.withSubject(indexer) + .withDocuments(mockDocuments) + .execute(); + + const mockedSearchResult = await testLunrSearchEngine.query({ + term: 'mary', + filters: { + title: 'a-home', + }, + }); + + expect(mockedSearchResult).toMatchObject({ + results: [ + { + document: { + title: 'a-home', + text: 'mary had a little lamb at home', + location: 'test/location', + }, + rank: 1, + }, + ], + nextPageCursor: undefined, + }); + }); + + it('test with only stop word in title', async () => { + const mockDocuments = [ + { + title: 'a', + text: 'mary had a little lamb at home', + location: 'test/location', + }, + ]; + + const indexer = await getActualIndexer(testLunrSearchEngine, 'test-index'); + + await TestPipeline.withSubject(indexer) + .withDocuments(mockDocuments) + .execute(); + + const mockedSearchResult = await testLunrSearchEngine.query({ + term: 'mary', + filters: { + title: 'a', + }, + }); + + expect(mockedSearchResult).toMatchObject({ + results: [ + { + document: { + title: 'a', + text: 'mary had a little lamb at home', + location: 'test/location', + }, + rank: 1, + }, + ], + nextPageCursor: undefined, + }); + }); +}); diff --git a/plugins/search-backend-node/src/engines/LunrSearchEngine.ts b/plugins/search-backend-node/src/engines/LunrSearchEngine.ts index ec8550d721..8780490dcc 100644 --- a/plugins/search-backend-node/src/engines/LunrSearchEngine.ts +++ b/plugins/search-backend-node/src/engines/LunrSearchEngine.ts @@ -114,10 +114,16 @@ export class LunrSearchEngine implements SearchEngine { // Require that the given field has the given value if (['string', 'number', 'boolean'].includes(typeof value)) { - q.term(lunr.tokenizer(value?.toString()), { - presence: lunr.Query.presence.REQUIRED, - fields: [field], - }); + q.term( + lunr + .tokenizer(value?.toString()) + .map(lunr.stopWordFilter) + .filter(element => element !== undefined), + { + presence: lunr.Query.presence.REQUIRED, + fields: [field], + }, + ); } else if (Array.isArray(value)) { // Illustrate how multi-value filters could work. // But warn that Lurn supports this poorly. From a1124adf5e72466461fb7432129145c019f2f416 Mon Sep 17 00:00:00 2001 From: Seow Wen Han Date: Tue, 23 Aug 2022 14:06:01 +0800 Subject: [PATCH 2/2] Commit changeset for bug fix in plugin-search-backend-node Signed-off-by: Seow Wen Han --- .changeset/heavy-ligers-laugh.md | 5 +++++ 1 file changed, 5 insertions(+) create mode 100644 .changeset/heavy-ligers-laugh.md diff --git a/.changeset/heavy-ligers-laugh.md b/.changeset/heavy-ligers-laugh.md new file mode 100644 index 0000000000..71f8b99b12 --- /dev/null +++ b/.changeset/heavy-ligers-laugh.md @@ -0,0 +1,5 @@ +--- +'@backstage/plugin-search-backend-node': patch +--- + +Fixed bug in LunrSearchEngine where stopwords in title is causing in-doc search not working