@thisisagile/easy-mongo 15.4.0 → 15.5.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,12 @@
1
+ import { MongoGateway } from './MongoGateway';
2
+ import { Collection } from './Collection';
3
+ import { MongoProvider } from './MongoProvider';
4
+ import { SearchDefinition } from './Lucene';
5
+ import { Filter, Json, PageList } from '@thisisagile/easy';
6
+ export declare const toFilters: (facets: unknown) => Filter[];
7
+ export declare class AtlasSearchGateway extends MongoGateway {
8
+ readonly searchDef: SearchDefinition;
9
+ readonly sortDef: Record<string, Record<string, 1 | -1>>;
10
+ constructor(collection: Collection, searchDef: SearchDefinition, sortDef?: Record<string, Record<string, 1 | -1>>, provider?: MongoProvider);
11
+ query: (query: Record<keyof typeof this.searchDef, string | number>) => Promise<PageList<Json>>;
12
+ }
@@ -0,0 +1,40 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.AtlasSearchGateway = exports.toFilters = void 0;
4
+ const Stages_1 = require("./Stages");
5
+ const MongoGateway_1 = require("./MongoGateway");
6
+ const Lucene_1 = require("./Lucene");
7
+ const easy_1 = require("@thisisagile/easy");
8
+ const { skip, take } = Stages_1.stages.skip;
9
+ const { replaceWith } = Stages_1.stages.replaceWith;
10
+ const { searchWithDef, searchMeta, facets } = Lucene_1.lucene;
11
+ const toFilters = (facets) => (0, easy_1.entries)(facets).map(([k, fs]) => ({
12
+ label: (0, easy_1.text)(k).title.toString(),
13
+ field: k,
14
+ values: fs.map((f) => toValue(f)),
15
+ }));
16
+ exports.toFilters = toFilters;
17
+ const toValue = (f) => ({ label: f._id ?? 'unknown', value: f._id ?? 'unknown', count: f.count });
18
+ class AtlasSearchGateway extends MongoGateway_1.MongoGateway {
19
+ constructor(collection, searchDef, sortDef = {}, provider = collection.provider) {
20
+ super(collection, provider);
21
+ this.searchDef = searchDef;
22
+ this.sortDef = sortDef;
23
+ this.query = async (query) => {
24
+ return (0, easy_1.tuple2)(this.aggregate(searchWithDef(query, this.searchDef), skip({ skip: query?.skip ?? 0 }), take({ take: query?.take ?? 250 })), this.aggregate(searchMeta(query, this.searchDef), replaceWith({
25
+ total: '$count.lowerBound',
26
+ facets: Object.keys(facets(this.searchDef)).reduce((acc, k) => ({ ...acc, [k]: `$facet.${k}.buckets` }), {}),
27
+ })))
28
+ .then(([data, meta]) => ({ data, meta: meta.first() }))
29
+ .then(({ data, meta }) => (0, easy_1.toPageList)(data, {
30
+ total: meta?.total ?? 0,
31
+ skip: query?.skip ?? 0,
32
+ take: query?.take ?? 250,
33
+ sorts: Object.keys(this.sortDef),
34
+ filters: (0, exports.toFilters)(meta.facets),
35
+ }));
36
+ };
37
+ }
38
+ }
39
+ exports.AtlasSearchGateway = AtlasSearchGateway;
40
+ //# sourceMappingURL=AtlasSearchGateway.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"AtlasSearchGateway.js","sourceRoot":"","sources":["../src/AtlasSearchGateway.ts"],"names":[],"mappings":"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"}
package/dist/Lucene.d.ts CHANGED
@@ -1,12 +1,35 @@
1
- import { Func, OneOrMore, Optional } from "@thisisagile/easy";
1
+ import { DateTime, Func, List, OneOrMore, Optional, RequireAtLeastOne } from '@thisisagile/easy';
2
2
  type FuzzyOptions = {
3
3
  maxEdits: number;
4
4
  prefixLength: number;
5
5
  maxExpansions: number;
6
6
  };
