Press n or j to go to the next uncovered block, b, p or k for the previous block.
| 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 | 1x 1x 1x 3x 3x 3x 3x 8x 8x 5x 8x 1x 8x 1x 8x 1x 8x 8x 3x 3x | import type { SearchAst } from '../types';
/**
* A leaf field-match condition in a CONTAINS filter tree.
* @category Utils
* @group Converters
*/
export interface ContainsTermFilter {
term: { field: string; op: string; values: string[] };
}
/**
* A node in a generic boolean CONTAINS filter tree, shared by GraphQL backends
* (Wix, Magento2) whose filter input uses the same `and`/`or`/`not`/`term`
* shape. Either a leaf {@link ContainsTermFilter} or a boolean combinator.
* @category Utils
* @group Converters
*/
export type ContainsFilterNode =
| ContainsTermFilter
| { and: ContainsFilterNode[] }
| { or: ContainsFilterNode[] }
| { not: ContainsFilterNode };
/**
* Translates a {@link SearchAst} into a generic boolean CONTAINS filter tree of
* the form `{ and|or|not | term: { field, op: "CONTAINS", values } }`. Used by
* GraphQL suppliers that accept this structure server-side, so the boolean
* matching happens on the backend in a single request.
*
* @category Utils
* @group Converters
* @param ast - The parsed query tree.
* @param wrapValue - Maps a term value to the stored value (e.g. add `*…*`
* wildcards for Wix). Defaults to identity.
* @param field - The field name to match against. Defaults to `"name"`.
* @returns A CONTAINS filter node.
* @example
* ```ts
* translateAstToContainsFilter({ type: "or",
* left: { type: "term", value: "foo", phrase: false },
* right: { type: "term", value: "bar", phrase: false } });
* // { or: [
* // { term: { field: "name", op: "CONTAINS", values: ["foo"] } },
* // { term: { field: "name", op: "CONTAINS", values: ["bar"] } },
* // ] }
* ```
* @source
*/
export function translateAstToContainsFilter(
ast: SearchAst,
wrapValue: (value: string) => string = (value) => value,
field: string = 'name',
): ContainsFilterNode {
const translate = (node: SearchAst): ContainsFilterNode => {
switch (node.type) {
case 'term':
return { term: { field, op: 'CONTAINS', values: [wrapValue(node.value)] } };
case 'and':
return { and: [translate(node.left), translate(node.right)] };
case 'or':
return { or: [translate(node.left), translate(node.right)] };
case 'not':
return { not: translate(node.operand) };
}
};
return translate(ast);
}
|