@inixiative/json-rules 1.1.2 → 1.3.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/README.md +352 -226
- package/dist/index.cjs +3 -1
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +333 -78
- package/dist/index.d.ts +333 -78
- package/dist/index.js +3 -1
- package/dist/index.js.map +1 -1
- package/package.json +14 -4
package/dist/index.d.cts
CHANGED
|
@@ -1,119 +1,374 @@
|
|
|
1
|
-
declare
|
|
2
|
-
equals
|
|
3
|
-
notEquals
|
|
4
|
-
lessThan
|
|
5
|
-
lessThanEquals
|
|
6
|
-
greaterThan
|
|
7
|
-
greaterThanEquals
|
|
8
|
-
contains
|
|
9
|
-
notContains
|
|
10
|
-
in
|
|
11
|
-
notIn
|
|
12
|
-
matches
|
|
13
|
-
notMatches
|
|
14
|
-
between
|
|
15
|
-
notBetween
|
|
16
|
-
isEmpty
|
|
17
|
-
notEmpty
|
|
18
|
-
exists
|
|
19
|
-
notExists
|
|
20
|
-
startsWith
|
|
21
|
-
endsWith
|
|
22
|
-
}
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
1
|
+
declare const Operator: {
|
|
2
|
+
readonly equals: "equals";
|
|
3
|
+
readonly notEquals: "notEquals";
|
|
4
|
+
readonly lessThan: "lessThan";
|
|
5
|
+
readonly lessThanEquals: "lessThanEquals";
|
|
6
|
+
readonly greaterThan: "greaterThan";
|
|
7
|
+
readonly greaterThanEquals: "greaterThanEquals";
|
|
8
|
+
readonly contains: "contains";
|
|
9
|
+
readonly notContains: "notContains";
|
|
10
|
+
readonly in: "in";
|
|
11
|
+
readonly notIn: "notIn";
|
|
12
|
+
readonly matches: "matches";
|
|
13
|
+
readonly notMatches: "notMatches";
|
|
14
|
+
readonly between: "between";
|
|
15
|
+
readonly notBetween: "notBetween";
|
|
16
|
+
readonly isEmpty: "isEmpty";
|
|
17
|
+
readonly notEmpty: "notEmpty";
|
|
18
|
+
readonly exists: "exists";
|
|
19
|
+
readonly notExists: "notExists";
|
|
20
|
+
readonly startsWith: "startsWith";
|
|
21
|
+
readonly endsWith: "endsWith";
|
|
22
|
+
};
|
|
23
|
+
type Operator = (typeof Operator)[keyof typeof Operator];
|
|
24
|
+
declare const ArrayOperator: {
|
|
25
|
+
readonly all: "all";
|
|
26
|
+
readonly any: "any";
|
|
27
|
+
readonly none: "none";
|
|
28
|
+
readonly atLeast: "atLeast";
|
|
29
|
+
readonly atMost: "atMost";
|
|
30
|
+
readonly exactly: "exactly";
|
|
31
|
+
readonly empty: "empty";
|
|
32
|
+
readonly notEmpty: "notEmpty";
|
|
33
|
+
};
|
|
34
|
+
type ArrayOperator = (typeof ArrayOperator)[keyof typeof ArrayOperator];
|
|
35
|
+
declare const DateOperator: {
|
|
36
|
+
readonly before: "before";
|
|
37
|
+
readonly after: "after";
|
|
38
|
+
readonly onOrBefore: "onOrBefore";
|
|
39
|
+
readonly onOrAfter: "onOrAfter";
|
|
40
|
+
readonly between: "between";
|
|
41
|
+
readonly notBetween: "notBetween";
|
|
42
|
+
readonly dayIn: "dayIn";
|
|
43
|
+
readonly dayNotIn: "dayNotIn";
|
|
44
|
+
};
|
|
45
|
+
type DateOperator = (typeof DateOperator)[keyof typeof DateOperator];
|
|
43
46
|
|
|
44
|
-
type
|
|
47
|
+
type OperatorValues = typeof Operator;
|
|
48
|
+
type ArrayOperatorValues = typeof ArrayOperator;
|
|
49
|
+
type DateOperatorValues = typeof DateOperator;
|
|
50
|
+
type RuleScalar = string | number | boolean | null | undefined;
|
|
51
|
+
type AggregateMode = 'sum' | 'avg';
|
|
52
|
+
type RuleValue = RuleScalar | Date | RegExp | RuleValue[] | {
|
|
53
|
+
[key: string]: RuleValue;
|
|
54
|
+
};
|
|
55
|
+
type OrderedRuleValue = string | number | Date;
|
|
56
|
+
type DateInputValue = string | number | Date;
|
|
57
|
+
type DateRuleValue = DateInputValue | [DateInputValue, DateInputValue] | string[];
|
|
58
|
+
type ValueSource<TValue> = {
|
|
59
|
+
value: TValue;
|
|
60
|
+
path?: never;
|
|
61
|
+
} | {
|
|
62
|
+
path: string;
|
|
63
|
+
value?: never;
|
|
64
|
+
};
|
|
65
|
+
type NoValueSource = {
|
|
66
|
+
value?: never;
|
|
67
|
+
path?: never;
|
|
68
|
+
};
|
|
69
|
+
type RuleBase<TOperator extends Operator> = {
|
|
70
|
+
field: string;
|
|
71
|
+
operator: TOperator;
|
|
72
|
+
error?: string;
|
|
73
|
+
};
|
|
74
|
+
type DateRuleBase<TOperator extends DateOperator> = {
|
|
75
|
+
field: string;
|
|
76
|
+
dateOperator: TOperator;
|
|
77
|
+
error?: string;
|
|
78
|
+
};
|
|
79
|
+
type StrictEqualityRule<TValue = RuleValue> = (RuleBase<OperatorValues['equals']> & ValueSource<TValue>) | (RuleBase<OperatorValues['notEquals']> & ValueSource<TValue>);
|
|
80
|
+
type StrictOrderedComparisonRule = (RuleBase<OperatorValues['lessThan']> & ValueSource<OrderedRuleValue>) | (RuleBase<OperatorValues['lessThanEquals']> & ValueSource<OrderedRuleValue>) | (RuleBase<OperatorValues['greaterThan']> & ValueSource<OrderedRuleValue>) | (RuleBase<OperatorValues['greaterThanEquals']> & ValueSource<OrderedRuleValue>);
|
|
81
|
+
type StrictMembershipRule<TValue = RuleValue> = (RuleBase<OperatorValues['in']> & ValueSource<TValue[]>) | (RuleBase<OperatorValues['notIn']> & ValueSource<TValue[]>);
|
|
82
|
+
type StrictContainsRule<TValue = RuleValue> = (RuleBase<OperatorValues['contains']> & ValueSource<TValue>) | (RuleBase<OperatorValues['notContains']> & ValueSource<TValue>);
|
|
83
|
+
type StrictPatternRule = (RuleBase<OperatorValues['matches']> & ValueSource<RegExp | string>) | (RuleBase<OperatorValues['notMatches']> & ValueSource<RegExp | string>);
|
|
84
|
+
type StrictStringBoundaryRule = (RuleBase<OperatorValues['startsWith']> & ValueSource<string>) | (RuleBase<OperatorValues['endsWith']> & ValueSource<string>);
|
|
85
|
+
type StrictRangeRule = (RuleBase<OperatorValues['between']> & ValueSource<[OrderedRuleValue, OrderedRuleValue]>) | (RuleBase<OperatorValues['notBetween']> & ValueSource<[OrderedRuleValue, OrderedRuleValue]>);
|
|
86
|
+
type StrictPresenceRule = (RuleBase<OperatorValues['isEmpty']> & NoValueSource) | (RuleBase<OperatorValues['notEmpty']> & NoValueSource) | (RuleBase<OperatorValues['exists']> & NoValueSource) | (RuleBase<OperatorValues['notExists']> & NoValueSource);
|
|
87
|
+
type StrictRule<TValue = RuleValue> = StrictEqualityRule<TValue> | StrictOrderedComparisonRule | StrictMembershipRule<TValue> | StrictContainsRule<TValue> | StrictPatternRule | StrictStringBoundaryRule | StrictRangeRule | StrictPresenceRule;
|
|
88
|
+
type ArrayRuleBase<TOperator extends ArrayOperator> = {
|
|
89
|
+
field: string;
|
|
90
|
+
arrayOperator: TOperator;
|
|
91
|
+
error?: string;
|
|
92
|
+
};
|
|
93
|
+
type StrictArrayPredicateRule<TRuleValue = RuleValue, TDateValue = DateRuleValue> = (ArrayRuleBase<ArrayOperatorValues['all']> & {
|
|
94
|
+
condition: StrictCondition<TRuleValue, TDateValue>;
|
|
95
|
+
count?: never;
|
|
96
|
+
}) | (ArrayRuleBase<ArrayOperatorValues['any']> & {
|
|
97
|
+
condition: StrictCondition<TRuleValue, TDateValue>;
|
|
98
|
+
count?: never;
|
|
99
|
+
}) | (ArrayRuleBase<ArrayOperatorValues['none']> & {
|
|
100
|
+
condition: StrictCondition<TRuleValue, TDateValue>;
|
|
101
|
+
count?: never;
|
|
102
|
+
});
|
|
103
|
+
type StrictArrayCountRule<TRuleValue = RuleValue, TDateValue = DateRuleValue> = (ArrayRuleBase<ArrayOperatorValues['atLeast']> & {
|
|
104
|
+
condition?: StrictCondition<TRuleValue, TDateValue>;
|
|
105
|
+
count?: number;
|
|
106
|
+
}) | (ArrayRuleBase<ArrayOperatorValues['atMost']> & {
|
|
107
|
+
condition?: StrictCondition<TRuleValue, TDateValue>;
|
|
108
|
+
count?: number;
|
|
109
|
+
}) | (ArrayRuleBase<ArrayOperatorValues['exactly']> & {
|
|
110
|
+
condition?: StrictCondition<TRuleValue, TDateValue>;
|
|
111
|
+
count?: number;
|
|
112
|
+
});
|
|
113
|
+
type StrictArrayPresenceRule = (ArrayRuleBase<ArrayOperatorValues['empty']> & {
|
|
114
|
+
condition?: never;
|
|
115
|
+
count?: never;
|
|
116
|
+
}) | (ArrayRuleBase<ArrayOperatorValues['notEmpty']> & {
|
|
117
|
+
condition?: never;
|
|
118
|
+
count?: never;
|
|
119
|
+
});
|
|
120
|
+
type StrictArrayRule<TRuleValue = RuleValue, TDateValue = DateRuleValue> = StrictArrayPredicateRule<TRuleValue, TDateValue> | StrictArrayCountRule<TRuleValue, TDateValue> | StrictArrayPresenceRule;
|
|
121
|
+
type StrictDateComparisonRule = (DateRuleBase<DateOperatorValues['before']> & ValueSource<DateInputValue>) | (DateRuleBase<DateOperatorValues['after']> & ValueSource<DateInputValue>) | (DateRuleBase<DateOperatorValues['onOrBefore']> & ValueSource<DateInputValue>) | (DateRuleBase<DateOperatorValues['onOrAfter']> & ValueSource<DateInputValue>);
|
|
122
|
+
type StrictDateRangeRule = (DateRuleBase<DateOperatorValues['between']> & ValueSource<[DateInputValue, DateInputValue]>) | (DateRuleBase<DateOperatorValues['notBetween']> & ValueSource<[DateInputValue, DateInputValue]>);
|
|
123
|
+
type StrictDateDayRule = (DateRuleBase<DateOperatorValues['dayIn']> & {
|
|
124
|
+
value: string[];
|
|
125
|
+
path?: never;
|
|
126
|
+
}) | (DateRuleBase<DateOperatorValues['dayNotIn']> & {
|
|
127
|
+
value: string[];
|
|
128
|
+
path?: never;
|
|
129
|
+
});
|
|
130
|
+
type StrictDateRule = StrictDateComparisonRule | StrictDateRangeRule | StrictDateDayRule;
|
|
131
|
+
type AggregateRuleBase = {
|
|
132
|
+
field: string;
|
|
133
|
+
aggregate: {
|
|
134
|
+
mode: AggregateMode;
|
|
135
|
+
field?: string;
|
|
136
|
+
};
|
|
137
|
+
error?: string;
|
|
138
|
+
};
|
|
139
|
+
type AggregateSingleOperator = OperatorValues['equals'] | OperatorValues['notEquals'] | OperatorValues['lessThan'] | OperatorValues['lessThanEquals'] | OperatorValues['greaterThan'] | OperatorValues['greaterThanEquals'];
|
|
140
|
+
type AggregateRangeOperator = OperatorValues['between'] | OperatorValues['notBetween'];
|
|
141
|
+
type StrictAggregateRule = (AggregateRuleBase & {
|
|
142
|
+
operator: AggregateSingleOperator;
|
|
143
|
+
} & ValueSource<number>) | (AggregateRuleBase & {
|
|
144
|
+
operator: AggregateRangeOperator;
|
|
145
|
+
} & ValueSource<[number, number]>);
|
|
146
|
+
type AggregateRule = {
|
|
147
|
+
field: string;
|
|
148
|
+
aggregate: {
|
|
149
|
+
mode: AggregateMode;
|
|
150
|
+
field?: string;
|
|
151
|
+
};
|
|
152
|
+
operator: Operator;
|
|
153
|
+
value?: number | [number, number];
|
|
154
|
+
path?: string;
|
|
155
|
+
error?: string;
|
|
156
|
+
};
|
|
157
|
+
type Rule<TValue = RuleValue> = {
|
|
45
158
|
field: string;
|
|
46
159
|
operator: Operator;
|
|
47
|
-
value?:
|
|
160
|
+
value?: TValue;
|
|
48
161
|
path?: string;
|
|
49
162
|
error?: string;
|
|
50
163
|
};
|
|
51
|
-
type
|
|
52
|
-
type ArrayRule = {
|
|
164
|
+
type ArrayRule<TRuleValue = RuleValue, TDateValue = DateRuleValue> = {
|
|
53
165
|
field: string;
|
|
54
166
|
arrayOperator: ArrayOperator;
|
|
55
|
-
|
|
56
|
-
condition?: Condition;
|
|
167
|
+
condition?: Condition<TRuleValue, TDateValue>;
|
|
57
168
|
count?: number;
|
|
58
169
|
error?: string;
|
|
59
170
|
};
|
|
60
|
-
type DateRule = {
|
|
171
|
+
type DateRule<TValue = DateRuleValue> = {
|
|
61
172
|
field: string;
|
|
62
173
|
dateOperator: DateOperator;
|
|
63
|
-
value?:
|
|
174
|
+
value?: TValue;
|
|
64
175
|
path?: string;
|
|
65
176
|
error?: string;
|
|
66
177
|
};
|
|
67
|
-
type All = {
|
|
68
|
-
all: Condition[];
|
|
178
|
+
type All<TRuleValue = RuleValue, TDateValue = DateRuleValue> = {
|
|
179
|
+
all: Condition<TRuleValue, TDateValue>[];
|
|
69
180
|
error?: string;
|
|
70
181
|
};
|
|
71
|
-
type Any = {
|
|
72
|
-
any: Condition[];
|
|
182
|
+
type Any<TRuleValue = RuleValue, TDateValue = DateRuleValue> = {
|
|
183
|
+
any: Condition<TRuleValue, TDateValue>[];
|
|
73
184
|
error?: string;
|
|
74
185
|
};
|
|
75
|
-
type IfThenElse = {
|
|
76
|
-
if: Condition
|
|
77
|
-
then: Condition
|
|
78
|
-
else?: Condition
|
|
186
|
+
type IfThenElse<TRuleValue = RuleValue, TDateValue = DateRuleValue> = {
|
|
187
|
+
if: Condition<TRuleValue, TDateValue>;
|
|
188
|
+
then: Condition<TRuleValue, TDateValue>;
|
|
189
|
+
else?: Condition<TRuleValue, TDateValue>;
|
|
79
190
|
error?: string;
|
|
80
191
|
};
|
|
81
|
-
type Condition = Rule | ArrayRule | DateRule | All | Any | IfThenElse | boolean;
|
|
192
|
+
type Condition<TRuleValue = RuleValue, TDateValue = DateRuleValue> = Rule<TRuleValue> | AggregateRule | ArrayRule<TRuleValue, TDateValue> | DateRule<TDateValue> | All<TRuleValue, TDateValue> | Any<TRuleValue, TDateValue> | IfThenElse<TRuleValue, TDateValue> | boolean;
|
|
193
|
+
type StrictAll<TRuleValue = RuleValue, TDateValue = DateRuleValue> = {
|
|
194
|
+
all: StrictCondition<TRuleValue, TDateValue>[];
|
|
195
|
+
error?: string;
|
|
196
|
+
};
|
|
197
|
+
type StrictAny<TRuleValue = RuleValue, TDateValue = DateRuleValue> = {
|
|
198
|
+
any: StrictCondition<TRuleValue, TDateValue>[];
|
|
199
|
+
error?: string;
|
|
200
|
+
};
|
|
201
|
+
type StrictIfThenElse<TRuleValue = RuleValue, TDateValue = DateRuleValue> = {
|
|
202
|
+
if: StrictCondition<TRuleValue, TDateValue>;
|
|
203
|
+
then: StrictCondition<TRuleValue, TDateValue>;
|
|
204
|
+
else?: StrictCondition<TRuleValue, TDateValue>;
|
|
205
|
+
error?: string;
|
|
206
|
+
};
|
|
207
|
+
type StrictCondition<TRuleValue = RuleValue, TDateValue = DateRuleValue> = StrictRule<TRuleValue> | StrictAggregateRule | StrictArrayRule<TRuleValue, TDateValue> | StrictDateRule | StrictAll<TRuleValue, TDateValue> | StrictAny<TRuleValue, TDateValue> | StrictIfThenElse<TRuleValue, TDateValue> | boolean;
|
|
82
208
|
|
|
83
|
-
declare const check: (conditions: Condition, data:
|
|
209
|
+
declare const check: <TData extends Record<string, unknown>>(conditions: Condition, data: TData, context?: TData) => boolean | string;
|
|
210
|
+
|
|
211
|
+
type PrismaWhere = Record<string, unknown>;
|
|
212
|
+
type FieldMapEntry = {
|
|
213
|
+
kind: 'scalar' | 'object' | 'enum';
|
|
214
|
+
type: string;
|
|
215
|
+
isList?: boolean;
|
|
216
|
+
fromFields?: string[];
|
|
217
|
+
toFields?: string[];
|
|
218
|
+
relationName?: string;
|
|
219
|
+
};
|
|
220
|
+
interface FieldMap {
|
|
221
|
+
[modelName: string]: {
|
|
222
|
+
dbName?: string | null;
|
|
223
|
+
fields: {
|
|
224
|
+
[fieldName: string]: FieldMapEntry;
|
|
225
|
+
};
|
|
226
|
+
};
|
|
227
|
+
}
|
|
228
|
+
type StepRef = {
|
|
229
|
+
__step: number;
|
|
230
|
+
};
|
|
231
|
+
type GroupByStep = {
|
|
232
|
+
operation: 'groupBy';
|
|
233
|
+
model: string;
|
|
234
|
+
args: {
|
|
235
|
+
by: string[];
|
|
236
|
+
where: Record<string, unknown>;
|
|
237
|
+
having: Record<string, unknown>;
|
|
238
|
+
};
|
|
239
|
+
extract: string;
|
|
240
|
+
};
|
|
241
|
+
type WhereStep = {
|
|
242
|
+
operation: 'where';
|
|
243
|
+
where: Record<string, unknown>;
|
|
244
|
+
};
|
|
245
|
+
type PrismaStep = GroupByStep | WhereStep;
|
|
246
|
+
type ToPrismaResult = {
|
|
247
|
+
steps: PrismaStep[];
|
|
248
|
+
};
|
|
249
|
+
type BuildOptions = {
|
|
250
|
+
map?: FieldMap;
|
|
251
|
+
model?: string;
|
|
252
|
+
context?: Record<string, unknown>;
|
|
253
|
+
};
|
|
254
|
+
|
|
255
|
+
/**
|
|
256
|
+
* Execute a Prisma query plan produced by toPrisma().
|
|
257
|
+
*
|
|
258
|
+
* The plan is a flat list of steps where all but the last are `groupBy` steps
|
|
259
|
+
* that feed results (via { __step: N } sentinels) into subsequent steps.
|
|
260
|
+
* The final step is always a `where` step whose resolved WHERE clause is returned.
|
|
261
|
+
*
|
|
262
|
+
* @param result - Result from toPrisma()
|
|
263
|
+
* @param prismaDelegate - Map of camelCase model name → Prisma delegate
|
|
264
|
+
* e.g. { post: prisma.post, user: prisma.user }
|
|
265
|
+
* @returns The resolved WHERE clause (ready for findMany/count/etc.)
|
|
266
|
+
*
|
|
267
|
+
* @example
|
|
268
|
+
* const plan = toPrisma(condition, { map, model: 'User' });
|
|
269
|
+
* const where = await executePrismaQueryPlan(plan, { post: prisma.post });
|
|
270
|
+
* await prisma.user.findMany({ where });
|
|
271
|
+
*/
|
|
272
|
+
declare const executePrismaQueryPlan: (result: ToPrismaResult, prismaDelegate: Record<string, Record<string, (...args: unknown[]) => unknown>>) => Promise<Record<string, unknown>>;
|
|
273
|
+
|
|
274
|
+
/**
|
|
275
|
+
* Convert a json-rules Condition to a Prisma query plan.
|
|
276
|
+
*
|
|
277
|
+
* Returns a `ToPrismaResult` with:
|
|
278
|
+
* - `where` – the Prisma WHERE clause
|
|
279
|
+
* - `steps` – optional array of groupBy steps for count-based relation filters
|
|
280
|
+
* (only present when `atLeast`/`atMost`/`exactly` operators are used with a map)
|
|
281
|
+
*
|
|
282
|
+
* When `steps` is present, pass the result to `executePrismaQueryPlan` to
|
|
283
|
+
* resolve step refs before using `where` in a Prisma query.
|
|
284
|
+
*
|
|
285
|
+
* @param condition - The rule condition to convert
|
|
286
|
+
* @param options - Optional map, model, and context
|
|
287
|
+
*
|
|
288
|
+
* @example
|
|
289
|
+
* ```typescript
|
|
290
|
+
* // Simple scalar
|
|
291
|
+
* toPrisma({ field: 'status', operator: Operator.equals, value: 'active' })
|
|
292
|
+
* // → { where: { status: { equals: 'active' } } }
|
|
293
|
+
*
|
|
294
|
+
* // JSON field detection (map required)
|
|
295
|
+
* toPrisma({ field: 'metadata.theme', operator: Operator.equals, value: 'dark' }, { map, model: 'User' })
|
|
296
|
+
* // → { where: { metadata: { path: ['theme'], equals: 'dark' } } }
|
|
297
|
+
*
|
|
298
|
+
* // Context path ref
|
|
299
|
+
* toPrisma({ field: 'userId', operator: Operator.equals, path: 'currentUser.id' }, { context: { currentUser: { id: '123' } } })
|
|
300
|
+
* // → { where: { userId: { equals: '123' } } }
|
|
301
|
+
*
|
|
302
|
+
* // Multi-step (map required)
|
|
303
|
+
* const plan = toPrisma({ field: 'posts', arrayOperator: 'atLeast', count: 3, condition: {...} }, { map, model: 'User' });
|
|
304
|
+
* const where = await executePrismaQueryPlan(plan, { post: prisma.post });
|
|
305
|
+
* await prisma.user.findMany({ where });
|
|
306
|
+
* ```
|
|
307
|
+
*/
|
|
308
|
+
declare const toPrisma: (condition: Condition, options?: BuildOptions) => ToPrismaResult;
|
|
84
309
|
|
|
85
310
|
type SqlResult = {
|
|
86
311
|
sql: string;
|
|
87
312
|
params: unknown[];
|
|
313
|
+
joins: string[];
|
|
88
314
|
};
|
|
89
315
|
|
|
316
|
+
type SqlBuildOptions = {
|
|
317
|
+
map?: FieldMap;
|
|
318
|
+
model?: string;
|
|
319
|
+
alias?: string;
|
|
320
|
+
context?: Record<string, unknown>;
|
|
321
|
+
};
|
|
90
322
|
/**
|
|
91
323
|
* Convert a json-rules Condition to a PostgreSQL WHERE clause.
|
|
92
324
|
*
|
|
93
325
|
* @param condition - The rule condition to convert
|
|
94
|
-
* @
|
|
326
|
+
* @param options - Optional map/model/alias for JOIN generation; context for path refs
|
|
327
|
+
* @returns Object with `sql`, `params`, and `joins` (LEFT JOIN clauses)
|
|
95
328
|
*
|
|
96
329
|
* @example
|
|
97
330
|
* ```typescript
|
|
98
|
-
*
|
|
99
|
-
*
|
|
100
|
-
* const rule = { field: 'status', operator: Operator.equals, value: 'active' };
|
|
101
|
-
* const { sql, params } = toSql(rule);
|
|
331
|
+
* // Simple field
|
|
332
|
+
* const { sql, params } = toSql({ field: 'status', operator: Operator.equals, value: 'active' });
|
|
102
333
|
* // sql: '"status" = $1'
|
|
103
|
-
* // params: ['active']
|
|
104
334
|
*
|
|
105
|
-
* //
|
|
106
|
-
* const
|
|
107
|
-
*
|
|
108
|
-
*
|
|
109
|
-
*
|
|
110
|
-
*
|
|
111
|
-
*
|
|
112
|
-
*
|
|
113
|
-
* //
|
|
114
|
-
*
|
|
335
|
+
* // Relation traversal with JOINs (map required)
|
|
336
|
+
* const { sql, params, joins } = toSql(
|
|
337
|
+
* { field: 'author.email', operator: Operator.equals, value: 'a@b.com' },
|
|
338
|
+
* { map, model: 'Post', alias: 't0' }
|
|
339
|
+
* );
|
|
340
|
+
* // sql: '"t1"."email" = $1'
|
|
341
|
+
* // joins: ['LEFT JOIN "User" AS "t1" ON "t1"."id" = "t0"."authorId"']
|
|
342
|
+
*
|
|
343
|
+
* // Same-record field comparison ($.field)
|
|
344
|
+
* const { sql: sql2 } = toSql({ field: 'endDate', operator: Operator.greaterThan, path: '$.startDate' });
|
|
345
|
+
* // sql2: '"endDate" > "startDate"'
|
|
346
|
+
*
|
|
347
|
+
* // External context ref
|
|
348
|
+
* const { sql: sql3 } = toSql(
|
|
349
|
+
* { field: 'userId', operator: Operator.equals, path: 'currentUser.id' },
|
|
350
|
+
* { context: { currentUser: { id: '123' } } }
|
|
351
|
+
* );
|
|
352
|
+
* // sql3: '"userId" = $1' params: ['123']
|
|
115
353
|
* ```
|
|
116
354
|
*/
|
|
117
|
-
declare const toSql: (condition: Condition) => SqlResult;
|
|
355
|
+
declare const toSql: (condition: Condition, options?: SqlBuildOptions) => SqlResult;
|
|
356
|
+
|
|
357
|
+
type RuleValidationTarget = 'check' | 'toPrisma' | 'toSql';
|
|
358
|
+
type ValidationIssue = {
|
|
359
|
+
path: string;
|
|
360
|
+
message: string;
|
|
361
|
+
code: string;
|
|
362
|
+
};
|
|
363
|
+
type ValidationResult = {
|
|
364
|
+
ok: boolean;
|
|
365
|
+
errors: ValidationIssue[];
|
|
366
|
+
};
|
|
367
|
+
declare const validateRule: (condition: unknown, options?: {
|
|
368
|
+
target?: RuleValidationTarget;
|
|
369
|
+
}) => ValidationResult;
|
|
370
|
+
declare const assertValidRule: (condition: unknown, options?: {
|
|
371
|
+
target?: RuleValidationTarget;
|
|
372
|
+
}) => asserts condition is Condition;
|
|
118
373
|
|
|
119
|
-
export { type All, type Any, ArrayOperator, type ArrayRule, type
|
|
374
|
+
export { type AggregateMode, type AggregateRule, type All, type Any, ArrayOperator, type ArrayRule, type BuildOptions, type Condition, type DateInputValue, DateOperator, type DateRule, type DateRuleValue, type FieldMap, type FieldMapEntry, type GroupByStep, type IfThenElse, Operator, type OrderedRuleValue, type PrismaStep, type PrismaWhere, type Rule, type RuleScalar, type RuleValidationTarget, type RuleValue, type SqlResult, type StepRef, type StrictAggregateRule, type StrictAll, type StrictAny, type StrictArrayCountRule, type StrictArrayPredicateRule, type StrictArrayPresenceRule, type StrictArrayRule, type StrictCondition, type StrictContainsRule, type StrictDateComparisonRule, type StrictDateDayRule, type StrictDateRangeRule, type StrictDateRule, type StrictEqualityRule, type StrictIfThenElse, type StrictMembershipRule, type StrictOrderedComparisonRule, type StrictPatternRule, type StrictPresenceRule, type StrictRangeRule, type StrictRule, type StrictStringBoundaryRule, type ToPrismaResult, type ValidationIssue, type ValidationResult, type WhereStep, assertValidRule, check, executePrismaQueryPlan, toPrisma, toSql, validateRule };
|