@adonis-agora/filter 0.9.0 → 0.10.0

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.
package/CHANGELOG.md CHANGED
@@ -1,5 +1,11 @@
1
1
  # @adonis-agora/filter
2
2
 
3
+ ## 0.10.0
4
+
5
+ ### Minor Changes
6
+
7
+ - [#67](https://github.com/DavideCarvalho/adonis-agora-filter/pull/67) [`1dd11c3`](https://github.com/DavideCarvalho/adonis-agora-filter/commit/1dd11c3563cd015d27627808cc3e23830ed4be50) Thanks [@DavideCarvalho](https://github.com/DavideCarvalho)! - In-memory adapter at `@adonis-agora/filter/in-memory`: `defineCollection({ fields, primaryKey, relations })` declares a row source (field types incl. `'string[]'`-style arrays, virtual fields, to-one/to-many relations), and `collection.query(rows)` is a `QueryBuilderLike` the existing runner drives unchanged — `applyFilter`, `applyCursor`, `applyFilterFromRequest`, `applyCursorFromRequest` and `groupByCountFromRequest` all work over a plain array with the same parsing, allow-listing and coercion. Evaluation mirrors the SQL the Lucid adapter emits (ILIKE, three-valued NULL logic, NULLS LAST asc / FIRST desc, EXISTS for to-many paths). `filterInMemory` / `cursorInMemory` do it in one call; `InMemoryQueryError` is thrown for SQL-only features (`computed`, `fullText`, `vectorSimilarity`).
8
+
3
9
  ## 0.9.0
4
10
 
5
11
  ### Minor Changes
package/README.md CHANGED
@@ -50,6 +50,21 @@ AND/OR composition. The `allowed`/`sortable`/`searchable` lists are the security
50
50
  boundary. The Lucid binding is structural (`QueryBuilderLike`) so any Lucid query
51
51
  builder works and the adapter is unit-testable.
52
52
 
53
+ ### In-memory lists
54
+
55
+ `@adonis-agora/filter/in-memory` runs the same input against a plain array — an
56
+ in-memory `QueryBuilderLike` the runner drives exactly like a Lucid query:
57
+
58
+ ```ts
59
+ import { defineCollection, filterInMemory } from '@adonis-agora/filter/in-memory'
60
+
61
+ const users = defineCollection<UserRow>({
62
+ fields: { name: 'string', age: 'number', fullName: { type: 'string', get: (u) => u.first + ' ' + u.last } },
63
+ })
64
+ const page = filterInMemory(users, rows, input, { allowed: ['name', 'age', 'fullName'] })
65
+ // { data, meta: { total, perPage, currentPage, lastPage, firstPage } }
66
+ ```
67
+
53
68
  See the [repository README](https://github.com/DavideCarvalho/adonis-filter).
54
69
 
55
70
  ## License
@@ -0,0 +1,268 @@
1
+ import { type CursorPage, type CursorParams } from './cursor.js';
2
+ import type { QueryBuilderLike } from './lucid_adapter.js';
3
+ import type { FilterConfig, FilterFieldKind, FilterInput } from './types.js';
4
+ /**
5
+ * The in-memory adapter: a {@link QueryBuilderLike} that evaluates against a plain JS array.
6
+ *
7
+ * The runner (`applyFilter`, `applyCursor`, `applyFilterFromRequest`, `groupByCountFromRequest`)
8
+ * does exactly what it does for a Lucid query — parse, alias-resolve, validate, allow-list, coerce —
9
+ * and then drives the same builder calls it would hand Lucid. This builder records those calls and
10
+ * evaluates them over rows instead of compiling SQL, so an in-memory listing speaks the same wire
11
+ * format, operators and error shapes as a database one, and a filter spec written for a model
12
+ * works unchanged over rows assembled in memory (several sources merged, a static catalog, a
13
+ * remote API page).
14
+ *
15
+ * The evaluation mirrors what Postgres does with the SQL the Lucid adapter emits — including the
16
+ * places that surprise people: three-valued NULL logic (a NULL value fails `notEquals`/`notIn`/
17
+ * `notBetween`, `NOT IN` a list holding NULL matches nothing), ILIKE for every LIKE-style operator,
18
+ * and NULLS LAST on ascending / NULLS FIRST on descending order.
19
+ */
20
+ /** A scalar array kind — an in-memory extension; see {@link InMemoryFieldType}. */
21
+ export type InMemoryArrayKind = 'string[]' | 'number[]' | 'boolean[]' | 'date[]';
22
+ /**
23
+ * A declared field type. The scalar kinds are the lib's own {@link FilterFieldKind}; the array
24
+ * kinds declare a list-valued field, on which a scalar operator matches when ANY element matches
25
+ * and a negated operator (`notEquals`, `notIn`, `notBetween`) matches when NO element does.
26
+ */
27
+ export type InMemoryFieldType = FilterFieldKind | InMemoryArrayKind;
28
+ /** A virtual field: a value computed from the row — the in-memory counterpart of `computed`. */
29
+ export interface InMemoryVirtualField<T> {
30
+ type: InMemoryFieldType;
31
+ get: (row: T) => unknown;
32
+ }
33
+ /** One entry of {@link DefineCollectionOptions.fields}: a stored field's type, or a virtual field. */
34
+ export type InMemoryFieldDeclaration<T> = InMemoryFieldType | InMemoryVirtualField<T>;
35
+ /** Relation cardinality. `*-to-one` reads a row (or null); `*-to-many` reads an array. */
36
+ export type InMemoryRelationKind = 'one-to-one' | 'many-to-one' | 'one-to-many' | 'many-to-many';
37
+ /**
38
+ * A relation a dotted filter path (`posts.title`) can cross. The runner turns such a path into a
39
+ * `whereHas`, evaluated here with EXISTS semantics: the row matches when at least one related row
40
+ * satisfies the nested conditions.
41
+ */
42
+ export interface InMemoryRelation<T> {
43
+ kind: InMemoryRelationKind;
44
+ /** The related collection — a thunk so two collections can reference each other. */
45
+ target: () => InMemoryCollection<any>;
46
+ /** Read the related row(s) off a row. `null`/`undefined` means no related row. */
47
+ get: (row: T) => unknown;
48
+ }
49
+ /** Options for {@link defineCollection}. */
50
+ export interface DefineCollectionOptions<T> {
51
+ /**
52
+ * The field declarations — what each field is, so filter values are compared as that kind
53
+ * (`'3'` equals `3` on a `number` field, `'true'` equals `true` on a `boolean`, ISO strings
54
+ * compare as instants on a `date`). A field that is not declared is read as an own property and
55
+ * compared by the kind its value has at runtime.
56
+ */
57
+ fields: Record<string, InMemoryFieldDeclaration<T>>;
58
+ /** The keyset tiebreaker for cursor pagination. Default `'id'`. */
59
+ primaryKey?: string;
60
+ /** Relations dotted filter paths may cross. */
61
+ relations?: Record<string, InMemoryRelation<T>>;
62
+ /**
63
+ * The collection's "table" name. A `distinct`/sort field qualified with it (`users.name`, the
64
+ * form {@link FilterConfig.table} makes projectable) reads the root field `name`.
65
+ */
66
+ name?: string;
67
+ }
68
+ interface ResolvedField<T> {
69
+ kind: FilterFieldKind;
70
+ array: boolean;
71
+ get: ((row: T) => unknown) | undefined;
72
+ }
73
+ /** A declared, reusable row source. Create one with {@link defineCollection}. */
74
+ export interface InMemoryCollection<T extends object> {
75
+ readonly name: string | undefined;
76
+ readonly primaryKey: string;
77
+ /**
78
+ * The declared fields as the colocated `filterable` map `defineFilter` accepts
79
+ * (`defineFilter({ filterable: users.filterable })`) — array kinds map to their element kind,
80
+ * which is what the runner coerces a filter value to.
81
+ */
82
+ readonly filterable: Readonly<Record<string, FilterFieldKind>>;
83
+ /** The declared fields as {@link FilterConfig.fieldTypes}, for `applyFilter` callers. */
84
+ readonly fieldTypes: Readonly<Record<string, {
85
+ kind: FilterFieldKind;
86
+ }>>;
87
+ /** Start a query over `rows` — hand the builder to the runner like a Lucid query. */
88
+ query(rows: Iterable<T>): InMemoryQueryBuilder<T>;
89
+ /** @internal */
90
+ readonly $fields: Readonly<Record<string, ResolvedField<T>>>;
91
+ /** @internal */
92
+ readonly $relations: Readonly<Record<string, InMemoryRelation<T>>>;
93
+ }
94
+ /**
95
+ * Thrown when the runner asks the in-memory builder for something only SQL can do: a raw
96
+ * predicate or ordering (policy `computed` fields, `fullText`, `vectorSimilarity`) — declare a
97
+ * virtual field instead — or a relation/field path the collection does not declare.
98
+ */
99
+ export declare class InMemoryQueryError extends Error {
100
+ constructor(message: string);
101
+ }
102
+ /**
103
+ * Declare a collection: its fields (and their types), virtual fields, primary key and relations.
104
+ *
105
+ * ```ts
106
+ * const posts = defineCollection<Post>({ fields: { id: 'number', title: 'string' } })
107
+ * const users = defineCollection<User>({
108
+ * fields: {
109
+ * id: 'number',
110
+ * name: 'string',
111
+ * age: 'number',
112
+ * tags: 'string[]',
113
+ * fullName: { type: 'string', get: (u) => `${u.first} ${u.last}` },
114
+ * },
115
+ * relations: { posts: { kind: 'one-to-many', target: () => posts, get: (u) => u.posts } },
116
+ * })
117
+ *
118
+ * const qb = users.query(rows)
119
+ * const { page, size } = applyFilter(qb, input, { allowed: ['name', 'posts.title'] })
120
+ * return qb.paginate(page, size)
121
+ * ```
122
+ */
123
+ export declare function defineCollection<T extends object>(options: DefineCollectionOptions<T>): InMemoryCollection<T>;
124
+ /** The pagination meta {@link InMemoryQueryBuilder.paginate} returns — Lucid's paginator fields. */
125
+ export interface InMemoryPageMeta {
126
+ total: number;
127
+ perPage: number;
128
+ currentPage: number;
129
+ lastPage: number;
130
+ firstPage: number;
131
+ }
132
+ /** One offset page — the shape of a serialized Lucid paginator (`{ meta, data }`). */
133
+ export interface InMemoryPage<T> {
134
+ data: T[];
135
+ meta: InMemoryPageMeta;
136
+ }
137
+ /**
138
+ * A {@link QueryBuilderLike} over an array. Created by {@link InMemoryCollection.query}; hand it to
139
+ * any runner entry point exactly as you would a Lucid query, then read the result with
140
+ * {@link all}, {@link paginate}, or by awaiting it (it is thenable, like a Lucid query — which is
141
+ * what lets `groupByCountFromRequest` run over it unchanged).
142
+ */
143
+ export declare class InMemoryQueryBuilder<T extends object> implements QueryBuilderLike {
144
+ readonly collection: InMemoryCollection<T>;
145
+ private readonly rows;
146
+ private readonly clauses;
147
+ private readonly sorts;
148
+ private readonly selects;
149
+ private readonly groups;
150
+ private readonly groupSearches;
151
+ private distinctFields;
152
+ private countAlias;
153
+ private limitCount;
154
+ private offsetCount;
155
+ constructor(collection: InMemoryCollection<T>, rows?: readonly T[]);
156
+ private field;
157
+ /** Strip a leading `<collection name>.` qualifier. */
158
+ private unqualify;
159
+ /**
160
+ * Read a (possibly dotted) path off a row. A dotted path crosses a to-one relation; crossing a
161
+ * to-many relation is ambiguous outside a `whereHas` (which the runner uses for filters) and is
162
+ * rejected.
163
+ */
164
+ read(row: T, rawPath: string): unknown;
165
+ /** The declared kind of a path (following to-one relations), or `unknown`. */
166
+ private kindOf;
167
+ /**
168
+ * Build a leaf predicate. `match` tests one non-null element; `negated` flips the element-level
169
+ * result into "no element matches" — with SQL's rule that a NULL value (or an uncastable
170
+ * comparison) satisfies neither a condition nor its negation.
171
+ */
172
+ private leaf;
173
+ private equalsLeaf;
174
+ private compareLeaf;
175
+ private inLeaf;
176
+ private betweenLeaf;
177
+ private likeLeaf;
178
+ private add;
179
+ private group;
180
+ /**
181
+ * Does `row` satisfy every recorded condition? Clauses chain left to right the way knex joins
182
+ * them — `a AND b OR c` — so AND binds tighter than OR, exactly as the emitted SQL would.
183
+ */
184
+ matches(row: T): boolean;
185
+ where(callback: (qb: QueryBuilderLike) => void): this;
186
+ where(column: string, value: unknown): this;
187
+ where(column: string, operator: string, value: unknown): this;
188
+ orWhere(callback: (qb: QueryBuilderLike) => void): this;
189
+ whereHas(relation: any, callback: (qb: QueryBuilderLike) => void): this;
190
+ whereNot(column: string, value: unknown): this;
191
+ whereIn(column: string, values: unknown[]): this;
192
+ whereNotIn(column: string, values: unknown[]): this;
193
+ whereNull(column: string): this;
194
+ whereNotNull(column: string): this;
195
+ whereBetween(column: string, range: [unknown, unknown]): this;
196
+ whereNotBetween(column: string, range: [unknown, unknown]): this;
197
+ whereILike(column: string, value: string): this;
198
+ orWhereILike(column: string, value: string): this;
199
+ orderBy(column: string, direction: 'asc' | 'desc'): this;
200
+ /**
201
+ * Only the group-by-count search predicate (`LOWER(??) LIKE ?`) is understood; any other raw
202
+ * SQL — a policy's `computed` fields, `fullText`, `vectorSimilarity` — throws
203
+ * {@link InMemoryQueryError}. Declare a virtual field on the collection instead of `computed`.
204
+ */
205
+ whereRaw(sql: string, bindings?: readonly unknown[]): this;
206
+ orderByRaw(sql: string, _bindings?: readonly unknown[]): this;
207
+ distinct(...columns: string[]): this;
208
+ limit(count: number): this;
209
+ offset(n: number): this;
210
+ select(...columns: string[]): this;
211
+ count(column: string): this;
212
+ groupBy(...columns: string[]): this;
213
+ private compareRows;
214
+ /** Ascending comparison with NULLs sorting last (so NULLS FIRST once a desc sort negates it). */
215
+ private compareValues;
216
+ /** Filter + sort (+ distinct / projection / aggregation), before limit/offset. */
217
+ private evaluate;
218
+ /**
219
+ * `GROUP BY` over the matched rows. An array-typed grouping field is unnested — each element is
220
+ * its own group — which is what a tag picker wants (Postgres would group whole arrays).
221
+ */
222
+ private aggregate;
223
+ private window;
224
+ /**
225
+ * Execute: the matching rows in order, honouring `limit`/`offset` (which is what a cursor page
226
+ * sets). Under a `distinct`, a `select` or a `groupBy`, the rows are projection objects — just
227
+ * as a Lucid query returns them.
228
+ */
229
+ all(): T[];
230
+ /** How many rows (or distinct tuples / groups) match, ignoring `limit`/`offset`. */
231
+ total(): number;
232
+ /**
233
+ * One offset page — the in-memory `query.paginate(page, size)`. Feed it the `{ page, size }`
234
+ * the runner resolved (clamped and defaulted), never raw request values.
235
+ */
236
+ paginate(page: number, perPage: number): InMemoryPage<T>;
237
+ /**
238
+ * Thenable, like a Lucid query: `await qb` resolves to {@link all}. This is what lets helpers
239
+ * that execute a builder by awaiting it (`groupByCountFromRequest`) run over an array.
240
+ */
241
+ then<R1 = T[], R2 = never>(onfulfilled?: ((rows: T[]) => R1 | PromiseLike<R1>) | null, onrejected?: ((reason: unknown) => R2 | PromiseLike<R2>) | null): Promise<R1 | R2>;
242
+ }
243
+ /**
244
+ * Filter, search, sort and offset-paginate `rows` in one call: {@link applyFilter} over a fresh
245
+ * builder, then {@link InMemoryQueryBuilder.paginate} with the resolved page. A `distinct` request
246
+ * pages the distinct tuples instead of rows.
247
+ *
248
+ * ```ts
249
+ * const page = filterInMemory(users, rows, parseFilterRequest(ctx.request.qs()), {
250
+ * allowed: ['name', 'age', 'posts.title'],
251
+ * searchable: ['name'],
252
+ * fieldTypes: users.fieldTypes,
253
+ * })
254
+ * // → { data, meta: { total, perPage, currentPage, lastPage, firstPage } }
255
+ * ```
256
+ */
257
+ export declare function filterInMemory<T extends object>(collection: InMemoryCollection<T>, rows: Iterable<T>, input: FilterInput, config: FilterConfig): InMemoryPage<T>;
258
+ /**
259
+ * The keyset (cursor) counterpart of {@link filterInMemory}: {@link applyCursor} over a fresh
260
+ * builder (the primary key defaults to the collection's), then `buildCursorPage`. Keyset values
261
+ * are read through the collection, so a virtual field or a to-one relation path works as a cursor
262
+ * sort field.
263
+ */
264
+ export declare function cursorInMemory<T extends object>(collection: InMemoryCollection<T>, rows: Iterable<T>, input: FilterInput & CursorParams, config: FilterConfig & {
265
+ primaryKey?: string;
266
+ }): CursorPage<T>;
267
+ export {};
268
+ //# sourceMappingURL=in_memory.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"in_memory.d.ts","sourceRoot":"","sources":["../../src/in_memory.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,759 @@
1
+ import { buildCursorPage, } from './cursor.js';
2
+ import { applyCursor, applyFilter } from './runner.js';
3
+ /**
4
+ * Thrown when the runner asks the in-memory builder for something only SQL can do: a raw
5
+ * predicate or ordering (policy `computed` fields, `fullText`, `vectorSimilarity`) — declare a
6
+ * virtual field instead — or a relation/field path the collection does not declare.
7
+ */
8
+ export class InMemoryQueryError extends Error {
9
+ constructor(message) {
10
+ super(message);
11
+ this.name = 'InMemoryQueryError';
12
+ }
13
+ }
14
+ const ARRAY_KINDS = {
15
+ 'string[]': 'string',
16
+ 'number[]': 'number',
17
+ 'boolean[]': 'boolean',
18
+ 'date[]': 'date',
19
+ };
20
+ function resolveType(type) {
21
+ const element = ARRAY_KINDS[type];
22
+ return element ? { kind: element, array: true } : { kind: type, array: false };
23
+ }
24
+ /**
25
+ * Declare a collection: its fields (and their types), virtual fields, primary key and relations.
26
+ *
27
+ * ```ts
28
+ * const posts = defineCollection<Post>({ fields: { id: 'number', title: 'string' } })
29
+ * const users = defineCollection<User>({
30
+ * fields: {
31
+ * id: 'number',
32
+ * name: 'string',
33
+ * age: 'number',
34
+ * tags: 'string[]',
35
+ * fullName: { type: 'string', get: (u) => `${u.first} ${u.last}` },
36
+ * },
37
+ * relations: { posts: { kind: 'one-to-many', target: () => posts, get: (u) => u.posts } },
38
+ * })
39
+ *
40
+ * const qb = users.query(rows)
41
+ * const { page, size } = applyFilter(qb, input, { allowed: ['name', 'posts.title'] })
42
+ * return qb.paginate(page, size)
43
+ * ```
44
+ */
45
+ export function defineCollection(options) {
46
+ const fields = Object.create(null);
47
+ const filterable = {};
48
+ const fieldTypes = {};
49
+ for (const [name, declaration] of Object.entries(options.fields)) {
50
+ const virtual = typeof declaration === 'object' ? declaration : undefined;
51
+ const { kind, array } = resolveType(virtual ? virtual.type : declaration);
52
+ fields[name] = { kind, array, get: virtual?.get };
53
+ filterable[name] = kind;
54
+ fieldTypes[name] = { kind };
55
+ }
56
+ const relations = Object.create(null);
57
+ for (const [name, relation] of Object.entries(options.relations ?? {})) {
58
+ relations[name] = relation;
59
+ }
60
+ const collection = {
61
+ name: options.name,
62
+ primaryKey: options.primaryKey ?? 'id',
63
+ filterable,
64
+ fieldTypes,
65
+ $fields: fields,
66
+ $relations: relations,
67
+ query: (rows) => new InMemoryQueryBuilder(collection, [...rows]),
68
+ };
69
+ return collection;
70
+ }
71
+ function isNil(value) {
72
+ return value === null || value === undefined;
73
+ }
74
+ function hasToMillis(value) {
75
+ return (typeof value === 'object' &&
76
+ value !== null &&
77
+ typeof value.toMillis === 'function');
78
+ }
79
+ /** The kind a runtime value has — used for undeclared (`unknown`/`json`) fields. */
80
+ function inferKind(value) {
81
+ if (typeof value === 'number' || typeof value === 'bigint')
82
+ return 'number';
83
+ if (typeof value === 'boolean')
84
+ return 'boolean';
85
+ if (typeof value === 'string')
86
+ return 'string';
87
+ if (value instanceof Date || hasToMillis(value))
88
+ return 'date';
89
+ return 'json';
90
+ }
91
+ /**
92
+ * Normalize a value to a comparable primitive of `kind`, the way Postgres casts a bound literal to
93
+ * the column type. `undefined` means "cannot be cast" — the comparison is then false, where
94
+ * Postgres would have rejected the query outright.
95
+ */
96
+ function normalize(value, kind) {
97
+ if (isNil(value))
98
+ return undefined;
99
+ switch (kind) {
100
+ case 'number': {
101
+ if (typeof value === 'number')
102
+ return Number.isFinite(value) ? value : undefined;
103
+ if (typeof value === 'bigint')
104
+ return Number(value);
105
+ if (typeof value === 'string' && value.trim() !== '') {
106
+ const n = Number(value.trim());
107
+ return Number.isFinite(n) ? n : undefined;
108
+ }
109
+ return undefined;
110
+ }
111
+ case 'boolean': {
112
+ if (typeof value === 'boolean')
113
+ return value;
114
+ if (value === 1 || value === 0)
115
+ return value === 1;
116
+ if (typeof value === 'string') {
117
+ const v = value.trim().toLowerCase();
118
+ if (v === 'true' || v === '1')
119
+ return true;
120
+ if (v === 'false' || v === '0')
121
+ return false;
122
+ }
123
+ return undefined;
124
+ }
125
+ case 'date': {
126
+ if (value instanceof Date) {
127
+ const t = value.getTime();
128
+ return Number.isNaN(t) ? undefined : t;
129
+ }
130
+ if (hasToMillis(value))
131
+ return value.toMillis();
132
+ if (typeof value === 'number')
133
+ return Number.isFinite(value) ? value : undefined;
134
+ if (typeof value === 'string') {
135
+ const t = Date.parse(value);
136
+ return Number.isNaN(t) ? undefined : t;
137
+ }
138
+ return undefined;
139
+ }
140
+ case 'string':
141
+ return typeof value === 'string' ? value : stringify(value);
142
+ default:
143
+ // json / unknown: structural equality only.
144
+ return typeof value === 'object' ? JSON.stringify(value) : value;
145
+ }
146
+ }
147
+ /** Text form of a value — what a LIKE on a non-text column matches against. */
148
+ function stringify(value) {
149
+ if (typeof value === 'string')
150
+ return value;
151
+ if (value instanceof Date)
152
+ return value.toISOString();
153
+ if (hasToMillis(value))
154
+ return new Date(value.toMillis()).toISOString();
155
+ if (typeof value === 'object' && value !== null)
156
+ return JSON.stringify(value);
157
+ return String(value);
158
+ }
159
+ /**
160
+ * Compare a row value to a comparand under `kind` (`json`/`unknown` → the row value's own kind).
161
+ * `undefined` when either side cannot be cast or the kind has no ordering.
162
+ */
163
+ function compare(rowValue, comparand, declared) {
164
+ const kind = declared === 'json' || declared === 'unknown' ? inferKind(rowValue) : declared;
165
+ const a = normalize(rowValue, kind);
166
+ const b = normalize(comparand, kind);
167
+ if (a === undefined || b === undefined)
168
+ return undefined;
169
+ if (typeof a === 'number' && typeof b === 'number')
170
+ return a - b;
171
+ if (typeof a === 'boolean' && typeof b === 'boolean')
172
+ return Number(a) - Number(b);
173
+ if (typeof a === 'string' && typeof b === 'string') {
174
+ // Code-unit order — Postgres' "C" collation. Deterministic and locale-free, which a keyset
175
+ // cursor needs: the seek predicate and the ORDER BY must agree on every pair of values.
176
+ return a < b ? -1 : a > b ? 1 : 0;
177
+ }
178
+ return a === b ? 0 : undefined;
179
+ }
180
+ /** Compile a LIKE pattern (backslash escapes, `%`, `_`) into an anchored RegExp. */
181
+ function likeToRegExp(pattern, caseInsensitive) {
182
+ let source = '';
183
+ for (let i = 0; i < pattern.length; i++) {
184
+ const ch = pattern[i];
185
+ if (ch === '\\' && i + 1 < pattern.length) {
186
+ source += escapeRegExp(pattern[++i]);
187
+ }
188
+ else if (ch === '%') {
189
+ source += '.*';
190
+ }
191
+ else if (ch === '_') {
192
+ source += '.';
193
+ }
194
+ else {
195
+ source += escapeRegExp(ch);
196
+ }
197
+ }
198
+ return new RegExp(`^${source}$`, caseInsensitive ? 'is' : 's');
199
+ }
200
+ function escapeRegExp(ch) {
201
+ return ch.replace(/[.*+?^${}()|[\]\\/]/g, '\\$&');
202
+ }
203
+ /** Relation targets normalized to a list (a to-one relation yields zero or one row). */
204
+ function relatedRows(value) {
205
+ if (isNil(value))
206
+ return [];
207
+ if (Array.isArray(value))
208
+ return value.filter((v) => !isNil(v));
209
+ return [value];
210
+ }
211
+ /** Parse a `expr AS alias` select/count argument. */
212
+ function parseAlias(expression) {
213
+ const match = /^\s*(.+?)\s+as\s+([A-Za-z_][A-Za-z0-9_]*)\s*$/i.exec(expression);
214
+ return match
215
+ ? { expr: match[1].trim(), alias: match[2] }
216
+ : { expr: expression.trim(), alias: expression.trim() };
217
+ }
218
+ /** The raw predicate the group-by-count search emits — the only raw SQL this adapter understands. */
219
+ const GROUP_SEARCH_SQL = /^\s*LOWER\(\?\?\)\s+LIKE\s+\?\s*$/i;
220
+ /**
221
+ * A {@link QueryBuilderLike} over an array. Created by {@link InMemoryCollection.query}; hand it to
222
+ * any runner entry point exactly as you would a Lucid query, then read the result with
223
+ * {@link all}, {@link paginate}, or by awaiting it (it is thenable, like a Lucid query — which is
224
+ * what lets `groupByCountFromRequest` run over it unchanged).
225
+ */
226
+ export class InMemoryQueryBuilder {
227
+ collection;
228
+ rows;
229
+ clauses = [];
230
+ sorts = [];
231
+ selects = [];
232
+ groups = [];
233
+ groupSearches = [];
234
+ distinctFields = [];
235
+ countAlias;
236
+ limitCount;
237
+ offsetCount;
238
+ constructor(collection, rows = []) {
239
+ this.collection = collection;
240
+ this.rows = rows;
241
+ }
242
+ // -- field access -----------------------------------------------------------------------------
243
+ field(name) {
244
+ return this.collection.$fields[name];
245
+ }
246
+ /** Strip a leading `<collection name>.` qualifier. */
247
+ unqualify(path) {
248
+ const name = this.collection.name;
249
+ return name !== undefined && path.startsWith(`${name}.`) ? path.slice(name.length + 1) : path;
250
+ }
251
+ /**
252
+ * Read a (possibly dotted) path off a row. A dotted path crosses a to-one relation; crossing a
253
+ * to-many relation is ambiguous outside a `whereHas` (which the runner uses for filters) and is
254
+ * rejected.
255
+ */
256
+ read(row, rawPath) {
257
+ const path = this.unqualify(rawPath);
258
+ const dot = path.indexOf('.');
259
+ if (dot === -1) {
260
+ const declared = this.field(path);
261
+ if (declared?.get)
262
+ return declared.get(row);
263
+ return Object.hasOwn(row, path) ? row[path] : undefined;
264
+ }
265
+ const head = path.slice(0, dot);
266
+ const relation = this.collection.$relations[head];
267
+ if (!relation) {
268
+ throw new InMemoryQueryError(`"${rawPath}" crosses "${head}", which is not a relation declared on this collection.`);
269
+ }
270
+ if (relation.kind === 'one-to-many' || relation.kind === 'many-to-many') {
271
+ throw new InMemoryQueryError(`"${rawPath}" reads through the to-many relation "${head}" — only a filter (EXISTS) can cross it.`);
272
+ }
273
+ const related = relatedRows(relation.get(row))[0];
274
+ if (related === undefined)
275
+ return undefined;
276
+ return relation
277
+ .target()
278
+ .query([])
279
+ .read(related, path.slice(dot + 1));
280
+ }
281
+ /** The declared kind of a path (following to-one relations), or `unknown`. */
282
+ kindOf(rawPath) {
283
+ const path = this.unqualify(rawPath);
284
+ const dot = path.indexOf('.');
285
+ if (dot === -1)
286
+ return this.field(path) ?? { kind: 'unknown', array: false };
287
+ const relation = this.collection.$relations[path.slice(0, dot)];
288
+ if (!relation)
289
+ return { kind: 'unknown', array: false };
290
+ return relation
291
+ .target()
292
+ .query([])
293
+ .kindOf(path.slice(dot + 1));
294
+ }
295
+ /**
296
+ * Build a leaf predicate. `match` tests one non-null element; `negated` flips the element-level
297
+ * result into "no element matches" — with SQL's rule that a NULL value (or an uncastable
298
+ * comparison) satisfies neither a condition nor its negation.
299
+ */
300
+ leaf(path, match, negated = false) {
301
+ const { kind, array } = this.kindOf(path);
302
+ return (row) => {
303
+ const value = this.read(row, path);
304
+ if (isNil(value))
305
+ return false;
306
+ if (array || (Array.isArray(value) && (kind === 'unknown' || kind === 'json'))) {
307
+ const elements = (Array.isArray(value) ? value : [value]).filter((e) => !isNil(e));
308
+ const results = elements.map((e) => match(e, kind));
309
+ if (negated)
310
+ return results.every((r) => r === false);
311
+ return results.some((r) => r === true);
312
+ }
313
+ const result = match(value, kind);
314
+ if (result === undefined)
315
+ return false;
316
+ return negated ? !result : result;
317
+ };
318
+ }
319
+ equalsLeaf(path, value, negated) {
320
+ return this.leaf(path, (e, kind) => {
321
+ const c = compare(e, value, kind);
322
+ return c === undefined ? undefined : c === 0;
323
+ }, negated);
324
+ }
325
+ compareLeaf(path, operator, value) {
326
+ switch (operator) {
327
+ case '=':
328
+ return isNil(value) ? () => false : this.equalsLeaf(path, value, false);
329
+ case '!=':
330
+ case '<>':
331
+ return isNil(value) ? () => false : this.equalsLeaf(path, value, true);
332
+ case '>':
333
+ case '>=':
334
+ case '<':
335
+ case '<=':
336
+ if (isNil(value))
337
+ return () => false;
338
+ return this.leaf(path, (e, kind) => {
339
+ const c = compare(e, value, kind);
340
+ if (c === undefined)
341
+ return undefined;
342
+ if (operator === '>')
343
+ return c > 0;
344
+ if (operator === '>=')
345
+ return c >= 0;
346
+ if (operator === '<')
347
+ return c < 0;
348
+ return c <= 0;
349
+ });
350
+ default:
351
+ throw new InMemoryQueryError(`Unsupported comparison operator "${operator}".`);
352
+ }
353
+ }
354
+ inLeaf(path, values, negated) {
355
+ // SQL: `x IN ()` is false and `x NOT IN ()` is true for every row, NULLs included (knex emits
356
+ // 1 = 0 / 1 = 1); `x NOT IN (…, NULL)` is never true.
357
+ if (values.length === 0)
358
+ return () => negated;
359
+ if (negated && values.some(isNil))
360
+ return () => false;
361
+ const candidates = values.filter((v) => !isNil(v));
362
+ return this.leaf(path, (e, kind) => {
363
+ let unknown = false;
364
+ for (const candidate of candidates) {
365
+ const c = compare(e, candidate, kind);
366
+ if (c === 0)
367
+ return true;
368
+ if (c === undefined)
369
+ unknown = true;
370
+ }
371
+ return unknown ? undefined : false;
372
+ }, negated);
373
+ }
374
+ betweenLeaf(path, range, negated) {
375
+ const [low, high] = Array.isArray(range) ? range : [undefined, undefined];
376
+ if (isNil(low) || isNil(high))
377
+ return () => false;
378
+ return this.leaf(path, (e, kind) => {
379
+ const lo = compare(e, low, kind);
380
+ const hi = compare(e, high, kind);
381
+ if (lo === undefined || hi === undefined)
382
+ return undefined;
383
+ return lo >= 0 && hi <= 0;
384
+ }, negated);
385
+ }
386
+ likeLeaf(path, pattern) {
387
+ const regex = likeToRegExp(pattern, true);
388
+ return this.leaf(path, (e) => regex.test(stringify(e)));
389
+ }
390
+ add(test, or = false) {
391
+ this.clauses.push({ or, test });
392
+ return this;
393
+ }
394
+ group(callback, or) {
395
+ const child = new InMemoryQueryBuilder(this.collection);
396
+ callback(child);
397
+ // An empty group compiles to nothing in knex — not to an always-true/false clause.
398
+ if (child.clauses.length === 0)
399
+ return this;
400
+ return this.add((row) => child.matches(row), or);
401
+ }
402
+ /**
403
+ * Does `row` satisfy every recorded condition? Clauses chain left to right the way knex joins
404
+ * them — `a AND b OR c` — so AND binds tighter than OR, exactly as the emitted SQL would.
405
+ */
406
+ matches(row) {
407
+ let result = false;
408
+ let segment = true;
409
+ this.clauses.forEach((clause, index) => {
410
+ if (clause.or && index > 0) {
411
+ result ||= segment;
412
+ segment = true;
413
+ }
414
+ segment &&= clause.test(row);
415
+ });
416
+ return this.clauses.length === 0 ? true : result || segment;
417
+ }
418
+ where(...args) {
419
+ if (typeof args[0] === 'function') {
420
+ return this.group(args[0], false);
421
+ }
422
+ const column = args[0];
423
+ if (args.length >= 3)
424
+ return this.add(this.compareLeaf(column, String(args[1]), args[2]));
425
+ // knex compiles `where(col, null)` to `col IS NULL`.
426
+ if (isNil(args[1]))
427
+ return this.whereNull(column);
428
+ return this.add(this.equalsLeaf(column, args[1], false));
429
+ }
430
+ orWhere(callback) {
431
+ return this.group(callback, true);
432
+ }
433
+ // biome-ignore lint/suspicious/noExplicitAny: matches QueryBuilderLike.whereHas (see its docblock).
434
+ whereHas(relation, callback) {
435
+ const name = String(relation);
436
+ const declared = this.collection.$relations[name];
437
+ if (!declared) {
438
+ throw new InMemoryQueryError(`"${name}" is not a relation declared on this collection.`);
439
+ }
440
+ const child = new InMemoryQueryBuilder(declared.target());
441
+ callback(child);
442
+ return this.add((row) => relatedRows(declared.get(row)).some((r) => child.matches(r)));
443
+ }
444
+ whereNot(column, value) {
445
+ if (isNil(value))
446
+ return this.whereNotNull(column);
447
+ return this.add(this.equalsLeaf(column, value, true));
448
+ }
449
+ whereIn(column, values) {
450
+ return this.add(this.inLeaf(column, Array.isArray(values) ? values : [values], false));
451
+ }
452
+ whereNotIn(column, values) {
453
+ return this.add(this.inLeaf(column, Array.isArray(values) ? values : [values], true));
454
+ }
455
+ whereNull(column) {
456
+ return this.add((row) => isNil(this.read(row, column)));
457
+ }
458
+ whereNotNull(column) {
459
+ return this.add((row) => !isNil(this.read(row, column)));
460
+ }
461
+ whereBetween(column, range) {
462
+ return this.add(this.betweenLeaf(column, range, false));
463
+ }
464
+ whereNotBetween(column, range) {
465
+ return this.add(this.betweenLeaf(column, range, true));
466
+ }
467
+ whereILike(column, value) {
468
+ return this.add(this.likeLeaf(column, value));
469
+ }
470
+ orWhereILike(column, value) {
471
+ return this.add(this.likeLeaf(column, value), true);
472
+ }
473
+ orderBy(column, direction) {
474
+ this.sorts.push({ field: column, direction: direction === 'desc' ? 'desc' : 'asc' });
475
+ return this;
476
+ }
477
+ /**
478
+ * Only the group-by-count search predicate (`LOWER(??) LIKE ?`) is understood; any other raw
479
+ * SQL — a policy's `computed` fields, `fullText`, `vectorSimilarity` — throws
480
+ * {@link InMemoryQueryError}. Declare a virtual field on the collection instead of `computed`.
481
+ */
482
+ whereRaw(sql, bindings = []) {
483
+ if (GROUP_SEARCH_SQL.test(sql) && typeof bindings[0] === 'string') {
484
+ const field = bindings[0];
485
+ const pattern = likeToRegExp(String(bindings[1] ?? ''), false);
486
+ this.groupSearches.push({ field, pattern });
487
+ return this.add(this.leaf(field, (e) => pattern.test(stringify(e).toLowerCase())), false);
488
+ }
489
+ throw new InMemoryQueryError(`The in-memory adapter cannot evaluate raw SQL (${JSON.stringify(sql)}). Policy \`computed\` fields, \`fullText\` and \`vectorSimilarity\` are SQL-only — declare a virtual field on the collection instead.`);
490
+ }
491
+ orderByRaw(sql, _bindings = []) {
492
+ throw new InMemoryQueryError(`The in-memory adapter cannot order by raw SQL (${JSON.stringify(sql)}). Declare a virtual field on the collection and sort on it instead.`);
493
+ }
494
+ distinct(...columns) {
495
+ this.distinctFields = columns;
496
+ return this;
497
+ }
498
+ limit(count) {
499
+ this.limitCount = Math.max(0, count);
500
+ return this;
501
+ }
502
+ offset(n) {
503
+ this.offsetCount = Math.max(0, n);
504
+ return this;
505
+ }
506
+ select(...columns) {
507
+ for (const column of columns)
508
+ this.selects.push(parseAlias(column));
509
+ return this;
510
+ }
511
+ count(column) {
512
+ const { expr, alias } = parseAlias(column);
513
+ if (expr !== '*') {
514
+ throw new InMemoryQueryError(`Only count('*') is supported in memory, got "${column}".`);
515
+ }
516
+ this.countAlias = alias;
517
+ return this;
518
+ }
519
+ groupBy(...columns) {
520
+ this.groups.push(...columns);
521
+ return this;
522
+ }
523
+ // -- execution --------------------------------------------------------------------------------
524
+ compareRows(a, b) {
525
+ for (const { field, direction } of this.sorts) {
526
+ const c = this.compareValues(this.read(a, field), this.read(b, field), this.kindOf(field).kind);
527
+ if (c !== 0)
528
+ return direction === 'desc' ? -c : c;
529
+ }
530
+ return 0;
531
+ }
532
+ /** Ascending comparison with NULLs sorting last (so NULLS FIRST once a desc sort negates it). */
533
+ compareValues(a, b, kind) {
534
+ if (isNil(a))
535
+ return isNil(b) ? 0 : 1;
536
+ if (isNil(b))
537
+ return -1;
538
+ return compare(a, b, kind) ?? 0;
539
+ }
540
+ /** Filter + sort (+ distinct / projection / aggregation), before limit/offset. */
541
+ evaluate() {
542
+ const matched = this.rows.filter((row) => this.matches(row));
543
+ if (this.groups.length > 0)
544
+ return this.aggregate(matched);
545
+ const sorted = this.sorts.length > 0 ? [...matched].sort((a, b) => this.compareRows(a, b)) : matched;
546
+ if (this.distinctFields.length > 0) {
547
+ const seen = new Set();
548
+ const out = [];
549
+ for (const row of sorted) {
550
+ const projected = {};
551
+ const key = [];
552
+ for (const field of this.distinctFields) {
553
+ const value = this.read(row, field);
554
+ projected[this.unqualify(field)] = value;
555
+ key.push(normalize(value, this.kindOf(field).kind) ?? null);
556
+ }
557
+ const k = JSON.stringify(key);
558
+ if (!seen.has(k)) {
559
+ seen.add(k);
560
+ out.push(projected);
561
+ }
562
+ }
563
+ return out;
564
+ }
565
+ if (this.selects.length > 0) {
566
+ return sorted.map((row) => {
567
+ const projected = {};
568
+ for (const { expr, alias } of this.selects)
569
+ projected[alias] = this.read(row, expr);
570
+ return projected;
571
+ });
572
+ }
573
+ return sorted;
574
+ }
575
+ /**
576
+ * `GROUP BY` over the matched rows. An array-typed grouping field is unnested — each element is
577
+ * its own group — which is what a tag picker wants (Postgres would group whole arrays).
578
+ */
579
+ aggregate(rows) {
580
+ const columns = this.groups;
581
+ const groups = new Map();
582
+ const single = columns.length === 1 ? columns[0] : undefined;
583
+ const unnest = single !== undefined && this.kindOf(single).array;
584
+ const searches = this.groupSearches.filter((s) => s.field === single);
585
+ for (const row of rows) {
586
+ const tuples = [];
587
+ if (unnest) {
588
+ const value = this.read(row, single);
589
+ const elements = Array.isArray(value) ? value : isNil(value) ? [null] : [value];
590
+ for (const element of elements) {
591
+ if (searches.every((s) => !isNil(element) && s.pattern.test(stringify(element).toLowerCase()))) {
592
+ tuples.push([element]);
593
+ }
594
+ }
595
+ }
596
+ else {
597
+ tuples.push(columns.map((c) => this.read(row, c)));
598
+ }
599
+ for (const values of tuples) {
600
+ const key = JSON.stringify(values.map((v, i) => normalize(v, this.kindOf(columns[i]).kind) ?? null));
601
+ const group = groups.get(key);
602
+ if (group)
603
+ group.count++;
604
+ else
605
+ groups.set(key, { values, count: 1 });
606
+ }
607
+ }
608
+ const outputs = [...groups.values()].map(({ values, count }) => {
609
+ const row = {};
610
+ const selects = this.selects.length > 0 ? this.selects : columns.map((c) => ({ expr: c, alias: c }));
611
+ for (const { expr, alias } of selects) {
612
+ const index = columns.indexOf(expr);
613
+ if (index === -1) {
614
+ throw new InMemoryQueryError(`"${expr}" is selected but not grouped by.`);
615
+ }
616
+ row[alias] = values[index];
617
+ }
618
+ if (this.countAlias !== undefined)
619
+ row[this.countAlias] = count;
620
+ return { row, values, count };
621
+ });
622
+ outputs.sort((a, b) => {
623
+ for (const { field, direction } of this.sorts) {
624
+ let c;
625
+ if (field === this.countAlias) {
626
+ c = a.count - b.count;
627
+ }
628
+ else {
629
+ const index = columns.indexOf(field);
630
+ const aliasIndex = this.selects.findIndex((s) => s.alias === field);
631
+ const i = index !== -1
632
+ ? index
633
+ : aliasIndex !== -1
634
+ ? columns.indexOf(this.selects[aliasIndex].expr)
635
+ : -1;
636
+ if (i === -1)
637
+ throw new InMemoryQueryError(`Cannot order grouped rows by "${field}".`);
638
+ c = this.compareValues(a.values[i], b.values[i], this.kindOf(columns[i]).kind);
639
+ }
640
+ if (c !== 0)
641
+ return direction === 'desc' ? -c : c;
642
+ }
643
+ return 0;
644
+ });
645
+ return outputs.map((o) => o.row);
646
+ }
647
+ window(rows) {
648
+ const start = this.offsetCount ?? 0;
649
+ const end = this.limitCount === undefined ? undefined : start + this.limitCount;
650
+ return rows.slice(start, end);
651
+ }
652
+ /**
653
+ * Execute: the matching rows in order, honouring `limit`/`offset` (which is what a cursor page
654
+ * sets). Under a `distinct`, a `select` or a `groupBy`, the rows are projection objects — just
655
+ * as a Lucid query returns them.
656
+ */
657
+ all() {
658
+ return this.window(this.evaluate());
659
+ }
660
+ /** How many rows (or distinct tuples / groups) match, ignoring `limit`/`offset`. */
661
+ total() {
662
+ return this.evaluate().length;
663
+ }
664
+ /**
665
+ * One offset page — the in-memory `query.paginate(page, size)`. Feed it the `{ page, size }`
666
+ * the runner resolved (clamped and defaulted), never raw request values.
667
+ */
668
+ paginate(page, perPage) {
669
+ const size = Math.max(1, Math.floor(perPage));
670
+ const current = Math.max(1, Math.floor(page));
671
+ const rows = this.evaluate();
672
+ const total = rows.length;
673
+ return {
674
+ data: rows.slice((current - 1) * size, current * size),
675
+ meta: {
676
+ total,
677
+ perPage: size,
678
+ currentPage: current,
679
+ lastPage: Math.max(1, Math.ceil(total / size)),
680
+ firstPage: 1,
681
+ },
682
+ };
683
+ }
684
+ /**
685
+ * Thenable, like a Lucid query: `await qb` resolves to {@link all}. This is what lets helpers
686
+ * that execute a builder by awaiting it (`groupByCountFromRequest`) run over an array.
687
+ */
688
+ // biome-ignore lint/suspicious/noThenProperty: deliberately thenable, mirroring Lucid's query builders.
689
+ then(onfulfilled, onrejected) {
690
+ return new Promise((resolve) => resolve(this.all())).then(onfulfilled, onrejected);
691
+ }
692
+ }
693
+ // ---------------------------------------------------------------------------------------------
694
+ // One-call helpers
695
+ // ---------------------------------------------------------------------------------------------
696
+ /**
697
+ * Filter, search, sort and offset-paginate `rows` in one call: {@link applyFilter} over a fresh
698
+ * builder, then {@link InMemoryQueryBuilder.paginate} with the resolved page. A `distinct` request
699
+ * pages the distinct tuples instead of rows.
700
+ *
701
+ * ```ts
702
+ * const page = filterInMemory(users, rows, parseFilterRequest(ctx.request.qs()), {
703
+ * allowed: ['name', 'age', 'posts.title'],
704
+ * searchable: ['name'],
705
+ * fieldTypes: users.fieldTypes,
706
+ * })
707
+ * // → { data, meta: { total, perPage, currentPage, lastPage, firstPage } }
708
+ * ```
709
+ */
710
+ export function filterInMemory(collection, rows, input, config) {
711
+ const qb = collection.query(rows);
712
+ const { page, size } = applyFilter(qb, input, config);
713
+ return qb.paginate(page, size);
714
+ }
715
+ /**
716
+ * The keyset (cursor) counterpart of {@link filterInMemory}: {@link applyCursor} over a fresh
717
+ * builder (the primary key defaults to the collection's), then `buildCursorPage`. Keyset values
718
+ * are read through the collection, so a virtual field or a to-one relation path works as a cursor
719
+ * sort field.
720
+ */
721
+ export function cursorInMemory(collection, rows, input, config) {
722
+ const qb = collection.query(rows);
723
+ const cursorConfig = {
724
+ ...config,
725
+ primaryKey: config.primaryKey ?? collection.primaryKey,
726
+ };
727
+ const resolved = applyCursor(qb, input, cursorConfig);
728
+ const fetched = qb.all();
729
+ // buildCursorPage reads keyset values as plain properties; stand each row in with an object
730
+ // carrying its keyset values (virtual fields and relation paths resolved), then map back.
731
+ const originals = new Map();
732
+ const keyed = fetched.map((row) => {
733
+ const values = resolved.keyset.map((k) => qb.read(row, k.field));
734
+ const stand = {};
735
+ resolved.keyset.forEach((k, i) => {
736
+ setPath(stand, k.field, values[i]);
737
+ });
738
+ originals.set(stand, row);
739
+ return stand;
740
+ });
741
+ const page = buildCursorPage(keyed, resolved);
742
+ return { ...page, items: page.items.map((stand) => originals.get(stand)) };
743
+ }
744
+ function setPath(target, path, value) {
745
+ const segments = path.split('.');
746
+ let node = target;
747
+ for (const segment of segments.slice(0, -1)) {
748
+ const next = node[segment];
749
+ if (typeof next === 'object' && next !== null)
750
+ node = next;
751
+ else {
752
+ const created = {};
753
+ node[segment] = created;
754
+ node = created;
755
+ }
756
+ }
757
+ node[segments[segments.length - 1]] = value;
758
+ }
759
+ //# sourceMappingURL=in_memory.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"in_memory.js","sourceRoot":"","sources":["../../src/in_memory.ts"],"names":[],"mappings":"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"}
@@ -1,5 +1,5 @@
1
1
  /** Keep in sync with this package's `version` in package.json. */
2
- export declare const VERSION = "0.9.0";
2
+ export declare const VERSION = "0.10.0";
3
3
  export type { LucidModelLike, LucidRelationLike } from './aggregate.js';
4
4
  export { discoverAggregateSources } from './aggregate.js';
5
5
  export type { AggregateFn, AggregatePath } from './aggregate_path.js';
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAAA,kEAAkE;AAClE,eAAO,MAAM,OAAO,UAAU,CAAC;AAE/B,YAAY,EAAE,cAAc,EAAE,iBAAiB,EAAE,MAAM,gBAAgB,CAAC;AACxE,OAAO,EAAE,wBAAwB,EAAE,MAAM,gBAAgB,CAAC;AAC1D,YAAY,EAAE,WAAW,EAAE,aAAa,EAAE,MAAM,qBAAqB,CAAC;AACtE,OAAO,EAAE,kBAAkB,EAAE,MAAM,qBAAqB,CAAC;AACzD,YAAY,EACV,6BAA6B,EAC7B,uBAAuB,EACvB,oBAAoB,GACrB,MAAM,yBAAyB,CAAC;AACjC,OAAO,EAAE,sBAAsB,EAAE,sBAAsB,EAAE,MAAM,yBAAyB,CAAC;AACzF,OAAO,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAC;AAC9C,OAAO,EAAE,eAAe,EAAE,MAAM,wBAAwB,CAAC;AACzD,YAAY,EAAE,UAAU,EAAE,YAAY,EAAE,YAAY,EAAE,cAAc,EAAE,MAAM,aAAa,CAAC;AAC1F,OAAO,EACL,eAAe,EACf,WAAW,EACX,YAAY,EACZ,YAAY,EACZ,mBAAmB,EACnB,aAAa,GACd,MAAM,aAAa,CAAC;AACrB,YAAY,EAAE,wBAAwB,EAAE,iBAAiB,EAAE,MAAM,oBAAoB,CAAC;AACtF,OAAO,EAAE,iBAAiB,EAAE,MAAM,oBAAoB,CAAC;AACvD,YAAY,EAAE,aAAa,EAAE,wBAAwB,EAAE,MAAM,iBAAiB,CAAC;AAC/E,OAAO,EAAE,UAAU,EAAE,SAAS,EAAE,UAAU,EAAE,QAAQ,EAAE,MAAM,iBAAiB,CAAC;AAC9E,OAAO,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAC;AAC9C,YAAY,EAAE,YAAY,EAAE,MAAM,oBAAoB,CAAC;AACvD,OAAO,EACL,oBAAoB,EACpB,kBAAkB,EAClB,gBAAgB,EAChB,iBAAiB,GAClB,MAAM,oBAAoB,CAAC;AAC5B,YAAY,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AACrD,OAAO,EACL,YAAY,EACZ,aAAa,EACb,YAAY,EACZ,mBAAmB,GACpB,MAAM,mBAAmB,CAAC;AAC3B,YAAY,EACV,mBAAmB,EACnB,UAAU,EACV,eAAe,EACf,YAAY,EACZ,cAAc,EACd,eAAe,GAChB,MAAM,kBAAkB,CAAC;AAC1B,OAAO,EACL,YAAY,EACZ,qBAAqB,EACrB,kBAAkB,GACnB,MAAM,kBAAkB,CAAC;AAC1B,YAAY,EAAE,sBAAsB,EAAE,MAAM,uBAAuB,CAAC;AACpE,OAAO,EAAE,UAAU,EAAE,MAAM,uBAAuB,CAAC;AACnD,YAAY,EACV,iBAAiB,EACjB,oBAAoB,EACpB,eAAe,EACf,mBAAmB,EACnB,qBAAqB,EACrB,2BAA2B,GAC5B,MAAM,sBAAsB,CAAC;AAC9B,OAAO,EACL,oBAAoB,EACpB,oBAAoB,EACpB,qBAAqB,EACrB,kBAAkB,GACnB,MAAM,sBAAsB,CAAC;AAC9B,YAAY,EACV,mBAAmB,EACnB,8BAA8B,EAC9B,eAAe,GAChB,MAAM,qBAAqB,CAAC;AAC7B,OAAO,EAAE,uBAAuB,EAAE,MAAM,qBAAqB,CAAC;AAC9D,OAAO,EACL,kBAAkB,EAClB,kBAAkB,EAClB,iBAAiB,EACjB,aAAa,EACb,mBAAmB,EACnB,iBAAiB,EACjB,WAAW,EACX,WAAW,EACX,SAAS,EACT,qBAAqB,EACrB,KAAK,qBAAqB,EAC1B,KAAK,gBAAgB,EACrB,yBAAyB,EACzB,KAAK,oBAAoB,EACzB,KAAK,uBAAuB,GAC7B,MAAM,oBAAoB,CAAC;AAC5B,YAAY,EAAE,qBAAqB,EAAE,MAAM,mBAAmB,CAAC;AAC/D,OAAO,EAAE,oBAAoB,EAAE,MAAM,mBAAmB,CAAC;AACzD,YAAY,EAAE,gBAAgB,EAAE,MAAM,iBAAiB,CAAC;AACxD,OAAO,EAAE,cAAc,EAAE,MAAM,iBAAiB,CAAC;AACjD,YAAY,EACV,YAAY,EACZ,cAAc,EACd,mBAAmB,EACnB,mBAAmB,GACpB,MAAM,gBAAgB,CAAC;AACxB,OAAO,EAAE,gBAAgB,EAAE,gBAAgB,EAAE,MAAM,gBAAgB,CAAC;AACpE,OAAO,EACL,aAAa,EACb,kBAAkB,EAClB,iBAAiB,EACjB,SAAS,EACT,eAAe,GAChB,MAAM,oBAAoB,CAAC;AAC5B,YAAY,EAAE,YAAY,EAAE,kBAAkB,EAAE,MAAM,aAAa,CAAC;AACpE,OAAO,EAAE,WAAW,EAAE,WAAW,EAAE,qBAAqB,EAAE,mBAAmB,EAAE,MAAM,aAAa,CAAC;AACnG,OAAO,EAAE,uBAAuB,EAAE,MAAM,sBAAsB,CAAC;AAC/D,YAAY,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAC;AACtD,OAAO,EAAE,kBAAkB,EAAE,MAAM,oBAAoB,CAAC;AACxD,YAAY,EACV,SAAS,EACT,eAAe,EACf,cAAc,EACd,cAAc,EACd,YAAY,EACZ,WAAW,EACX,oBAAoB,EACpB,mBAAmB,EACnB,mBAAmB,EACnB,eAAe,EACf,WAAW,EACX,QAAQ,EACR,sBAAsB,GACvB,MAAM,YAAY,CAAC;AACpB,OAAO,EACL,wBAAwB,EACxB,gBAAgB,EAChB,iBAAiB,EACjB,oBAAoB,EACpB,qBAAqB,GACtB,MAAM,6BAA6B,CAAC;AACrC,OAAO,EAAE,gBAAgB,EAAE,oBAAoB,EAAE,MAAM,kBAAkB,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"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"}
package/dist/src/index.js CHANGED
@@ -1,5 +1,5 @@
1
1
  /** Keep in sync with this package's `version` in package.json. */
2
- export const VERSION = '0.9.0';
2
+ export const VERSION = '0.10.0';
3
3
  export { discoverAggregateSources } from './aggregate.js';
4
4
  export { parseAggregatePath } from './aggregate_path.js';
5
5
  export { applyCursorFromRequest, applyFilterFromRequest } from './apply_from_request.js';
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAAA,kEAAkE;AAClE,MAAM,CAAC,MAAM,OAAO,GAAG,OAAO,CAAC;AAG/B,OAAO,EAAE,wBAAwB,EAAE,MAAM,gBAAgB,CAAC;AAE1D,OAAO,EAAE,kBAAkB,EAAE,MAAM,qBAAqB,CAAC;AAMzD,OAAO,EAAE,sBAAsB,EAAE,sBAAsB,EAAE,MAAM,yBAAyB,CAAC;AACzF,OAAO,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAC;AAC9C,OAAO,EAAE,eAAe,EAAE,MAAM,wBAAwB,CAAC;AAEzD,OAAO,EACL,eAAe,EACf,WAAW,EACX,YAAY,EACZ,YAAY,EACZ,mBAAmB,EACnB,aAAa,GACd,MAAM,aAAa,CAAC;AAErB,OAAO,EAAE,iBAAiB,EAAE,MAAM,oBAAoB,CAAC;AAEvD,OAAO,EAAE,UAAU,EAAE,SAAS,EAAE,UAAU,EAAE,QAAQ,EAAE,MAAM,iBAAiB,CAAC;AAC9E,OAAO,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAC;AAE9C,OAAO,EACL,oBAAoB,EACpB,kBAAkB,EAClB,gBAAgB,EAChB,iBAAiB,GAClB,MAAM,oBAAoB,CAAC;AAE5B,OAAO,EACL,YAAY,EACZ,aAAa,EACb,YAAY,EACZ,mBAAmB,GACpB,MAAM,mBAAmB,CAAC;AAS3B,OAAO,EACL,YAAY,EACZ,qBAAqB,EACrB,kBAAkB,GACnB,MAAM,kBAAkB,CAAC;AAE1B,OAAO,EAAE,UAAU,EAAE,MAAM,uBAAuB,CAAC;AASnD,OAAO,EACL,oBAAoB,EACpB,oBAAoB,EACpB,qBAAqB,EACrB,kBAAkB,GACnB,MAAM,sBAAsB,CAAC;AAM9B,OAAO,EAAE,uBAAuB,EAAE,MAAM,qBAAqB,CAAC;AAC9D,OAAO,EACL,kBAAkB,EAClB,kBAAkB,EAClB,iBAAiB,EACjB,aAAa,EACb,mBAAmB,EACnB,iBAAiB,EACjB,WAAW,EACX,WAAW,EACX,SAAS,EACT,qBAAqB,EAGrB,yBAAyB,GAG1B,MAAM,oBAAoB,CAAC;AAE5B,OAAO,EAAE,oBAAoB,EAAE,MAAM,mBAAmB,CAAC;AAEzD,OAAO,EAAE,cAAc,EAAE,MAAM,iBAAiB,CAAC;AAOjD,OAAO,EAAE,gBAAgB,EAAE,gBAAgB,EAAE,MAAM,gBAAgB,CAAC;AACpE,OAAO,EACL,aAAa,EACb,kBAAkB,EAClB,iBAAiB,EACjB,SAAS,EACT,eAAe,GAChB,MAAM,oBAAoB,CAAC;AAE5B,OAAO,EAAE,WAAW,EAAE,WAAW,EAAE,qBAAqB,EAAE,mBAAmB,EAAE,MAAM,aAAa,CAAC;AACnG,OAAO,EAAE,uBAAuB,EAAE,MAAM,sBAAsB,CAAC;AAE/D,OAAO,EAAE,kBAAkB,EAAE,MAAM,oBAAoB,CAAC;AAgBxD,OAAO,EACL,wBAAwB,EACxB,gBAAgB,EAChB,iBAAiB,EACjB,oBAAoB,EACpB,qBAAqB,GACtB,MAAM,6BAA6B,CAAC;AACrC,OAAO,EAAE,gBAAgB,EAAE,oBAAoB,EAAE,MAAM,kBAAkB,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAAA,kEAAkE;AAClE,MAAM,CAAC,MAAM,OAAO,GAAG,QAAQ,CAAC;AAGhC,OAAO,EAAE,wBAAwB,EAAE,MAAM,gBAAgB,CAAC;AAE1D,OAAO,EAAE,kBAAkB,EAAE,MAAM,qBAAqB,CAAC;AAMzD,OAAO,EAAE,sBAAsB,EAAE,sBAAsB,EAAE,MAAM,yBAAyB,CAAC;AACzF,OAAO,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAC;AAC9C,OAAO,EAAE,eAAe,EAAE,MAAM,wBAAwB,CAAC;AAEzD,OAAO,EACL,eAAe,EACf,WAAW,EACX,YAAY,EACZ,YAAY,EACZ,mBAAmB,EACnB,aAAa,GACd,MAAM,aAAa,CAAC;AAErB,OAAO,EAAE,iBAAiB,EAAE,MAAM,oBAAoB,CAAC;AAEvD,OAAO,EAAE,UAAU,EAAE,SAAS,EAAE,UAAU,EAAE,QAAQ,EAAE,MAAM,iBAAiB,CAAC;AAC9E,OAAO,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAC;AAE9C,OAAO,EACL,oBAAoB,EACpB,kBAAkB,EAClB,gBAAgB,EAChB,iBAAiB,GAClB,MAAM,oBAAoB,CAAC;AAE5B,OAAO,EACL,YAAY,EACZ,aAAa,EACb,YAAY,EACZ,mBAAmB,GACpB,MAAM,mBAAmB,CAAC;AAS3B,OAAO,EACL,YAAY,EACZ,qBAAqB,EACrB,kBAAkB,GACnB,MAAM,kBAAkB,CAAC;AAE1B,OAAO,EAAE,UAAU,EAAE,MAAM,uBAAuB,CAAC;AASnD,OAAO,EACL,oBAAoB,EACpB,oBAAoB,EACpB,qBAAqB,EACrB,kBAAkB,GACnB,MAAM,sBAAsB,CAAC;AAM9B,OAAO,EAAE,uBAAuB,EAAE,MAAM,qBAAqB,CAAC;AAC9D,OAAO,EACL,kBAAkB,EAClB,kBAAkB,EAClB,iBAAiB,EACjB,aAAa,EACb,mBAAmB,EACnB,iBAAiB,EACjB,WAAW,EACX,WAAW,EACX,SAAS,EACT,qBAAqB,EAGrB,yBAAyB,GAG1B,MAAM,oBAAoB,CAAC;AAE5B,OAAO,EAAE,oBAAoB,EAAE,MAAM,mBAAmB,CAAC;AAEzD,OAAO,EAAE,cAAc,EAAE,MAAM,iBAAiB,CAAC;AAOjD,OAAO,EAAE,gBAAgB,EAAE,gBAAgB,EAAE,MAAM,gBAAgB,CAAC;AACpE,OAAO,EACL,aAAa,EACb,kBAAkB,EAClB,iBAAiB,EACjB,SAAS,EACT,eAAe,GAChB,MAAM,oBAAoB,CAAC;AAE5B,OAAO,EAAE,WAAW,EAAE,WAAW,EAAE,qBAAqB,EAAE,mBAAmB,EAAE,MAAM,aAAa,CAAC;AACnG,OAAO,EAAE,uBAAuB,EAAE,MAAM,sBAAsB,CAAC;AAE/D,OAAO,EAAE,kBAAkB,EAAE,MAAM,oBAAoB,CAAC;AAgBxD,OAAO,EACL,wBAAwB,EACxB,gBAAgB,EAChB,iBAAiB,EACjB,oBAAoB,EACpB,qBAAqB,GACtB,MAAM,6BAA6B,CAAC;AACrC,OAAO,EAAE,gBAAgB,EAAE,oBAAoB,EAAE,MAAM,kBAAkB,CAAC"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@adonis-agora/filter",
3
- "version": "0.9.0",
3
+ "version": "0.10.0",
4
4
  "description": "Server-side query filtering/sorting/pagination for AdonisJS — Spatie-style input, a Lucid adapter, and field allow-listing. Part of the Agora ecosystem.",
5
5
  "license": "MIT",
6
6
  "repository": {
@@ -8,6 +8,21 @@
8
8
  "url": "git+https://github.com/DavideCarvalho/adonis-agora-filter.git",
9
9
  "directory": "packages/core"
10
10
  },
11
+ "homepage": "https://davidecarvalho.github.io/agora/docs/filter",
12
+ "bugs": {
13
+ "url": "https://github.com/DavideCarvalho/adonis-agora-filter/issues"
14
+ },
15
+ "keywords": [
16
+ "adonisjs",
17
+ "adonis",
18
+ "filter",
19
+ "lucid",
20
+ "query",
21
+ "spatie",
22
+ "pagination",
23
+ "agora",
24
+ "tanstack-intent"
25
+ ],
11
26
  "author": "Davi Carvalho <davi@goflip.ai>",
12
27
  "type": "module",
13
28
  "main": "./dist/src/index.js",
@@ -23,6 +38,11 @@
23
38
  "import": "./dist/src/testing.js",
24
39
  "default": "./dist/src/testing.js"
25
40
  },