7
+ export type Facet = {
8
+ path: string;
9
+ type: 'string';
10
+ numBuckets: number;
11
+ } | {
12
+ path: string;
13
+ type: 'number';
14
+ boundaries: number[];
15
+ default?: string;
16
+ } | {
17
+ path: string;
18
+ type: 'date';
19
+ boundaries: Date[];
20
+ default?: string;
21
+ };
7
22
  export type Operator = Func<Optional<object>, string>;
8
23
  export type Clause = object | Operator;
9
24
  export type Clauses = Record<string, Clause>;
25
+ export type SearchDefinition = Record<string, (v: string | number) => RequireAtLeastOne<{
26
+ should?: Clauses;
27
+ filter?: Clauses;
28
+ must?: Clauses;
29
+ mustNot?: Clauses;
30
+ sort?: Record<string, 1 | -1>;
31
+ facet?: Facet;
32
+ }>>;
10
33
  type Compound = {
11
34
  must: OneOrMore<Clauses>;
12
35
  should: OneOrMore<Clauses>;
@@ -14,7 +37,7 @@ type Compound = {
14
37
  filter: OneOrMore<Clauses>;
15
38
  };
16
39
  export declare const lucene: {
17
- clause: (c: Clauses) => import("@thisisagile/easy").List<unknown>;
40
+ clause: (c: Clauses) => List<unknown>;
18
41
  clauses: (cs: OneOrMore<Clauses>) => unknown[];
19
42
  search: (c: Partial<Compound>, index?: string) => {
20
43
  $search: {
@@ -22,7 +45,29 @@ export declare const lucene: {
22
45
  index?: string | undefined;
23
46
  };
24
47
  };
48
+ searchWithDef: (query: Record<string, string | number>, options: SearchDefinition, index?: string) => {
49
+ $search: {
50
+ sort?: Record<string, 1 | -1> | undefined;
51
+ compound: Partial<Compound>;
52
+ index?: string | undefined;
53
+ };
54
+ };
55
+ searchMeta: (query: Record<string, string | number>, def: SearchDefinition, index?: string) => {
56
+ $searchMeta: {
57
+ facet: {
58
+ operator: {
59
+ compound: Partial<Compound>;
60
+ };
61
+ facets: {
62
+ [x: string]: Facet | undefined;
63
+ };
64
+ };
65
+ index?: string | undefined;
66
+ };
67
+ };
68
+ exists: () => Operator;
25
69
  text: (value?: OneOrMore<unknown>, fuzzy?: Partial<FuzzyOptions>) => Operator;
70
+ wildcard: (value?: OneOrMore<unknown>) => Operator;
26
71
  lt: (value: unknown) => Operator;
27
72
  lte: (value: unknown) => Operator;
28
73
  gt: (value: unknown) => Operator;
@@ -30,5 +75,13 @@ export declare const lucene: {
30
75
  after: (date: unknown) => Operator;
31
76
  before: (date: unknown) => Operator;
32
77
  between: (after: unknown, before: unknown) => Operator;
78
+ facets: (def: SearchDefinition) => {
79
+ [x: string]: Facet | undefined;
80
+ };
81
+ facet: {
82
+ string: (path: string, numBuckets?: number) => Facet;
83
+ number: (path: string, boundaries: List<number>, alt?: string) => Facet;
84
+ date: (path: string, boundaries: List<DateTime>, alt?: string) => Facet;
85
+ };
33
86
  };
34
87
  export {};
package/dist/Lucene.js CHANGED
@@ -3,22 +3,60 @@ Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.lucene = void 0;
4
4
  const easy_1 = require("@thisisagile/easy");
5
5
  const Utils_1 = require("./Utils");
6
+ const should = (query, def) => (0, easy_1.entries)(query).mapDefined(([k, v]) => def[k]?.(v)?.should);
7
+ const must = (query, def) => (0, easy_1.entries)(query).mapDefined(([k, v]) => def[k]?.(v)?.must);
8
+ const mustNot = (query, def) => (0, easy_1.entries)(query).mapDefined(([k, v]) => def[k]?.(v)?.mustNot);
9
+ const filter = (query, def) => (0, easy_1.entries)(query).mapDefined(([k, v]) => def[k]?.(v)?.filter);
10
+ const compound = (query, def) => (0, easy_1.entries)({
11
+ should: (0, easy_1.ifNotEmpty)(should(query, def).concat(filter(query, def), must(query, def), mustNot(query, def)), should(query, def), [
12
+ { wildcard: exports.lucene.wildcard() },
13
+ ]),
14
+ ...(0, easy_1.ifNotEmpty)(filter(query, def), f => ({ filter: f })),
15
+ ...(0, easy_1.ifNotEmpty)(mustNot(query, def), m => ({ mustNot: m })),
16
+ ...(0, easy_1.ifNotEmpty)(must(query, def), m => ({ must: m })),
17
+ }).reduce((res, [k, v]) => (0, easy_1.on)(res, r => (r[k] = exports.lucene.clauses(v))), {});
6
18
  exports.lucene = {
7
19
  clause: (c) => (0, easy_1.entries)(c).reduce((res, [k, v]) => res.add((0, easy_1.isFunction)(v) ? v(k) : v), (0, easy_1.toList)()),
8
20
  clauses: (cs) => (0, easy_1.toArray)(cs).flatMap(c => exports.lucene.clause(c)),
9
21
  search: (c, index) => ({
10
22
  $search: {
11
23
  ...(0, easy_1.ifDefined)(index, { index }),
12
- compound: (0, easy_1.entries)(c).reduce((res, [k, v]) => (0, easy_1.on)(res, r => (r[k] = exports.lucene.clauses(v))), {})
13
- }
24
+ compound: (0, easy_1.entries)(c).reduce((res, [k, v]) => (0, easy_1.on)(res, r => (r[k] = exports.lucene.clauses(v))), {}),
25
+ },
14
26
  }),
27
+ searchWithDef: (query, options, index) => {
28
+ const sort = (0, easy_1.entries)(query)
29
+ .mapDefined(([k, v]) => options[k]?.(v)?.sort)
30
+ .first();
31
+ return {
32
+ $search: { ...(0, easy_1.ifDefined)(index, { index }), compound: compound(query, options), ...(0, easy_1.ifDefined)(sort, { sort }) },
33
+ };
34
+ },
35
+ searchMeta: (query, def, index) => ({
36
+ $searchMeta: {
37
+ ...(0, easy_1.ifDefined)(index, { index }),
38
+ facet: {
39
+ operator: {
40
+ compound: compound(query, def),
41
+ },
42
+ facets: exports.lucene.facets(def),
43
+ },
44
+ },
45
+ }),
46
+ exists: () => (path) => ({ exists: { path } }),
15
47
  text: (value, fuzzy) => (path) => (0, easy_1.ifDefined)(value, v => ({
16
48
  text: {
17
49
  path: path === 'wildcard' ? { wildcard: '*' } : path,
18
50
  query: v,
19
- ...(0, easy_1.ifDefined)(fuzzy, { fuzzy })
20
- }
51
+ ...(0, easy_1.ifDefined)(fuzzy, { fuzzy }),
52
+ },
21
53
  })),
54
+ wildcard: (value) => (path) => ({
55
+ wildcard: {
56
+ path: path === 'wildcard' ? { wildcard: '*' } : path,
57
+ query: (0, easy_1.ifDefined)(value, value, '*'),
58
+ },
59
+ }),
22
60
  lt: (value) => (path) => (0, easy_1.ifDefined)(value, lt => ({ range: { path, lt } })),
23
61
  lte: (value) => (path) => (0, easy_1.ifDefined)(value, lte => ({ range: { path, lte } })),
24
62
  gt: (value) => (path) => (0, easy_1.ifDefined)(value, gt => ({ range: { path, gt } })),
@@ -29,8 +67,31 @@ exports.lucene = {
29
67
  range: {
30
68
  path,
31
69
  gte: (0, Utils_1.toMongoType)(after),
32
- lt: (0, Utils_1.toMongoType)(before)
33
- }
34
- })
70
+ lt: (0, Utils_1.toMongoType)(before),
71
+ },
72
+ }),
73
+ facets: (def) => (0, easy_1.entries)(def)
74
+ .filter(([k, v]) => (0, easy_1.isDefined)(v(k)?.facet))
75
+ .map(([k, v]) => ({ [k]: v(k)?.facet }))
76
+ .reduce((acc, v) => ({ ...acc, ...v }), {}),
77
+ facet: {
78
+ string: (path, numBuckets = 1000) => ({
79
+ type: 'string',
80
+ path,
81
+ numBuckets,
82
+ }),
83
+ number: (path, boundaries, alt) => ({
84
+ type: 'number',
85
+ path,
86
+ boundaries,
87
+ ...(0, easy_1.ifDefined)(alt, a => ({ default: a })),
88
+ }),
89
+ date: (path, boundaries, alt) => ({
90
+ type: 'date',
91
+ path,
92
+ boundaries: boundaries.mapDefined(b => b.toDate()),
93
+ ...(0, easy_1.ifDefined)(alt, a => ({ default: a })),
94
+ }),
95
+ },
35
96
  };
