From 7e6e422f8944d5906323af24112acf853bf86099 Mon Sep 17 00:00:00 2001 From: "F. Levi" <55688616+flevi29@users.noreply.github.com> Date: Thu, 15 Aug 2024 11:40:55 +0300 Subject: [PATCH 1/9] Remove cross-fetch dependency --- .github/dependabot.yml | 2 -- package.json | 3 --- rollup.config.js | 3 --- src/http-requests.ts | 4 ---- tests/settings.test.ts | 4 +++- tests/utils/meilisearch-test-utils.ts | 2 +- yarn.lock | 2 +- 7 files changed, 5 insertions(+), 15 deletions(-) diff --git a/.github/dependabot.yml b/.github/dependabot.yml index 156507f7e..2c683134b 100644 --- a/.github/dependabot.yml +++ b/.github/dependabot.yml @@ -11,8 +11,6 @@ updates: - package-ecosystem: npm directory: '/' - allow: - - dependency-name: cross-fetch schedule: interval: 'monthly' diff --git a/package.json b/package.json index 5b27f003a..9e9813565 100644 --- a/package.json +++ b/package.json @@ -72,9 +72,6 @@ "git add" ] }, - "dependencies": { - "cross-fetch": "^3.1.6" - }, "devDependencies": { "@babel/core": "^7.23.6", "@babel/preset-env": "^7.22.5", diff --git a/rollup.config.js b/rollup.config.js index 853cd9512..210fb6345 100644 --- a/rollup.config.js +++ b/rollup.config.js @@ -29,7 +29,6 @@ module.exports = [ // browser-friendly UMD build { input: 'src/browser.ts', // directory to transpilation of typescript - external: ['cross-fetch', 'cross-fetch/polyfill'], output: { name: 'window', extend: true, @@ -75,7 +74,6 @@ module.exports = [ // ES module (for bundlers) build. { input: 'src/index.ts', - external: ['cross-fetch', 'cross-fetch/polyfill'], output: [ { file: getOutputFileName( @@ -96,7 +94,6 @@ module.exports = [ // Compatible only in a nodeJS environment. { input: 'src/index.ts', - external: ['cross-fetch', 'cross-fetch/polyfill'], output: { file: getOutputFileName( // will add .min. in filename if in production env diff --git a/src/http-requests.ts b/src/http-requests.ts index 96e2b606e..fa61ec0a5 100644 --- a/src/http-requests.ts +++ b/src/http-requests.ts @@ -123,10 +123,6 @@ class HttpRequests { body?: any; config?: Record; }) { - if (typeof fetch === 'undefined') { - require('cross-fetch/polyfill'); - } - const constructURL = new URL(url, this.url); if (params) { const queryParams = new URLSearchParams(); diff --git a/tests/settings.test.ts b/tests/settings.test.ts index 9c77d74de..a5c2389f0 100644 --- a/tests/settings.test.ts +++ b/tests/settings.test.ts @@ -171,7 +171,9 @@ describe.each([{ permission: 'Master' }, { permission: 'Admin' }])( }, }; const task = await client.index(index.uid).updateSettings(newSettings); - await client.index(index.uid).waitForTask(task.taskUid); + await client + .index(index.uid) + .waitForTask(task.taskUid, { timeOutMs: 60_000 }); const response = await client.index(index.uid).getSettings(); expect(response).toMatchSnapshot(); diff --git a/tests/utils/meilisearch-test-utils.ts b/tests/utils/meilisearch-test-utils.ts index e9d06c747..0a742d8f9 100644 --- a/tests/utils/meilisearch-test-utils.ts +++ b/tests/utils/meilisearch-test-utils.ts @@ -85,7 +85,7 @@ const clearAllIndexes = async (config: Config): Promise => { const { taskUid } = await client.index(indexUid).delete(); taskIds.push(taskUid); } - await client.waitForTasks(taskIds); + await client.waitForTasks(taskIds, { timeOutMs: 60_000 }); }; function decode64(buff: string) { diff --git a/yarn.lock b/yarn.lock index 2355d0aa6..6fb5a3b39 100644 --- a/yarn.lock +++ b/yarn.lock @@ -2776,7 +2776,7 @@ create-jest@^29.7.0: jest-util "^29.7.0" prompts "^2.0.1" -cross-fetch@^3.0.4, cross-fetch@^3.1.6: +cross-fetch@^3.0.4: version "3.1.6" resolved "https://registry.yarnpkg.com/cross-fetch/-/cross-fetch-3.1.6.tgz#bae05aa31a4da760969756318feeee6e70f15d6c" integrity sha512-riRvo06crlE8HiqOwIpQhxwdOk4fOeR7FVM/wXoxchFEqMNUjvbs3bfo4OTgMEMHzppd4DxFBDbyySj8Cv781g== From b5fff0d20cc2feb50e10d71c4ac2bb4f9b1b7d62 Mon Sep 17 00:00:00 2001 From: "F. Levi" <55688616+flevi29@users.noreply.github.com> Date: Fri, 16 Aug 2024 10:41:32 +0300 Subject: [PATCH 2/9] Add types for federation feature --- src/types/types.ts | 38 ++++++++++++++++++++++++++++---------- 1 file changed, 28 insertions(+), 10 deletions(-) diff --git a/src/types/types.ts b/src/types/types.ts index 9c08bc4ad..ac6813b9f 100644 --- a/src/types/types.ts +++ b/src/types/types.ts @@ -159,12 +159,23 @@ export type SearchRequestGET = Pagination & locales?: Locale[]; }; -export type MultiSearchQuery = SearchParams & { indexUid: string }; +export type FederationOptions = { weight: number }; +export type MultiSearchFederation = { limit?: number; offset?: number }; -export type MultiSearchParams = { - queries: MultiSearchQuery[]; +export type MultiSearchQuery = SearchParams & { indexUid: string }; +export type MultiSearchQueryWithFederation = MultiSearchQuery & { + federationOptions?: FederationOptions; }; +export type MultiSearchParams = + | { + queries: MultiSearchQuery[]; + } + | { + federation: MultiSearchFederation; + queries: MultiSearchQueryWithFederation[]; + }; + export type CategoriesDistribution = { [category: string]: number; }; @@ -175,13 +186,6 @@ export type MatchesPosition = Partial< Record> >; -export type Hit> = T & { - _formatted?: Partial; - _matchesPosition?: MatchesPosition; - _rankingScore?: number; - _rankingScoreDetails?: RankingScoreDetails; -}; - export type RankingScoreDetails = { words?: { order: number; @@ -213,6 +217,20 @@ export type RankingScoreDetails = { [key: string]: Record | undefined; }; +export type FederationDetails = { + indexUid: string; + queriesPosition: number; + weightedRankingScore: number; +}; + +export type Hit> = T & { + _formatted?: Partial; + _matchesPosition?: MatchesPosition; + _rankingScore?: number; + _rankingScoreDetails?: RankingScoreDetails; + _federation?: FederationDetails; +}; + export type Hits> = Array>; export type FacetStat = { min: number; max: number }; From 0640015479571f01c5d548d524c5ca6ff73c370a Mon Sep 17 00:00:00 2001 From: "F. Levi" <55688616+flevi29@users.noreply.github.com> Date: Fri, 16 Aug 2024 19:55:19 +0300 Subject: [PATCH 3/9] Add test, minor changes to types --- src/clients/client.ts | 20 +++++++++---- src/types/types.ts | 15 +++++----- tests/search.test.ts | 42 +++++++++++++++++++++++++++ tests/utils/meilisearch-test-utils.ts | 39 +++++++++---------------- 4 files changed, 77 insertions(+), 39 deletions(-) diff --git a/src/clients/client.ts b/src/clients/client.ts index ac031601a..f3c097f65 100644 --- a/src/clients/client.ts +++ b/src/clients/client.ts @@ -5,8 +5,6 @@ * Copyright: 2019, MeiliSearch */ -'use strict'; - import { Index } from '../indexes'; import { KeyCreation, @@ -34,6 +32,8 @@ import { DeleteTasksQuery, MultiSearchParams, MultiSearchResponse, + SearchResponse, + FederatedMultiSearchParams, } from '../types'; import { HttpRequests } from '../http-requests'; import { TaskClient, Task } from '../task'; @@ -216,10 +216,20 @@ class Client { * @param config - Additional request configuration options * @returns Promise containing the search responses */ - async multiSearch = Record>( - queries?: MultiSearchParams, + multiSearch = Record>( + queries: MultiSearchParams, + config?: Partial, + ): Promise>; + multiSearch = Record>( + queries: FederatedMultiSearchParams, + config?: Partial, + ): Promise>; + async multiSearch< + TRecord extends Record = Record, + >( + queries: MultiSearchParams | FederatedMultiSearchParams, config?: Partial, - ): Promise> { + ): Promise | SearchResponse> { const url = `multi-search`; return await this.httpRequest.post(url, queries, undefined, config); diff --git a/src/types/types.ts b/src/types/types.ts index ac6813b9f..768c429da 100644 --- a/src/types/types.ts +++ b/src/types/types.ts @@ -167,14 +167,13 @@ export type MultiSearchQueryWithFederation = MultiSearchQuery & { federationOptions?: FederationOptions; }; -export type MultiSearchParams = - | { - queries: MultiSearchQuery[]; - } - | { - federation: MultiSearchFederation; - queries: MultiSearchQueryWithFederation[]; - }; +export type MultiSearchParams = { + queries: MultiSearchQuery[]; +}; +export type FederatedMultiSearchParams = { + federation: MultiSearchFederation; + queries: MultiSearchQueryWithFederation[]; +}; export type CategoriesDistribution = { [category: string]: number; diff --git a/tests/search.test.ts b/tests/search.test.ts index 8ff3a173c..a34dad974 100644 --- a/tests/search.test.ts +++ b/tests/search.test.ts @@ -143,6 +143,48 @@ describe.each([ expect(response.results[0].hits[0].title).toEqual('Le Petit Prince'); }); + test.only(`${permission} key: Multi index search with federation`, async () => { + const client = await getClient(permission); + + const response1 = await client.multiSearch< + Books | { id: number; asd: string } + >({ + federation: {}, + queries: [ + { indexUid: index.uid, q: '456', attributesToSearchOn: ['id'] }, + { + indexUid: index.uid, + q: '1344', + federationOptions: { weight: 0.9 }, + attributesToSearchOn: ['id'], + }, + ], + }); + + expect(response1).toHaveProperty('hits'); + expect(Array.isArray(response1.hits)).toBe(true); + expect(response1.hits.length).toEqual(2); + expect(response1.hits[0].id).toEqual(456); + + const response2 = await client.multiSearch({ + federation: {}, + queries: [ + { + indexUid: index.uid, + q: '456', + federationOptions: { weight: 0.9 }, + attributesToSearchOn: ['id'], + }, + { indexUid: index.uid, q: '1344', attributesToSearchOn: ['id'] }, + ], + }); + + expect(response2).toHaveProperty('hits'); + expect(Array.isArray(response2.hits)).toBe(true); + expect(response2.hits.length).toEqual(2); + expect(response2.hits[0].id).toEqual(1344); + }); + test(`${permission} key: Basic search`, async () => { const client = await getClient(permission); const response = await client.index(index.uid).search('prince', {}); diff --git a/tests/utils/meilisearch-test-utils.ts b/tests/utils/meilisearch-test-utils.ts index 0a742d8f9..c27b55638 100644 --- a/tests/utils/meilisearch-test-utils.ts +++ b/tests/utils/meilisearch-test-utils.ts @@ -46,32 +46,19 @@ async function getKey(permission: string): Promise { } async function getClient(permission: string): Promise { - if (permission === 'No') { - const anonymousClient = new MeiliSearch({ - host: HOST, - }); - return anonymousClient; - } - - if (permission === 'Search') { - const searchKey = await getKey(permission); - const searchClient = new MeiliSearch({ - host: HOST, - apiKey: searchKey, - }); - return searchClient; - } - - if (permission === 'Admin') { - const adminKey = await getKey(permission); - const adminClient = new MeiliSearch({ - host: HOST, - apiKey: adminKey, - }); - return adminClient; - } - - return masterClient; + const apiKey = + permission === 'Search' || permission === 'Admin' + ? await getKey(permission) + : permission === 'No' + ? undefined + : null; + + return apiKey === null + ? masterClient + : new MeiliSearch({ + host: HOST, + apiKey, + }); } const clearAllIndexes = async (config: Config): Promise => { From 85d574de50732a02e96391c8ebf83161e38c7cfe Mon Sep 17 00:00:00 2001 From: "F. Levi" <55688616+flevi29@users.noreply.github.com> Date: Fri, 16 Aug 2024 20:28:31 +0300 Subject: [PATCH 4/9] Revert "Remove cross-fetch dependency" This reverts commit 899d2a7b78e868f4a5d33be1be45837269b0ea34. --- .github/dependabot.yml | 2 ++ package.json | 3 +++ rollup.config.js | 3 +++ src/http-requests.ts | 4 ++++ tests/settings.test.ts | 4 +--- tests/utils/meilisearch-test-utils.ts | 4 ++-- yarn.lock | 2 +- 7 files changed, 16 insertions(+), 6 deletions(-) diff --git a/.github/dependabot.yml b/.github/dependabot.yml index 2c683134b..156507f7e 100644 --- a/.github/dependabot.yml +++ b/.github/dependabot.yml @@ -11,6 +11,8 @@ updates: - package-ecosystem: npm directory: '/' + allow: + - dependency-name: cross-fetch schedule: interval: 'monthly' diff --git a/package.json b/package.json index 9e9813565..5b27f003a 100644 --- a/package.json +++ b/package.json @@ -72,6 +72,9 @@ "git add" ] }, + "dependencies": { + "cross-fetch": "^3.1.6" + }, "devDependencies": { "@babel/core": "^7.23.6", "@babel/preset-env": "^7.22.5", diff --git a/rollup.config.js b/rollup.config.js index 210fb6345..853cd9512 100644 --- a/rollup.config.js +++ b/rollup.config.js @@ -29,6 +29,7 @@ module.exports = [ // browser-friendly UMD build { input: 'src/browser.ts', // directory to transpilation of typescript + external: ['cross-fetch', 'cross-fetch/polyfill'], output: { name: 'window', extend: true, @@ -74,6 +75,7 @@ module.exports = [ // ES module (for bundlers) build. { input: 'src/index.ts', + external: ['cross-fetch', 'cross-fetch/polyfill'], output: [ { file: getOutputFileName( @@ -94,6 +96,7 @@ module.exports = [ // Compatible only in a nodeJS environment. { input: 'src/index.ts', + external: ['cross-fetch', 'cross-fetch/polyfill'], output: { file: getOutputFileName( // will add .min. in filename if in production env diff --git a/src/http-requests.ts b/src/http-requests.ts index fa61ec0a5..96e2b606e 100644 --- a/src/http-requests.ts +++ b/src/http-requests.ts @@ -123,6 +123,10 @@ class HttpRequests { body?: any; config?: Record; }) { + if (typeof fetch === 'undefined') { + require('cross-fetch/polyfill'); + } + const constructURL = new URL(url, this.url); if (params) { const queryParams = new URLSearchParams(); diff --git a/tests/settings.test.ts b/tests/settings.test.ts index a5c2389f0..9c77d74de 100644 --- a/tests/settings.test.ts +++ b/tests/settings.test.ts @@ -171,9 +171,7 @@ describe.each([{ permission: 'Master' }, { permission: 'Admin' }])( }, }; const task = await client.index(index.uid).updateSettings(newSettings); - await client - .index(index.uid) - .waitForTask(task.taskUid, { timeOutMs: 60_000 }); + await client.index(index.uid).waitForTask(task.taskUid); const response = await client.index(index.uid).getSettings(); expect(response).toMatchSnapshot(); diff --git a/tests/utils/meilisearch-test-utils.ts b/tests/utils/meilisearch-test-utils.ts index c27b55638..9430e3d99 100644 --- a/tests/utils/meilisearch-test-utils.ts +++ b/tests/utils/meilisearch-test-utils.ts @@ -67,12 +67,12 @@ const clearAllIndexes = async (config: Config): Promise => { const { results } = await client.getRawIndexes(); const indexes = results.map((elem) => elem.uid); - const taskIds: number[] = []; + const taskIds = []; for (const indexUid of indexes) { const { taskUid } = await client.index(indexUid).delete(); taskIds.push(taskUid); } - await client.waitForTasks(taskIds, { timeOutMs: 60_000 }); + await client.waitForTasks(taskIds); }; function decode64(buff: string) { diff --git a/yarn.lock b/yarn.lock index 6fb5a3b39..2355d0aa6 100644 --- a/yarn.lock +++ b/yarn.lock @@ -2776,7 +2776,7 @@ create-jest@^29.7.0: jest-util "^29.7.0" prompts "^2.0.1" -cross-fetch@^3.0.4: +cross-fetch@^3.0.4, cross-fetch@^3.1.6: version "3.1.6" resolved "https://registry.yarnpkg.com/cross-fetch/-/cross-fetch-3.1.6.tgz#bae05aa31a4da760969756318feeee6e70f15d6c" integrity sha512-riRvo06crlE8HiqOwIpQhxwdOk4fOeR7FVM/wXoxchFEqMNUjvbs3bfo4OTgMEMHzppd4DxFBDbyySj8Cv781g== From a8b823fba6734e140cb5d3a3123bd228dc0092ed Mon Sep 17 00:00:00 2001 From: "F. Levi" <55688616+flevi29@users.noreply.github.com> Date: Fri, 16 Aug 2024 20:31:12 +0300 Subject: [PATCH 5/9] Revert generic name back to T for consistency --- src/clients/client.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/clients/client.ts b/src/clients/client.ts index f3c097f65..0a04efe00 100644 --- a/src/clients/client.ts +++ b/src/clients/client.ts @@ -216,10 +216,10 @@ class Client { * @param config - Additional request configuration options * @returns Promise containing the search responses */ - multiSearch = Record>( + multiSearch = Record>( queries: MultiSearchParams, config?: Partial, - ): Promise>; + ): Promise>; multiSearch = Record>( queries: FederatedMultiSearchParams, config?: Partial, From 6b77b2293071484651b9298082049c47e4c6408d Mon Sep 17 00:00:00 2001 From: "F. Levi" <55688616+flevi29@users.noreply.github.com> Date: Fri, 16 Aug 2024 20:32:30 +0300 Subject: [PATCH 6/9] Revert rest of the generics to T --- src/clients/client.ts | 10 ++++------ 1 file changed, 4 insertions(+), 6 deletions(-) diff --git a/src/clients/client.ts b/src/clients/client.ts index 0a04efe00..520cdf687 100644 --- a/src/clients/client.ts +++ b/src/clients/client.ts @@ -220,16 +220,14 @@ class Client { queries: MultiSearchParams, config?: Partial, ): Promise>; - multiSearch = Record>( + multiSearch = Record>( queries: FederatedMultiSearchParams, config?: Partial, - ): Promise>; - async multiSearch< - TRecord extends Record = Record, - >( + ): Promise>; + async multiSearch = Record>( queries: MultiSearchParams | FederatedMultiSearchParams, config?: Partial, - ): Promise | SearchResponse> { + ): Promise | SearchResponse> { const url = `multi-search`; return await this.httpRequest.post(url, queries, undefined, config); From 772761f07aa6018e84e69f06cd90de462f420a30 Mon Sep 17 00:00:00 2001 From: "F. Levi" <55688616+flevi29@users.noreply.github.com> Date: Fri, 16 Aug 2024 20:35:09 +0300 Subject: [PATCH 7/9] Remove focus from test --- tests/search.test.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/search.test.ts b/tests/search.test.ts index a34dad974..e1d66f64f 100644 --- a/tests/search.test.ts +++ b/tests/search.test.ts @@ -143,7 +143,7 @@ describe.each([ expect(response.results[0].hits[0].title).toEqual('Le Petit Prince'); }); - test.only(`${permission} key: Multi index search with federation`, async () => { + test(`${permission} key: Multi index search with federation`, async () => { const client = await getClient(permission); const response1 = await client.multiSearch< From b218f1ffcd347b781f4a109efab932825a9f50fe Mon Sep 17 00:00:00 2001 From: "F. Levi" <55688616+flevi29@users.noreply.github.com> Date: Thu, 22 Aug 2024 10:54:01 +0300 Subject: [PATCH 8/9] Revert changes to test-utils getClient --- tests/utils/meilisearch-test-utils.ts | 39 ++++++++++++++++++--------- 1 file changed, 26 insertions(+), 13 deletions(-) diff --git a/tests/utils/meilisearch-test-utils.ts b/tests/utils/meilisearch-test-utils.ts index 9430e3d99..1a370a8f6 100644 --- a/tests/utils/meilisearch-test-utils.ts +++ b/tests/utils/meilisearch-test-utils.ts @@ -46,19 +46,32 @@ async function getKey(permission: string): Promise { } async function getClient(permission: string): Promise { - const apiKey = - permission === 'Search' || permission === 'Admin' - ? await getKey(permission) - : permission === 'No' - ? undefined - : null; - - return apiKey === null - ? masterClient - : new MeiliSearch({ - host: HOST, - apiKey, - }); + if (permission === 'No') { + const anonymousClient = new MeiliSearch({ + host: HOST, + }); + return anonymousClient; + } + + if (permission === 'Search') { + const searchKey = await getKey(permission); + const searchClient = new MeiliSearch({ + host: HOST, + apiKey: searchKey, + }); + return searchClient; + } + + if (permission === 'Admin') { + const adminKey = await getKey(permission); + const adminClient = new MeiliSearch({ + host: HOST, + apiKey: adminKey, + }); + return adminClient; + } + + return masterClient; } const clearAllIndexes = async (config: Config): Promise => { From 1c48c8002aaf3766fdb82c386ade48f2c76a13bb Mon Sep 17 00:00:00 2001 From: "F. Levi" <55688616+flevi29@users.noreply.github.com> Date: Thu, 22 Aug 2024 15:06:52 +0300 Subject: [PATCH 9/9] Add back accidentally removed type from test utils --- tests/utils/meilisearch-test-utils.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/utils/meilisearch-test-utils.ts b/tests/utils/meilisearch-test-utils.ts index 1a370a8f6..e9d06c747 100644 --- a/tests/utils/meilisearch-test-utils.ts +++ b/tests/utils/meilisearch-test-utils.ts @@ -80,7 +80,7 @@ const clearAllIndexes = async (config: Config): Promise => { const { results } = await client.getRawIndexes(); const indexes = results.map((elem) => elem.uid); - const taskIds = []; + const taskIds: number[] = []; for (const indexUid of indexes) { const { taskUid } = await client.index(indexUid).delete(); taskIds.push(taskUid);