41
+ "./in-memory": {
42
+ "types": "./dist/src/in_memory.d.ts",
43
+ "import": "./dist/src/in_memory.js",
44
+ "default": "./dist/src/in_memory.js"
45
+ },
26
46
  "./configure": {
27
47
  "types": "./dist/configure.d.ts",
28
48
  "import": "./dist/configure.js",
@@ -57,32 +77,21 @@
57
77
  }
58
78
  },
59
79
  "devDependencies": {
60
- "@adonisjs/assembler": "8.5.0",
61
- "@adonisjs/core": "7.5.0",
80
+ "@adonisjs/assembler": "8.5.2",
81
+ "@adonisjs/core": "7.5.2",
62
82
  "@adonisjs/lucid": "22.4.2",
63
- "@tanstack/intent": "^0.3.7",
83
+ "@tanstack/intent": "0.4.0",
64
84
  "@types/luxon": "3.7.5",
65
- "@types/node": "26.4.0",
85
+ "@types/node": "26.6.2",
66
86
  "@types/pg": "8.23.1",
67
87
  "luxon": "3.7.2",
68
88
  "pg": "8.23.0",
69
89
  "typescript": "7.0.2",
70
- "vitest": "4.1.11"
90
+ "vitest": "5.0.2"
71
91
  },
