@naylence/advanced-security 0.3.15 → 0.4.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/dist/browser/index.cjs +2673 -3
- package/dist/browser/index.mjs +2684 -14
- package/dist/cjs/advanced-security-isomorphic.js +4 -0
- package/dist/cjs/advanced-security-isomorphic.js.map +1 -1
- package/dist/cjs/naylence/fame/expr/ast.js +135 -0
- package/dist/cjs/naylence/fame/expr/ast.js.map +1 -0
- package/dist/cjs/naylence/fame/expr/builtins.js +477 -0
- package/dist/cjs/naylence/fame/expr/builtins.js.map +1 -0
- package/dist/cjs/naylence/fame/expr/errors.js +88 -0
- package/dist/cjs/naylence/fame/expr/errors.js.map +1 -0
- package/dist/cjs/naylence/fame/expr/evaluator.js +385 -0
- package/dist/cjs/naylence/fame/expr/evaluator.js.map +1 -0
- package/dist/cjs/naylence/fame/expr/index.js +21 -0
- package/dist/cjs/naylence/fame/expr/index.js.map +1 -0
- package/dist/cjs/naylence/fame/expr/limits.js +80 -0
- package/dist/cjs/naylence/fame/expr/limits.js.map +1 -0
- package/dist/cjs/naylence/fame/expr/parser.js +429 -0
- package/dist/cjs/naylence/fame/expr/parser.js.map +1 -0
- package/dist/cjs/naylence/fame/expr/tokenizer.js +336 -0
- package/dist/cjs/naylence/fame/expr/tokenizer.js.map +1 -0
- package/dist/cjs/naylence/fame/factory-manifest.js +2 -0
- package/dist/cjs/naylence/fame/factory-manifest.js.map +1 -1
- package/dist/cjs/naylence/fame/security/auth/index.js +7 -0
- package/dist/cjs/naylence/fame/security/auth/index.js.map +1 -0
- package/dist/cjs/naylence/fame/security/auth/policy/advanced-authorization-policy-factory.js +70 -0
- package/dist/cjs/naylence/fame/security/auth/policy/advanced-authorization-policy-factory.js.map +1 -0
- package/dist/cjs/naylence/fame/security/auth/policy/advanced-authorization-policy.js +562 -0
- package/dist/cjs/naylence/fame/security/auth/policy/advanced-authorization-policy.js.map +1 -0
- package/dist/cjs/naylence/fame/security/auth/policy/expr-builtins.js +129 -0
- package/dist/cjs/naylence/fame/security/auth/policy/expr-builtins.js.map +1 -0
- package/dist/cjs/naylence/fame/security/auth/policy/index.js +15 -0
- package/dist/cjs/naylence/fame/security/auth/policy/index.js.map +1 -0
- package/dist/cjs/naylence/fame/security/index.js +2 -0
- package/dist/cjs/naylence/fame/security/index.js.map +1 -1
- package/dist/cjs/naylence/fame/security/register-advanced-security-factories.js +2 -0
- package/dist/cjs/naylence/fame/security/register-advanced-security-factories.js.map +1 -1
- package/dist/cjs/naylence/fame/security/strict-overlay-security-profile.js +64 -0
- package/dist/cjs/naylence/fame/security/strict-overlay-security-profile.js.map +1 -0
- package/dist/cjs/plugin.js +2 -0
- package/dist/cjs/plugin.js.map +1 -1
- package/dist/cjs/version.js +2 -2
- package/dist/cjs/version.js.map +1 -1
- package/dist/esm/advanced-security-isomorphic.js +4 -0
- package/dist/esm/advanced-security-isomorphic.js.map +1 -1
- package/dist/esm/naylence/fame/expr/ast.js +135 -0
- package/dist/esm/naylence/fame/expr/ast.js.map +1 -0
- package/dist/esm/naylence/fame/expr/builtins.js +477 -0
- package/dist/esm/naylence/fame/expr/builtins.js.map +1 -0
- package/dist/esm/naylence/fame/expr/errors.js +88 -0
- package/dist/esm/naylence/fame/expr/errors.js.map +1 -0
- package/dist/esm/naylence/fame/expr/evaluator.js +385 -0
- package/dist/esm/naylence/fame/expr/evaluator.js.map +1 -0
- package/dist/esm/naylence/fame/expr/index.js +21 -0
- package/dist/esm/naylence/fame/expr/index.js.map +1 -0
- package/dist/esm/naylence/fame/expr/limits.js +80 -0
- package/dist/esm/naylence/fame/expr/limits.js.map +1 -0
- package/dist/esm/naylence/fame/expr/parser.js +429 -0
- package/dist/esm/naylence/fame/expr/parser.js.map +1 -0
- package/dist/esm/naylence/fame/expr/tokenizer.js +336 -0
- package/dist/esm/naylence/fame/expr/tokenizer.js.map +1 -0
- package/dist/esm/naylence/fame/factory-manifest.js +2 -0
- package/dist/esm/naylence/fame/factory-manifest.js.map +1 -1
- package/dist/esm/naylence/fame/security/auth/index.js +7 -0
- package/dist/esm/naylence/fame/security/auth/index.js.map +1 -0
- package/dist/esm/naylence/fame/security/auth/policy/advanced-authorization-policy-factory.js +70 -0
- package/dist/esm/naylence/fame/security/auth/policy/advanced-authorization-policy-factory.js.map +1 -0
- package/dist/esm/naylence/fame/security/auth/policy/advanced-authorization-policy.js +562 -0
- package/dist/esm/naylence/fame/security/auth/policy/advanced-authorization-policy.js.map +1 -0
- package/dist/esm/naylence/fame/security/auth/policy/expr-builtins.js +129 -0
- package/dist/esm/naylence/fame/security/auth/policy/expr-builtins.js.map +1 -0
- package/dist/esm/naylence/fame/security/auth/policy/index.js +15 -0
- package/dist/esm/naylence/fame/security/auth/policy/index.js.map +1 -0
- package/dist/esm/naylence/fame/security/index.js +2 -0
- package/dist/esm/naylence/fame/security/index.js.map +1 -1
- package/dist/esm/naylence/fame/security/register-advanced-security-factories.js +2 -0
- package/dist/esm/naylence/fame/security/register-advanced-security-factories.js.map +1 -1
- package/dist/esm/naylence/fame/security/strict-overlay-security-profile.js +64 -0
- package/dist/esm/naylence/fame/security/strict-overlay-security-profile.js.map +1 -0
- package/dist/esm/plugin.js +2 -0
- package/dist/esm/plugin.js.map +1 -1
- package/dist/esm/version.js +2 -2
- package/dist/esm/version.js.map +1 -1
- package/dist/node/index.cjs +2795 -6
- package/dist/node/index.mjs +2770 -15
- package/dist/node/node.cjs +2819 -3
- package/dist/node/node.mjs +2796 -15
- package/dist/types/advanced-security-isomorphic.d.ts +2 -0
- package/dist/types/advanced-security-isomorphic.d.ts.map +1 -1
- package/dist/types/naylence/fame/expr/ast.d.ts +85 -0
- package/dist/types/naylence/fame/expr/ast.d.ts.map +1 -0
- package/dist/types/naylence/fame/expr/builtins.d.ts +79 -0
- package/dist/types/naylence/fame/expr/builtins.d.ts.map +1 -0
- package/dist/types/naylence/fame/expr/errors.d.ts +61 -0
- package/dist/types/naylence/fame/expr/errors.d.ts.map +1 -0
- package/dist/types/naylence/fame/expr/evaluator.d.ts +90 -0
- package/dist/types/naylence/fame/expr/evaluator.d.ts.map +1 -0
- package/dist/types/naylence/fame/expr/index.d.ts +16 -0
- package/dist/types/naylence/fame/expr/index.d.ts.map +1 -0
- package/dist/types/naylence/fame/expr/limits.d.ts +65 -0
- package/dist/types/naylence/fame/expr/limits.d.ts.map +1 -0
- package/dist/types/naylence/fame/expr/parser.d.ts +102 -0
- package/dist/types/naylence/fame/expr/parser.d.ts.map +1 -0
- package/dist/types/naylence/fame/expr/tokenizer.d.ts +51 -0
- package/dist/types/naylence/fame/expr/tokenizer.d.ts.map +1 -0
- package/dist/types/naylence/fame/factory-manifest.d.ts +1 -1
- package/dist/types/naylence/fame/factory-manifest.d.ts.map +1 -1
- package/dist/types/naylence/fame/security/auth/index.d.ts +7 -0
- package/dist/types/naylence/fame/security/auth/index.d.ts.map +1 -0
- package/dist/types/naylence/fame/security/auth/policy/advanced-authorization-policy-factory.d.ts +47 -0
- package/dist/types/naylence/fame/security/auth/policy/advanced-authorization-policy-factory.d.ts.map +1 -0
- package/dist/types/naylence/fame/security/auth/policy/advanced-authorization-policy.d.ts +73 -0
- package/dist/types/naylence/fame/security/auth/policy/advanced-authorization-policy.d.ts.map +1 -0
- package/dist/types/naylence/fame/security/auth/policy/expr-builtins.d.ts +14 -0
- package/dist/types/naylence/fame/security/auth/policy/expr-builtins.d.ts.map +1 -0
- package/dist/types/naylence/fame/security/auth/policy/index.d.ts +12 -0
- package/dist/types/naylence/fame/security/auth/policy/index.d.ts.map +1 -0
- package/dist/types/naylence/fame/security/index.d.ts +2 -0
- package/dist/types/naylence/fame/security/index.d.ts.map +1 -1
- package/dist/types/naylence/fame/security/register-advanced-security-factories.d.ts +1 -0
- package/dist/types/naylence/fame/security/register-advanced-security-factories.d.ts.map +1 -1
- package/dist/types/naylence/fame/security/strict-overlay-security-profile.d.ts +11 -0
- package/dist/types/naylence/fame/security/strict-overlay-security-profile.d.ts.map +1 -0
- package/dist/types/plugin.d.ts.map +1 -1
- package/dist/types/version.d.ts +1 -1
- package/dist/types/version.d.ts.map +1 -1
- package/package.json +3 -3
|
@@ -0,0 +1,385 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Expression evaluator.
|
|
3
|
+
*
|
|
4
|
+
* Evaluates an AST against a set of variable bindings and returns a value.
|
|
5
|
+
*
|
|
6
|
+
* Null handling semantics:
|
|
7
|
+
* - `undefined` values are normalized to `null` throughout evaluation.
|
|
8
|
+
* - Missing identifiers evaluate to `null`.
|
|
9
|
+
* - Member access on `null` or non-object returns `null`.
|
|
10
|
+
* - Missing properties return `null` (including properties set to `undefined`).
|
|
11
|
+
*/
|
|
12
|
+
import { BUILTIN_FUNCTIONS, callBuiltin, getTypeName, normalizeJsValue, } from "./builtins.js";
|
|
13
|
+
import { EvaluationError, TypeError } from "./errors.js";
|
|
14
|
+
import { DEFAULT_EXPRESSION_LIMITS, } from "./limits.js";
|
|
15
|
+
/**
|
|
16
|
+
* Evaluates an AST node and returns the result.
|
|
17
|
+
*/
|
|
18
|
+
export class Evaluator {
|
|
19
|
+
constructor(context) {
|
|
20
|
+
this.memberAccessDepth = 0;
|
|
21
|
+
this.context = context;
|
|
22
|
+
this.limits = context.limits ?? DEFAULT_EXPRESSION_LIMITS;
|
|
23
|
+
this.source = context.source ?? "";
|
|
24
|
+
this.functions = context.functions ?? BUILTIN_FUNCTIONS;
|
|
25
|
+
}
|
|
26
|
+
/**
|
|
27
|
+
* Evaluates an AST node and returns the value.
|
|
28
|
+
*/
|
|
29
|
+
evaluate(node) {
|
|
30
|
+
switch (node.type) {
|
|
31
|
+
case "StringLiteral":
|
|
32
|
+
return node.value;
|
|
33
|
+
case "NumberLiteral":
|
|
34
|
+
return node.value;
|
|
35
|
+
case "BooleanLiteral":
|
|
36
|
+
return node.value;
|
|
37
|
+
case "NullLiteral":
|
|
38
|
+
return null;
|
|
39
|
+
case "ArrayLiteral":
|
|
40
|
+
return node.elements.map((e) => this.evaluate(e));
|
|
41
|
+
case "Identifier":
|
|
42
|
+
return this.evaluateIdentifier(node.name, node.position);
|
|
43
|
+
case "MemberAccess":
|
|
44
|
+
return this.evaluateMemberAccess(node);
|
|
45
|
+
case "IndexAccess":
|
|
46
|
+
return this.evaluateIndexAccess(node);
|
|
47
|
+
case "FunctionCall":
|
|
48
|
+
return this.evaluateFunctionCall(node);
|
|
49
|
+
case "UnaryOp":
|
|
50
|
+
return this.evaluateUnaryOp(node.operator, node.operand, node.position);
|
|
51
|
+
case "BinaryOp":
|
|
52
|
+
return this.evaluateBinaryOp(node.operator, node.left, node.right, node.position);
|
|
53
|
+
case "TernaryOp":
|
|
54
|
+
return this.evaluateTernaryOp(node.condition, node.consequent, node.alternate, node.position);
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
/**
|
|
58
|
+
* Evaluates as boolean with strict type checking.
|
|
59
|
+
*/
|
|
60
|
+
evaluateAsBoolean(node) {
|
|
61
|
+
const value = this.evaluate(node);
|
|
62
|
+
if (typeof value !== "boolean") {
|
|
63
|
+
throw new TypeError("boolean", getTypeName(value), node.position, this.source);
|
|
64
|
+
}
|
|
65
|
+
return value;
|
|
66
|
+
}
|
|
67
|
+
evaluateIdentifier(name, _position) {
|
|
68
|
+
// Check if it's a top-level binding
|
|
69
|
+
if (name in this.context.bindings) {
|
|
70
|
+
// Normalize the value to ensure undefined becomes null
|
|
71
|
+
return normalizeJsValue(this.context.bindings[name]);
|
|
72
|
+
}
|
|
73
|
+
// Unknown identifier evaluates to null (missing field)
|
|
74
|
+
return null;
|
|
75
|
+
}
|
|
76
|
+
evaluateMemberAccess(node) {
|
|
77
|
+
// Check member access depth
|
|
78
|
+
this.memberAccessDepth++;
|
|
79
|
+
if (this.memberAccessDepth > this.limits.maxMemberAccessDepth) {
|
|
80
|
+
throw new EvaluationError(`Member access depth ${this.memberAccessDepth} exceeds limit of ${this.limits.maxMemberAccessDepth}`, node.position, this.source);
|
|
81
|
+
}
|
|
82
|
+
try {
|
|
83
|
+
const obj = this.evaluate(node.object);
|
|
84
|
+
// Null-safe member access: null.foo -> null
|
|
85
|
+
if (obj === null) {
|
|
86
|
+
return null;
|
|
87
|
+
}
|
|
88
|
+
// Must be an object (not primitive, not array)
|
|
89
|
+
if (typeof obj !== "object" || Array.isArray(obj)) {
|
|
90
|
+
// Type mismatch during access returns null (not error)
|
|
91
|
+
return null;
|
|
92
|
+
}
|
|
93
|
+
const record = obj;
|
|
94
|
+
if (node.property in record) {
|
|
95
|
+
// Normalize the value to ensure undefined becomes null
|
|
96
|
+
return normalizeJsValue(record[node.property]);
|
|
97
|
+
}
|
|
98
|
+
// Missing property evaluates to null
|
|
99
|
+
return null;
|
|
100
|
+
}
|
|
101
|
+
finally {
|
|
102
|
+
this.memberAccessDepth--;
|
|
103
|
+
}
|
|
104
|
+
}
|
|
105
|
+
evaluateIndexAccess(node) {
|
|
106
|
+
const obj = this.evaluate(node.object);
|
|
107
|
+
const index = this.evaluate(node.index);
|
|
108
|
+
// Null-safe index access: null[0] -> null
|
|
109
|
+
if (obj === null) {
|
|
110
|
+
return null;
|
|
111
|
+
}
|
|
112
|
+
// Array access with numeric index
|
|
113
|
+
if (Array.isArray(obj)) {
|
|
114
|
+
if (typeof index !== "number") {
|
|
115
|
+
throw new TypeError("number", getTypeName(index), node.position, this.source);
|
|
116
|
+
}
|
|
117
|
+
const intIndex = Math.floor(index);
|
|
118
|
+
if (intIndex < 0 || intIndex >= obj.length) {
|
|
119
|
+
// Out of bounds evaluates to null
|
|
120
|
+
return null;
|
|
121
|
+
}
|
|
122
|
+
// Normalize array element to ensure undefined becomes null
|
|
123
|
+
return normalizeJsValue(obj[intIndex]);
|
|
124
|
+
}
|
|
125
|
+
// Object access with string key
|
|
126
|
+
if (typeof obj === "object") {
|
|
127
|
+
if (typeof index !== "string") {
|
|
128
|
+
throw new TypeError("string", getTypeName(index), node.position, this.source);
|
|
129
|
+
}
|
|
130
|
+
const record = obj;
|
|
131
|
+
if (index in record) {
|
|
132
|
+
// Normalize the value to ensure undefined becomes null
|
|
133
|
+
return normalizeJsValue(record[index]);
|
|
134
|
+
}
|
|
135
|
+
// Missing key evaluates to null
|
|
136
|
+
return null;
|
|
137
|
+
}
|
|
138
|
+
// Type mismatch during access returns null
|
|
139
|
+
return null;
|
|
140
|
+
}
|
|
141
|
+
evaluateFunctionCall(node) {
|
|
142
|
+
// Evaluate arguments
|
|
143
|
+
const args = node.args.map((arg) => this.evaluate(arg));
|
|
144
|
+
const builtinContext = {
|
|
145
|
+
limits: this.limits,
|
|
146
|
+
position: node.position,
|
|
147
|
+
source: this.source,
|
|
148
|
+
};
|
|
149
|
+
return callBuiltin(node.name, args, builtinContext, this.functions);
|
|
150
|
+
}
|
|
151
|
+
evaluateUnaryOp(operator, operand, position) {
|
|
152
|
+
const value = this.evaluate(operand);
|
|
153
|
+
switch (operator) {
|
|
154
|
+
case "!":
|
|
155
|
+
if (typeof value !== "boolean") {
|
|
156
|
+
throw new TypeError("boolean", getTypeName(value), position, this.source);
|
|
157
|
+
}
|
|
158
|
+
return !value;
|
|
159
|
+
case "-":
|
|
160
|
+
if (typeof value !== "number") {
|
|
161
|
+
throw new TypeError("number", getTypeName(value), position, this.source);
|
|
162
|
+
}
|
|
163
|
+
return -value;
|
|
164
|
+
}
|
|
165
|
+
}
|
|
166
|
+
evaluateBinaryOp(operator, left, right, position) {
|
|
167
|
+
// Short-circuit evaluation for logical operators
|
|
168
|
+
if (operator === "&&") {
|
|
169
|
+
const leftValue = this.evaluate(left);
|
|
170
|
+
if (typeof leftValue !== "boolean") {
|
|
171
|
+
throw new TypeError("boolean", getTypeName(leftValue), left.position, this.source);
|
|
172
|
+
}
|
|
173
|
+
if (!leftValue)
|
|
174
|
+
return false;
|
|
175
|
+
const rightValue = this.evaluate(right);
|
|
176
|
+
if (typeof rightValue !== "boolean") {
|
|
177
|
+
throw new TypeError("boolean", getTypeName(rightValue), right.position, this.source);
|
|
178
|
+
}
|
|
179
|
+
return rightValue;
|
|
180
|
+
}
|
|
181
|
+
if (operator === "||") {
|
|
182
|
+
const leftValue = this.evaluate(left);
|
|
183
|
+
if (typeof leftValue !== "boolean") {
|
|
184
|
+
throw new TypeError("boolean", getTypeName(leftValue), left.position, this.source);
|
|
185
|
+
}
|
|
186
|
+
if (leftValue)
|
|
187
|
+
return true;
|
|
188
|
+
const rightValue = this.evaluate(right);
|
|
189
|
+
if (typeof rightValue !== "boolean") {
|
|
190
|
+
throw new TypeError("boolean", getTypeName(rightValue), right.position, this.source);
|
|
191
|
+
}
|
|
192
|
+
return rightValue;
|
|
193
|
+
}
|
|
194
|
+
// Eager evaluation for other operators
|
|
195
|
+
const leftValue = this.evaluate(left);
|
|
196
|
+
const rightValue = this.evaluate(right);
|
|
197
|
+
switch (operator) {
|
|
198
|
+
// Arithmetic
|
|
199
|
+
case "+":
|
|
200
|
+
if (typeof leftValue === "string" && typeof rightValue === "string") {
|
|
201
|
+
return leftValue + rightValue;
|
|
202
|
+
}
|
|
203
|
+
if (typeof leftValue === "number" && typeof rightValue === "number") {
|
|
204
|
+
return leftValue + rightValue;
|
|
205
|
+
}
|
|
206
|
+
throw new EvaluationError(`Cannot add ${getTypeName(leftValue)} and ${getTypeName(rightValue)}`, position, this.source);
|
|
207
|
+
case "-":
|
|
208
|
+
if (typeof leftValue !== "number" || typeof rightValue !== "number") {
|
|
209
|
+
throw new EvaluationError(`Cannot subtract ${getTypeName(leftValue)} and ${getTypeName(rightValue)}`, position, this.source);
|
|
210
|
+
}
|
|
211
|
+
return leftValue - rightValue;
|
|
212
|
+
case "*":
|
|
213
|
+
if (typeof leftValue !== "number" || typeof rightValue !== "number") {
|
|
214
|
+
throw new EvaluationError(`Cannot multiply ${getTypeName(leftValue)} and ${getTypeName(rightValue)}`, position, this.source);
|
|
215
|
+
}
|
|
216
|
+
return leftValue * rightValue;
|
|
217
|
+
case "/":
|
|
218
|
+
if (typeof leftValue !== "number" || typeof rightValue !== "number") {
|
|
219
|
+
throw new EvaluationError(`Cannot divide ${getTypeName(leftValue)} and ${getTypeName(rightValue)}`, position, this.source);
|
|
220
|
+
}
|
|
221
|
+
if (rightValue === 0) {
|
|
222
|
+
throw new EvaluationError("Division by zero", position, this.source);
|
|
223
|
+
}
|
|
224
|
+
return leftValue / rightValue;
|
|
225
|
+
case "%":
|
|
226
|
+
if (typeof leftValue !== "number" || typeof rightValue !== "number") {
|
|
227
|
+
throw new EvaluationError(`Cannot compute modulo of ${getTypeName(leftValue)} and ${getTypeName(rightValue)}`, position, this.source);
|
|
228
|
+
}
|
|
229
|
+
if (rightValue === 0) {
|
|
230
|
+
throw new EvaluationError("Modulo by zero", position, this.source);
|
|
231
|
+
}
|
|
232
|
+
return leftValue % rightValue;
|
|
233
|
+
// Comparison
|
|
234
|
+
case "<":
|
|
235
|
+
case "<=":
|
|
236
|
+
case ">":
|
|
237
|
+
case ">=":
|
|
238
|
+
return this.evaluateComparison(operator, leftValue, rightValue, position);
|
|
239
|
+
// Equality
|
|
240
|
+
case "==":
|
|
241
|
+
return this.valuesEqual(leftValue, rightValue);
|
|
242
|
+
case "!=":
|
|
243
|
+
return !this.valuesEqual(leftValue, rightValue);
|
|
244
|
+
// Membership
|
|
245
|
+
case "in":
|
|
246
|
+
return this.evaluateIn(leftValue, rightValue, position);
|
|
247
|
+
case "not in":
|
|
248
|
+
return !this.evaluateIn(leftValue, rightValue, position);
|
|
249
|
+
}
|
|
250
|
+
}
|
|
251
|
+
evaluateComparison(operator, left, right, position) {
|
|
252
|
+
// Numbers
|
|
253
|
+
if (typeof left === "number" && typeof right === "number") {
|
|
254
|
+
switch (operator) {
|
|
255
|
+
case "<":
|
|
256
|
+
return left < right;
|
|
257
|
+
case "<=":
|
|
258
|
+
return left <= right;
|
|
259
|
+
case ">":
|
|
260
|
+
return left > right;
|
|
261
|
+
case ">=":
|
|
262
|
+
return left >= right;
|
|
263
|
+
}
|
|
264
|
+
}
|
|
265
|
+
// Strings
|
|
266
|
+
if (typeof left === "string" && typeof right === "string") {
|
|
267
|
+
switch (operator) {
|
|
268
|
+
case "<":
|
|
269
|
+
return left < right;
|
|
270
|
+
case "<=":
|
|
271
|
+
return left <= right;
|
|
272
|
+
case ">":
|
|
273
|
+
return left > right;
|
|
274
|
+
case ">=":
|
|
275
|
+
return left >= right;
|
|
276
|
+
}
|
|
277
|
+
}
|
|
278
|
+
throw new EvaluationError(`Cannot compare ${getTypeName(left)} and ${getTypeName(right)} with ${operator}`, position, this.source);
|
|
279
|
+
}
|
|
280
|
+
evaluateIn(left, right, position) {
|
|
281
|
+
// String in string (substring check)
|
|
282
|
+
if (typeof left === "string" && typeof right === "string") {
|
|
283
|
+
return right.includes(left);
|
|
284
|
+
}
|
|
285
|
+
// Value in array
|
|
286
|
+
if (Array.isArray(right)) {
|
|
287
|
+
return right.some((item) => this.valuesEqual(left, item));
|
|
288
|
+
}
|
|
289
|
+
// Key in object
|
|
290
|
+
if (typeof right === "object" && right !== null && !Array.isArray(right)) {
|
|
291
|
+
if (typeof left !== "string") {
|
|
292
|
+
throw new EvaluationError(`Cannot check if ${getTypeName(left)} is a key in object (expected string)`, position, this.source);
|
|
293
|
+
}
|
|
294
|
+
return left in right;
|
|
295
|
+
}
|
|
296
|
+
throw new EvaluationError(`Cannot check membership: ${getTypeName(left)} in ${getTypeName(right)}`, position, this.source);
|
|
297
|
+
}
|
|
298
|
+
evaluateTernaryOp(condition, consequent, alternate, _position) {
|
|
299
|
+
const condValue = this.evaluate(condition);
|
|
300
|
+
if (typeof condValue !== "boolean") {
|
|
301
|
+
throw new TypeError("boolean", getTypeName(condValue), condition.position, this.source);
|
|
302
|
+
}
|
|
303
|
+
return condValue ? this.evaluate(consequent) : this.evaluate(alternate);
|
|
304
|
+
}
|
|
305
|
+
/**
|
|
306
|
+
* Deep equality check for expression values.
|
|
307
|
+
*/
|
|
308
|
+
valuesEqual(a, b) {
|
|
309
|
+
// Identical primitives or same reference
|
|
310
|
+
if (a === b)
|
|
311
|
+
return true;
|
|
312
|
+
// Type mismatch
|
|
313
|
+
if (typeof a !== typeof b)
|
|
314
|
+
return false;
|
|
315
|
+
// null check (both must be null if one is)
|
|
316
|
+
if (a === null || b === null)
|
|
317
|
+
return false;
|
|
318
|
+
// Arrays
|
|
319
|
+
if (Array.isArray(a) && Array.isArray(b)) {
|
|
320
|
+
if (a.length !== b.length)
|
|
321
|
+
return false;
|
|
322
|
+
for (let i = 0; i < a.length; i++) {
|
|
323
|
+
if (!this.valuesEqual(a[i], b[i])) {
|
|
324
|
+
return false;
|
|
325
|
+
}
|
|
326
|
+
}
|
|
327
|
+
return true;
|
|
328
|
+
}
|
|
329
|
+
// Objects
|
|
330
|
+
if (typeof a === "object" && typeof b === "object") {
|
|
331
|
+
const aKeys = Object.keys(a);
|
|
332
|
+
const bKeys = Object.keys(b);
|
|
333
|
+
if (aKeys.length !== bKeys.length)
|
|
334
|
+
return false;
|
|
335
|
+
for (const key of aKeys) {
|
|
336
|
+
if (!Object.prototype.hasOwnProperty.call(b, key))
|
|
337
|
+
return false;
|
|
338
|
+
const aRecord = a;
|
|
339
|
+
const bRecord = b;
|
|
340
|
+
if (!this.valuesEqual(aRecord[key], bRecord[key])) {
|
|
341
|
+
return false;
|
|
342
|
+
}
|
|
343
|
+
}
|
|
344
|
+
return true;
|
|
345
|
+
}
|
|
346
|
+
return false;
|
|
347
|
+
}
|
|
348
|
+
}
|
|
349
|
+
/**
|
|
350
|
+
* Evaluates an AST against a context and returns the result.
|
|
351
|
+
*
|
|
352
|
+
* @param ast - The AST to evaluate
|
|
353
|
+
* @param context - The evaluation context with bindings
|
|
354
|
+
* @returns The evaluation result
|
|
355
|
+
*/
|
|
356
|
+
export function evaluate(ast, context) {
|
|
357
|
+
try {
|
|
358
|
+
const evaluator = new Evaluator(context);
|
|
359
|
+
const value = evaluator.evaluate(ast);
|
|
360
|
+
return { value, success: true };
|
|
361
|
+
}
|
|
362
|
+
catch (error) {
|
|
363
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
364
|
+
return { value: null, success: false, error: message };
|
|
365
|
+
}
|
|
366
|
+
}
|
|
367
|
+
/**
|
|
368
|
+
* Evaluates an AST as a boolean condition.
|
|
369
|
+
*
|
|
370
|
+
* @param ast - The AST to evaluate
|
|
371
|
+
* @param context - The evaluation context with bindings
|
|
372
|
+
* @returns true if the condition is met, false otherwise (including errors)
|
|
373
|
+
*/
|
|
374
|
+
export function evaluateAsBoolean(ast, context) {
|
|
375
|
+
try {
|
|
376
|
+
const evaluator = new Evaluator(context);
|
|
377
|
+
const value = evaluator.evaluateAsBoolean(ast);
|
|
378
|
+
return { value };
|
|
379
|
+
}
|
|
380
|
+
catch (error) {
|
|
381
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
382
|
+
return { value: false, error: message };
|
|
383
|
+
}
|
|
384
|
+
}
|
|
385
|
+
//# sourceMappingURL=evaluator.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"evaluator.js","sourceRoot":"","sources":["../../../../../src/naylence/fame/expr/evaluator.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Generic expression engine.
|
|
3
|
+
*
|
|
4
|
+
* This module provides a deterministic, side-effect-free expression
|
|
5
|
+
* evaluation engine with injectable built-in functions.
|
|
6
|
+
*
|
|
7
|
+
* @packageDocumentation
|
|
8
|
+
*/
|
|
9
|
+
// Core types and utilities
|
|
10
|
+
export * from "./ast.js";
|
|
11
|
+
export * from "./errors.js";
|
|
12
|
+
export * from "./limits.js";
|
|
13
|
+
// Tokenizer
|
|
14
|
+
export { tokenize, Tokenizer } from "./tokenizer.js";
|
|
15
|
+
// Parser
|
|
16
|
+
export { parse, Parser } from "./parser.js";
|
|
17
|
+
// Evaluator
|
|
18
|
+
export { evaluate, evaluateAsBoolean, Evaluator, } from "./evaluator.js";
|
|
19
|
+
// Builtins
|
|
20
|
+
export { BUILTIN_FUNCTIONS, callBuiltin, isBuiltinFunction, getTypeName, normalizeJsValue, } from "./builtins.js";
|
|
21
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../../src/naylence/fame/expr/index.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,2BAA2B;AAC3B,cAAc,UAAU,CAAC;AACzB,cAAc,aAAa,CAAC;AAC5B,cAAc,aAAa,CAAC;AAE5B,YAAY;AACZ,OAAO,EAAE,QAAQ,EAAE,SAAS,EAA8B,MAAM,gBAAgB,CAAC;AAEjF,SAAS;AACT,OAAO,EAAE,KAAK,EAAE,MAAM,EAAE,MAAM,aAAa,CAAC;AAE5C,YAAY;AACZ,OAAO,EACL,QAAQ,EACR,iBAAiB,EACjB,SAAS,GAGV,MAAM,gBAAgB,CAAC;AAExB,WAAW;AACX,OAAO,EACL,iBAAiB,EACjB,WAAW,EACX,iBAAiB,EACjB,WAAW,EACX,gBAAgB,GAKjB,MAAM,eAAe,CAAC"}
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Resource limits for expression parsing and evaluation.
|
|
3
|
+
*
|
|
4
|
+
* These limits protect against resource exhaustion attacks and
|
|
5
|
+
* overly complex expressions.
|
|
6
|
+
*/
|
|
7
|
+
/**
|
|
8
|
+
* Default expression limits.
|
|
9
|
+
*
|
|
10
|
+
* These values are chosen to allow reasonable expressions while
|
|
11
|
+
* preventing resource exhaustion.
|
|
12
|
+
*/
|
|
13
|
+
export const DEFAULT_EXPRESSION_LIMITS = {
|
|
14
|
+
maxExpressionLength: 4096,
|
|
15
|
+
maxAstDepth: 32,
|
|
16
|
+
maxAstNodes: 256,
|
|
17
|
+
maxRegexPatternLength: 256,
|
|
18
|
+
maxGlobPatternLength: 256,
|
|
19
|
+
maxStringLength: 1024,
|
|
20
|
+
maxArrayLength: 64,
|
|
21
|
+
maxFunctionArgs: 16,
|
|
22
|
+
maxMemberAccessDepth: 16,
|
|
23
|
+
};
|
|
24
|
+
/**
|
|
25
|
+
* Validates that expression length is within limits.
|
|
26
|
+
*/
|
|
27
|
+
export function checkExpressionLength(expression, limits = DEFAULT_EXPRESSION_LIMITS) {
|
|
28
|
+
if (expression.length > limits.maxExpressionLength) {
|
|
29
|
+
throw new Error(`Expression length ${expression.length} exceeds limit of ${limits.maxExpressionLength}`);
|
|
30
|
+
}
|
|
31
|
+
}
|
|
32
|
+
/**
|
|
33
|
+
* Validates AST depth during parsing.
|
|
34
|
+
*/
|
|
35
|
+
export function checkAstDepth(depth, limits = DEFAULT_EXPRESSION_LIMITS) {
|
|
36
|
+
if (depth > limits.maxAstDepth) {
|
|
37
|
+
throw new Error(`AST depth ${depth} exceeds limit of ${limits.maxAstDepth}`);
|
|
38
|
+
}
|
|
39
|
+
}
|
|
40
|
+
/**
|
|
41
|
+
* Validates AST node count during parsing.
|
|
42
|
+
*/
|
|
43
|
+
export function checkAstNodeCount(count, limits = DEFAULT_EXPRESSION_LIMITS) {
|
|
44
|
+
if (count > limits.maxAstNodes) {
|
|
45
|
+
throw new Error(`AST node count ${count} exceeds limit of ${limits.maxAstNodes}`);
|
|
46
|
+
}
|
|
47
|
+
}
|
|
48
|
+
/**
|
|
49
|
+
* Validates regex pattern length before compilation.
|
|
50
|
+
*/
|
|
51
|
+
export function checkRegexPatternLength(pattern, limits = DEFAULT_EXPRESSION_LIMITS) {
|
|
52
|
+
if (pattern.length > limits.maxRegexPatternLength) {
|
|
53
|
+
throw new Error(`Regex pattern length ${pattern.length} exceeds limit of ${limits.maxRegexPatternLength}`);
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
/**
|
|
57
|
+
* Validates glob pattern length before compilation.
|
|
58
|
+
*/
|
|
59
|
+
export function checkGlobPatternLength(pattern, limits = DEFAULT_EXPRESSION_LIMITS) {
|
|
60
|
+
if (pattern.length > limits.maxGlobPatternLength) {
|
|
61
|
+
throw new Error(`Glob pattern length ${pattern.length} exceeds limit of ${limits.maxGlobPatternLength}`);
|
|
62
|
+
}
|
|
63
|
+
}
|
|
64
|
+
/**
|
|
65
|
+
* Validates array length during evaluation.
|
|
66
|
+
*/
|
|
67
|
+
export function checkArrayLength(length, limits = DEFAULT_EXPRESSION_LIMITS) {
|
|
68
|
+
if (length > limits.maxArrayLength) {
|
|
69
|
+
throw new Error(`Array length ${length} exceeds limit of ${limits.maxArrayLength}`);
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
/**
|
|
73
|
+
* Validates function argument count.
|
|
74
|
+
*/
|
|
75
|
+
export function checkFunctionArgCount(count, limits = DEFAULT_EXPRESSION_LIMITS) {
|
|
76
|
+
if (count > limits.maxFunctionArgs) {
|
|
77
|
+
throw new Error(`Function argument count ${count} exceeds limit of ${limits.maxFunctionArgs}`);
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
//# sourceMappingURL=limits.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"limits.js","sourceRoot":"","sources":["../../../../../src/naylence/fame/expr/limits.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAkCH;;;;;GAKG;AACH,MAAM,CAAC,MAAM,yBAAyB,GAA+B;IACnE,mBAAmB,EAAE,IAAI;IACzB,WAAW,EAAE,EAAE;IACf,WAAW,EAAE,GAAG;IAChB,qBAAqB,EAAE,GAAG;IAC1B,oBAAoB,EAAE,GAAG;IACzB,eAAe,EAAE,IAAI;IACrB,cAAc,EAAE,EAAE;IAClB,eAAe,EAAE,EAAE;IACnB,oBAAoB,EAAE,EAAE;CAChB,CAAC;AAEX;;GAEG;AACH,MAAM,UAAU,qBAAqB,CACnC,UAAkB,EAClB,SAA2B,yBAAyB;IAEpD,IAAI,UAAU,CAAC,MAAM,GAAG,MAAM,CAAC,mBAAmB,EAAE,CAAC;QACnD,MAAM,IAAI,KAAK,CACb,qBAAqB,UAAU,CAAC,MAAM,qBAAqB,MAAM,CAAC,mBAAmB,EAAE,CACxF,CAAC;IACJ,CAAC;AACH,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,aAAa,CAC3B,KAAa,EACb,SAA2B,yBAAyB;IAEpD,IAAI,KAAK,GAAG,MAAM,CAAC,WAAW,EAAE,CAAC;QAC/B,MAAM,IAAI,KAAK,CACb,aAAa,KAAK,qBAAqB,MAAM,CAAC,WAAW,EAAE,CAC5D,CAAC;IACJ,CAAC;AACH,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,iBAAiB,CAC/B,KAAa,EACb,SAA2B,yBAAyB;IAEpD,IAAI,KAAK,GAAG,MAAM,CAAC,WAAW,EAAE,CAAC;QAC/B,MAAM,IAAI,KAAK,CACb,kBAAkB,KAAK,qBAAqB,MAAM,CAAC,WAAW,EAAE,CACjE,CAAC;IACJ,CAAC;AACH,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,uBAAuB,CACrC,OAAe,EACf,SAA2B,yBAAyB;IAEpD,IAAI,OAAO,CAAC,MAAM,GAAG,MAAM,CAAC,qBAAqB,EAAE,CAAC;QAClD,MAAM,IAAI,KAAK,CACb,wBAAwB,OAAO,CAAC,MAAM,qBAAqB,MAAM,CAAC,qBAAqB,EAAE,CAC1F,CAAC;IACJ,CAAC;AACH,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,sBAAsB,CACpC,OAAe,EACf,SAA2B,yBAAyB;IAEpD,IAAI,OAAO,CAAC,MAAM,GAAG,MAAM,CAAC,oBAAoB,EAAE,CAAC;QACjD,MAAM,IAAI,KAAK,CACb,uBAAuB,OAAO,CAAC,MAAM,qBAAqB,MAAM,CAAC,oBAAoB,EAAE,CACxF,CAAC;IACJ,CAAC;AACH,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,gBAAgB,CAC9B,MAAc,EACd,SAA2B,yBAAyB;IAEpD,IAAI,MAAM,GAAG,MAAM,CAAC,cAAc,EAAE,CAAC;QACnC,MAAM,IAAI,KAAK,CACb,gBAAgB,MAAM,qBAAqB,MAAM,CAAC,cAAc,EAAE,CACnE,CAAC;IACJ,CAAC;AACH,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,qBAAqB,CACnC,KAAa,EACb,SAA2B,yBAAyB;IAEpD,IAAI,KAAK,GAAG,MAAM,CAAC,eAAe,EAAE,CAAC;QACnC,MAAM,IAAI,KAAK,CACb,2BAA2B,KAAK,qBAAqB,MAAM,CAAC,eAAe,EAAE,CAC9E,CAAC;IACJ,CAAC;AACH,CAAC"}
|