36
97
  //# sourceMappingURL=Lucene.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"Lucene.js","sourceRoot":"","sources":["../src/Lucene.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"Lucene.js","sourceRoot":"","sources":["../src/Lucene.ts"],"names":[],"mappings":"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"}
@@ -36,7 +36,7 @@ class MongoGateway {
36
36
  return this.provider.aggregate((0, easy_1.toArray)(...filters).filter(easy_1.isPresent));
37
37
  }
38
38
  count(...filters) {
39
- return this.aggregate(...filters, { $count: 'total' }).then(d => d.first().total ?? 0);
39
+ return this.aggregate(...filters, { $count: 'total' }).then(d => d.first()?.total ?? 0);
40
40
  }
41
41
  match(f) {
42
42
  return this.aggregate(Stages_1.stages.match.match(f));
@@ -1 +1 @@
1
- {"version":3,"file":"MongoGateway.js","sourceRoot":"","sources":["../src/MongoGateway.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"MongoGateway.js","sourceRoot":"","sources":["../src/MongoGateway.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@thisisagile/easy-mongo",
3
- "version": "15.4.0",
3
+ "version": "15.5.1",
4
4
  "description": "Add support for MongoDB",
5
5
  "author": "Sander Hoogendoorn",
6
6
  "license": "MIT",
@@ -31,10 +31,10 @@
31
31
  "access": "public"
32
32
  },
33
33
  "devDependencies": {
34
- "@thisisagile/easy-test": "15.4.0"
34
+ "@thisisagile/easy-test": "15.5.1"
35
35
  },
36
36
  "dependencies": {
37
- "@thisisagile/easy": "^15.4.0",
37
+ "@thisisagile/easy": "^15.5.1",
38
38
  "mongodb": "^5.6.0"
39
39
  }
40
40
  }
@@ -0,0 +1,55 @@
1
+ import { stages } from './Stages';
2
+ import { MongoGateway } from './MongoGateway';
3
+ import { Collection } from './Collection';
4
+ import { MongoProvider } from './MongoProvider';
5
+ import { lucene, SearchDefinition } from './Lucene';
6
+ import { entries, Filter, Json, PageList, text, toPageList, tuple2 } from '@thisisagile/easy';
7
+
8
+ const { skip, take } = stages.skip;
9
+ const { replaceWith } = stages.replaceWith;
10
+ const { searchWithDef, searchMeta, facets } = lucene;
11
+
12
+ type FacetResult = { _id: string; count: number };
13
+ type Value = { label: string; value: string; count: number };
14
+ export const toFilters = (facets: unknown): Filter[] =>
15
+ entries(facets as Record<string, unknown>).map(([k, fs]) => ({
16
+ label: text(k).title.toString(),
17
+ field: k,
18
+ values: (fs as []).map((f: FacetResult) => toValue(f)),
19
+ }));
20
+
21
+ const toValue = (f: FacetResult): Value => ({ label: f._id ?? 'unknown', value: f._id ?? 'unknown', count: f.count });
22
+
23
+ export class AtlasSearchGateway extends MongoGateway {
24
+ constructor(
25
+ collection: Collection,
26
+ readonly searchDef: SearchDefinition,
27
+ readonly sortDef: Record<string, Record<string, 1 | -1>> = {},
28
+ provider: MongoProvider = collection.provider
29
+ ) {
30
+ super(collection, provider);
31
+ }
32
+
33
+ query = async (query: Record<keyof typeof this.searchDef, string | number>): Promise<PageList<Json>> => {
34
+ return tuple2(
35
+ this.aggregate(searchWithDef(query, this.searchDef), skip({ skip: (query?.skip as number) ?? 0 }), take({ take: (query?.take as number) ?? 250 })),
36
+ this.aggregate(
37
+ searchMeta(query, this.searchDef),
38
+ replaceWith({
39
+ total: '$count.lowerBound',
40
+ facets: Object.keys(facets(this.searchDef)).reduce((acc, k) => ({ ...acc, [k]: `$facet.${k}.buckets` }), {}),
41
+ })
42
+ )
43
+ )
44
+ .then(([data, meta]) => ({ data, meta: meta.first() as any }))
45
+ .then(({ data, meta }) =>
46
+ toPageList<Json>(data, {
47
+ total: meta?.total ?? 0,
48
+ skip: (query?.skip as number) ?? 0,
49
+ take: (query?.take as number) ?? 250,
50
+ sorts: Object.keys(this.sortDef),
51
+ filters: toFilters(meta.facets),
52
+ })
53
+ );
54
+ };
55
+ }
package/src/Lucene.ts CHANGED
@@ -1,5 +1,20 @@
1
- import { entries, Func, ifDefined, isFunction, on, OneOrMore, Optional, toArray, toList } from "@thisisagile/easy";
2
- import { toMongoType } from "./Utils";
1
+ import {
2
+ DateTime,
3
+ entries,
4
+ Func,
5
+ ifDefined,
6
+ ifNotEmpty,
7
+ isDefined,
8
+ isFunction,
9
+ List,
10
+ on,
11
+ OneOrMore,
12
+ Optional,
13
+ RequireAtLeastOne,
14
+ toArray,
15
+ toList,
16
+ } from '@thisisagile/easy';
17
+ import { toMongoType } from './Utils';
3
18
 
4
19
  type FuzzyOptions = {
5
20
  maxEdits: number;
@@ -7,9 +22,20 @@ type FuzzyOptions = {
7
22
  maxExpansions: number;
8
23
  };
9
24
 
25
+ export type Facet =
26
+ | { path: string; type: 'string'; numBuckets: number }
27
+ | { path: string; type: 'number'; boundaries: number[]; default?: string }
28
+ | { path: string; type: 'date'; boundaries: Date[]; default?: string };
29
+
10
30
  export type Operator = Func<Optional<object>, string>;
11
31
  export type Clause = object | Operator;
12
32
  export type Clauses = Record<string, Clause>;
33
+ export type SearchDefinition = Record<
34
+ string,
35
+ (
36
+ v: string | number
37
+ ) => RequireAtLeastOne<{ should?: Clauses; filter?: Clauses; must?: Clauses; mustNot?: Clauses; sort?: Record<string, 1 | -1>; facet?: Facet }>
38
+ >;
13
39
 
14
40
  type Compound = {
15
41
  must: OneOrMore<Clauses>;
@@ -18,50 +44,117 @@ type Compound = {
18
44
  filter: OneOrMore<Clauses>;
19
45
  };
20
46
 
47
+ const should = (query: Record<string, string | number>, def: SearchDefinition): Clauses[] => entries(query).mapDefined(([k, v]) => def[k]?.(v)?.should);
48
+ const must = (query: Record<string, string | number>, def: SearchDefinition): Clauses[] => entries(query).mapDefined(([k, v]) => def[k]?.(v)?.must);
49
+ const mustNot = (query: Record<string, string | number>, def: SearchDefinition): Clauses[] => entries(query).mapDefined(([k, v]) => def[k]?.(v)?.mustNot);
50
+ const filter = (query: Record<string, string | number>, def: SearchDefinition): Clauses[] => entries(query).mapDefined(([k, v]) => def[k]?.(v)?.filter);
51
+
52
+ const compound = (query: Record<string, string | number>, def: SearchDefinition): Partial<Compound> =>
53
+ entries({
54
+ should: ifNotEmpty(should(query, def).concat(filter(query, def), must(query, def), mustNot(query, def)), should(query, def), [
55
+ { wildcard: lucene.wildcard() },
56
+ ]),
57
+ ...ifNotEmpty(filter(query, def), f => ({ filter: f })),
58
+ ...ifNotEmpty(mustNot(query, def), m => ({ mustNot: m })),
59
+ ...ifNotEmpty(must(query, def), m => ({ must: m })),
60
+ }).reduce((res, [k, v]) => on(res, r => (r[k] = lucene.clauses(v))), {} as any);
61
+
21
62
  export const lucene = {
22
63
  clause: (c: Clauses) => entries(c).reduce((res, [k, v]) => res.add(isFunction(v) ? v(k) : v), toList()),
23
64
  clauses: (cs: OneOrMore<Clauses>) => toArray(cs).flatMap(c => lucene.clause(c)),
24
65
  search: (c: Partial<Compound>, index?: string) => ({
25
66
  $search: {
26
67
  ...ifDefined(index, { index }),
27
- compound: entries(c).reduce((res, [k, v]) => on(res, r => (r[k] = lucene.clauses(v))), {} as any)
28
- }
68
+ compound: entries(c).reduce((res, [k, v]) => on(res, r => (r[k] = lucene.clauses(v))), {} as any),
69
+ },
70
+ }),
71
+ searchWithDef: (query: Record<string, string | number>, options: SearchDefinition, index?: string) => {
72
+ const sort = entries(query)
73
+ .mapDefined(([k, v]) => options[k]?.(v)?.sort)
74
+ .first();
75
+ return {
76
+ $search: { ...ifDefined(index, { index }), compound: compound(query, options), ...ifDefined(sort, { sort }) },
77
+ };
78
+ },
79
+ searchMeta: (query: Record<string, string | number>, def: SearchDefinition, index?: string) => ({
80
+ $searchMeta: {
81
+ ...ifDefined(index, { index }),
82
+ facet: {
83
+ operator: {
84
+ compound: compound(query, def),
85
+ },
86
+ facets: lucene.facets(def),
87
+ },
88
+ },
29
89
  }),
90
+ exists: (): Operator => (path: string) => ({ exists: { path } }),
30
91
  text:
31
92
  (value?: OneOrMore<unknown>, fuzzy?: Partial<FuzzyOptions>): Operator =>
32
- (path: string ) =>
33
- ifDefined(value, v => ({
34
- text: {
35
- path: path === 'wildcard' ? { wildcard: '*' } : path,
36
- query: v,
37
- ...ifDefined(fuzzy, { fuzzy })
38
- }
39
- })),
93
+ (path: string) =>
94
+ ifDefined(value, v => ({
95
+ text: {
96
+ path: path === 'wildcard' ? { wildcard: '*' } : path,
97
+ query: v,
98
+ ...ifDefined(fuzzy, { fuzzy }),
99
+ },
100
+ })),
101
+ wildcard:
102
+ (value?: OneOrMore<unknown>): Operator =>
103
+ (path: string) => ({
104
+ wildcard: {
105
+ path: path === 'wildcard' ? { wildcard: '*' } : path,
106
+ query: ifDefined(value, value, '*'),
107
+ },
108
+ }),
40
109
  lt:
41
110
  (value: unknown): Operator =>
42
- (path: string) =>
43
- ifDefined(value, lt => ({ range: { path, lt } })),
111
+ (path: string) =>
112
+ ifDefined(value, lt => ({ range: { path, lt } })),
44
113
  lte:
45
114
  (value: unknown): Operator =>
46
- (path: string) =>
47
- ifDefined(value, lte => ({ range: { path, lte } })),
115
+ (path: string) =>
116
+ ifDefined(value, lte => ({ range: { path, lte } })),
48
117
  gt:
49
118
  (value: unknown): Operator =>
50
- (path: string) =>
51
- ifDefined(value, gt => ({ range: { path, gt } })),
119
+ (path: string) =>
120
+ ifDefined(value, gt => ({ range: { path, gt } })),
52
121
  gte:
53
122
  (value: unknown): Operator =>
54
- (path: string) =>
55
- ifDefined(value, gte => ({ range: { path, gte } })),
123
+ (path: string) =>
124
+ ifDefined(value, gte => ({ range: { path, gte } })),
56
125
  after: (date: unknown): Operator => lucene.gte(toMongoType(date)),
57
126
  before: (date: unknown): Operator => lucene.lt(toMongoType(date)),
58
127
  between:
59
128
  (after: unknown, before: unknown): Operator =>
60
- (path: string) => ({
61
- range: {
62
- path,
63
- gte: toMongoType(after),
64
- lt: toMongoType(before)
65
- }
66
- })
129
+ (path: string) => ({
130
+ range: {
131
+ path,
132
+ gte: toMongoType(after),
133
+ lt: toMongoType(before),
134
+ },
135
+ }),
136
+ facets: (def: SearchDefinition) =>
137
+ entries(def)
138
+ .filter(([k, v]) => isDefined(v(k)?.facet))
139
+ .map(([k, v]) => ({ [k]: v(k)?.facet }))
140
+ .reduce((acc, v) => ({ ...acc, ...v }), {}),
141
+ facet: {
142
+ string: (path: string, numBuckets = 1000): Facet => ({
143
+ type: 'string',
144
+ path,
145
+ numBuckets,
146
+ }),
147
+ number: (path: string, boundaries: List<number>, alt?: string): Facet => ({
148
+ type: 'number',
149
+ path,
150
+ boundaries,
151
+ ...ifDefined(alt, a => ({ default: a })),
152
+ }),
153
+ date: (path: string, boundaries: List<DateTime>, alt?: string): Facet => ({
154
+ type: 'date',
155
+ path,
156
+ boundaries: boundaries.mapDefined(b => b.toDate()),
157
+ ...ifDefined(alt, a => ({ default: a })),
158
+ }),
159
+ },
67
160
  };
@@ -58,7 +58,7 @@ export class MongoGateway implements Gateway<FindOptions> {
58
58
  }
59
59
 
60
60
  count(...filters: Optional<Filter>[]): Promise<number> {
61
- return this.aggregate(...filters, {$count: 'total' }).then(d => d.first().total as number ?? 0);
61
+ return this.aggregate(...filters, {$count: 'total' }).then(d => d.first()?.total as number ?? 0);
62
62
  }
63
63
 
64
64
  match(f: Filter): Promise<PageList<Json>> {