72
92
  "engines": {
73
93
  "node": ">=20.6.0"
74
94
  },
75
- "keywords": [
76
- "adonisjs",
77
- "adonis",
78
- "filter",
79
- "lucid",
80
- "query",
81
- "spatie",
82
- "pagination",
83
- "agora",
84
- "tanstack-intent"
85
- ],
86
95
  "scripts": {
87
96
  "build": "tsc -p tsconfig.json && pnpm run copy:stubs",
88
97
  "test": "vitest run --passWithNoTests",
@@ -8,8 +8,11 @@ description: >
8
8
  defaultFilters, defaultSort, defaultSize/maxSize), the optional provider
9
9
  macros .applyFilterFromRequest() / .filterPaginate(), wire format parsing
10
10
  (filter[field][op]=value, sort=-createdAt, page/size), and input sourcing from
11
- query string, POST body, or a nested key. Use when building a filtered list
12
- endpoint, wiring a reusable filter policy, or deciding free functions vs macros.
11
+ query string, POST body, or a nested key, and the in-memory adapter
12
+ (@adonis-agora/filter/in-memory: defineCollection, filterInMemory,
13
+ cursorInMemory) for lists that are not a table. Use when building a filtered
14
+ list endpoint, wiring a reusable filter policy, deciding free functions vs
15
+ macros, or filtering a plain array with the same wire format.
13
16
  metadata:
14
17
  type: core
15
18
  library: "@adonis-agora/filter"
@@ -21,6 +24,7 @@ sources:
21
24
  - "DavideCarvalho/adonis-filter:docs/guides/filter-classes.mdx"
22
25
  - "DavideCarvalho/adonis-filter:docs/guides/provider.mdx"
23
26
  - "DavideCarvalho/adonis-filter:docs/guides/operators.mdx"
27
+ - "DavideCarvalho/adonis-filter:docs/guides/in-memory.mdx"
24
28
  ---
25
29
 
26
30
  # Filter basics: parse a request, apply it to a Lucid query
@@ -168,6 +172,34 @@ filtered query.
168
172
 
169
173
  Source: `docs/getting-started.mdx`, `docs/guides/filter-classes.mdx`
170
174
 
175
+ ### 5. Lists that are not a table — the in-memory adapter
176
+
177
+ Rows merged from several sources, static catalogs and remote API pages take the
178
+ same input through `@adonis-agora/filter/in-memory`. `collection.query(rows)` is a
179
+ `QueryBuilderLike`, so every runner entry point (and `defineFilter` specs) drives
180
+ it unchanged; the builder evaluates the calls with Postgres semantics (ILIKE,
181
+ three-valued NULLs, NULLS LAST asc / FIRST desc, EXISTS for to-many paths).
182
+
183
+ ```typescript
184
+ import { defineCollection, filterInMemory } from '@adonis-agora/filter/in-memory'
185
+
186
+ const users = defineCollection<UserRow>({
187
+ fields: { name: 'string', age: 'number', tags: 'string[]', fullName: { type: 'string', get: (u) => `${u.first} ${u.last}` } },
188
+ relations: { posts: { kind: 'one-to-many', target: () => posts, get: (u) => u.posts } },
189
+ })
190
+
191
+ const page = filterInMemory(users, rows, parseFilterRequest(ctx.request.qs()), {
192
+ allowed: ['name', 'age', 'fullName', 'posts.title'],
193
+ fieldTypes: users.fieldTypes,
194
+ })
195
+ // or: const q = users.query(rows); const { page, size } = applyFilterFromRequest(q, spec, ctx); q.paginate(page, size)
196
+ ```
197
+
198
+ Policy `computed`, `fullText` and `vectorSimilarity` are SQL-only and throw
199
+ `InMemoryQueryError` there — declare a virtual field on the collection instead.
200
+
201
+ Source: `docs/guides/in-memory.mdx`
202
+
171
203
  ## Common mistakes
172
204
 
173
205
  ### [CRITICAL] Feeding raw request page/size to paginate()