Skip to content
This repository has been archived by the owner on Jul 11, 2023. It is now read-only.

feat(types): support algoliasearch v5 #910

Merged
merged 16 commits into from
Jun 24, 2022
Merged
67 changes: 20 additions & 47 deletions index.d.ts
Original file line number Diff line number Diff line change
@@ -1,45 +1,10 @@
// Note: Below, we will be importing both algoliasearch
// `v3` and algoliasearch `v4` types. The goal is being
// able to export the algoliasearch-helper types using
// the developer installed version of the client.

import algoliasearch, {
// @ts-ignore
SearchClient as SearchClientV4,
// @ts-ignore
Client as SearchClientV3,
// @ts-ignore
QueryParameters as SearchOptionsV3,
// @ts-ignore
Response as SearchResponseV3,
} from 'algoliasearch';
import {
SearchOptions as SearchOptionsV4,
SearchResponse as SearchResponseV4,
FindAnswersResponse
// @ts-ignore
} from '@algolia/client-search';
import EventEmitter from '@algolia/events';

type DummySearchClientV4 = {
transporter: any;
};

type Client = ReturnType<typeof algoliasearch> extends DummySearchClientV4
? SearchClientV4
: SearchClientV3;
type SearchOptions = ReturnType<
typeof algoliasearch
> extends DummySearchClientV4
? SearchOptionsV4
: SearchOptionsV3;
type SearchResponse<T> = ReturnType<
typeof algoliasearch
> extends DummySearchClientV4
? SearchResponseV4<T>
: SearchResponseV3<T>;

type SearchClient = Pick<Client, 'search' | 'searchForFacetValues'>;
import {
FindAnswersResponse,
SearchClient,
SearchOptions,
SearchResponse,
} from './types/algoliasearch';

/**
* The algoliasearchHelper module is the function that will let its
Expand Down Expand Up @@ -272,7 +237,11 @@ declare namespace algoliasearchHelper {
*/
addDisjunctiveRefine(facet: string, value: string): this;
addHierarchicalFacetRefinement(facet: string, path: string): this;
addNumericRefinement(facet: string, operator?: SearchParameters.Operator, value?: number | number[]): this;
addNumericRefinement(
facet: string,
operator?: SearchParameters.Operator,
value?: number | number[]
): this;
addFacetRefinement(facet: string, value: string): this;
/**
* @deprecated since version 2.4.0, see {@link AlgoliaSearchHelper#addFacetRefinement}
Expand All @@ -284,7 +253,11 @@ declare namespace algoliasearchHelper {
*/
addExclude: AlgoliaSearchHelper['addFacetExclusion'];
addTag(tag: string): this;
removeNumericRefinement(facet: string, operator?: SearchParameters.Operator, value?: number | number[]): this;
removeNumericRefinement(
facet: string,
operator?: SearchParameters.Operator,
value?: number | number[]
): this;
removeDisjunctiveFacetRefinement(facet: string, value?: string): this;
/**
* @deprecated since version 2.4.0, see {@link AlgoliaSearchHelper#removeDisjunctiveFacetRefinement}
Expand Down Expand Up @@ -530,7 +503,7 @@ declare namespace algoliasearchHelper {
'facetsRefinements',
'hierarchicalFacets',
'facetsExcludes',

'disjunctiveFacetsRefinements',
'numericRefinements',
'tagRefinements',
Expand Down Expand Up @@ -950,7 +923,7 @@ declare namespace algoliasearchHelper {
queryType?: 'prefixAll' | 'prefixLast' | 'prefixNone';
/**
* Search entries inside a given area defined by a set of points
* defauly: ''
* default: ''
* https://www.algolia.com/doc/api-reference/api-parameters/insidePolygon/
*/
insidePolygon?: number[][];
Expand Down Expand Up @@ -1150,7 +1123,7 @@ declare namespace algoliasearchHelper {
* Marker which can be added to search results to identify them as created without a search response.
* This is for internal use, e.g., avoiding caching in infinite hits, or delaying the display of these results.
*/
__isArtificial?: boolean | undefined
__isArtificial?: boolean | undefined;
}

type ISearchResponse<T> = Omit<SearchResponse<T>, 'facets' | 'params'> &
Expand Down Expand Up @@ -1392,7 +1365,7 @@ declare namespace algoliasearchHelper {

/**
* Returns all refinements for all filters + tags. It also provides
* additional information: count and exhausistivity for each filter.
* additional information: count and exhaustiveness for each filter.
*
* See the [refinement type](#Refinement) for an exhaustive view of the available
* data.
Expand Down
6 changes: 4 additions & 2 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,9 @@
"dist",
"src",
"index.js",
"index.d.ts"
"index.d.ts",
"types/algoliasearch.d.ts",
"types/algoliasearch.js"
],
"devDependencies": {
"@types/algoliasearch": "3.34.11",
Expand Down Expand Up @@ -101,7 +103,7 @@
"@algolia/events": "^4.0.1"
},
"peerDependencies": {
"algoliasearch": ">= 3.1 < 5"
"algoliasearch": ">= 3.1 < 6"
Haroenv marked this conversation as resolved.
Show resolved Hide resolved
},
"resolutions": {
"node-sass": "4.14.1"
Expand Down
148 changes: 148 additions & 0 deletions types/algoliasearch.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,148 @@
// Note: Below, we will be importing all algoliasearch v3,4,5 types.
// The goal is being able to export the algoliasearch-helper types using
// the version of the client installed by the developer.

// @ts-ignore
import type algoliasearch from 'algoliasearch/lite';
// @ts-ignore
import type * as AlgoliaSearchLite from 'algoliasearch/lite';
// @ts-ignore
import type * as AlgoliaSearch from 'algoliasearch';
// @ts-ignore
import type * as ClientSearch from '@algolia/client-search';

// turns any to unknown, so it can be used as a conditional
type AnyToUnknown<T> = (any extends T ? true : false) extends true
? unknown
: T;

type SearchClientV4Shape = {
transporter: unknown;
};

type SearchClientShape = {
search: unknown;
};

// @ts-ignore
type ClientV3_4 = ReturnType<typeof algoliasearch>;

type ClientLiteV5 = AnyToUnknown<
// @ts-ignore
ReturnType<typeof AlgoliaSearchLite.liteClient>
>;
type ClientFullV5 = AnyToUnknown<
// @ts-ignore
ReturnType<typeof AlgoliaSearch.algoliasearch>
>;
type ClientSearchV5 = AnyToUnknown<
// @ts-ignore
ReturnType<typeof ClientSearch.searchClient>
>;
type ClientV5 = ClientLiteV5 extends SearchClientShape
? ClientLiteV5
: ClientSearchV5 extends SearchClientShape
? ClientSearchV5
: ClientFullV5 extends SearchClientShape
? ClientFullV5
: unknown;

type PickForClient<
T extends {
v3: unknown;
v4: unknown;
v5: unknown;
}
> = ClientV5 extends SearchClientShape
? T['v5']
: // @ts-ignore
ClientV3_4 extends SearchClientV4Shape
? T['v4']
: T['v3'];

type DefaultSearchClient = PickForClient<{
v3: ClientV3_4;
v4: ClientV3_4;
v5: ClientV5;
}>;

export type SearchOptions = PickForClient<{
// @ts-ignore
v3: AlgoliaSearch.QueryParameters;
// @ts-ignore
v4: ClientSearch.SearchOptions;
v5: NonNullable<
// @ts-ignore
AlgoliaSearch.LegacySearchMethodProps[number]['params']
>;
}>;

export type SearchResponse<T> = PickForClient<{
// @ts-ignore
v3: AlgoliaSearch.Response<T> & {
appliedRelevancyStrictness?: number;
nbSortedHits?: number;
renderingContent?: {
facetOrdering?: {
facets?: {
order?: string[];
};
values?: {
[facet: string]: {
order?: string[];
sortRemainingBy?: 'count' | 'alpha' | 'hidden';
};
};
};
};
};
// @ts-ignore
v4: ClientSearch.SearchResponse<T>;
// @ts-ignore
v5: AlgoliaSearch.SearchResponse; // TODO: should be generic
sarahdayan marked this conversation as resolved.
Show resolved Hide resolved
}>;

export type SearchResponses<T> = PickForClient<{
// @ts-ignore
v3: AlgoliaSearch.MultiResponse<T>;
// @ts-ignore
v4: ClientSearch.MultipleQueriesResponse<T>;
// @ts-ignore
v5: AlgoliaSearch.SearchResponses; // TODO: should be generic
}>;

export type SearchForFacetValuesResponse = PickForClient<{
// @ts-ignore
v3: AlgoliaSearch.SearchForFacetValues.Response;
// @ts-ignore
v4: ClientSearch.SearchForFacetValuesResponse;
// @ts-ignore
v5: AlgoliaSearch.SearchForFacetValuesResponse;
}>;

export type FindAnswersOptions = PickForClient<{
v3: any;
// @ts-ignore
v4: ClientSearch.FindAnswersOptions;
v5: any;
}>;

export type FindAnswersResponse<T> = PickForClient<{
v3: any;
// @ts-ignore
v4: ClientSearch.FindAnswersResponse<T>;
v5: any;
}>;

export interface SearchClient {
search: DefaultSearchClient['search'];
searchForFacetValues?: DefaultSearchClient extends {
searchForFacetValues: unknown;
}
? DefaultSearchClient['searchForFacetValues']
: never;
initIndex?: DefaultSearchClient extends { initIndex: unknown }
? DefaultSearchClient['initIndex']
: never;
addAlgoliaAgent?: DefaultSearchClient['addAlgoliaAgent'];
}
1 change: 1 addition & 0 deletions types/algoliasearch.js
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
// fake file to allow `export * from 'algoliasearch-helper/types/algoliasearch'`