@statedelta-libs/expressions 0.0.2 → 0.0.3

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 CHANGED
@@ -8,8 +8,9 @@
8
8
  ## Características
9
9
 
10
10
  - **Compilação** - Compila uma vez, executa milhões de vezes
11
- - **Alta performance** - ~3M ops/sec após compilação
11
+ - **Alta performance** - ~25-30M ops/s após compilação
12
12
  - **Scope externo** - Funções vêm via scope, não hardcoded
13
+ - **Accessor customizado** - Suporte a `ctx.get(path)` para objetos especiais
13
14
  - **$pipe** - Composição com valor inicial (sintaxe DSL)
14
15
  - **Path syntax** - Suporte a wildcards (`items[*].price`)
15
16
  - **Dependency extraction** - Para dirty tracking/reatividade
@@ -221,6 +222,42 @@ const scope = {
221
222
  const { fn } = compile(expression, { scope });
222
223
  ```
223
224
 
225
+ ## Accessor Customizado
226
+
227
+ Para objetos que usam interface de acesso customizada (como `ctx.get(path)`), use o `accessor`:
228
+
229
+ ```typescript
230
+ // Contexto com método get() customizado
231
+ interface TickContext {
232
+ get(path: string): unknown;
233
+ }
234
+
235
+ const accessor = (path: string, ctx: TickContext) => ctx.get(path);
236
+
237
+ // Compilação com accessor
238
+ const { fn } = compile<TickContext>(
239
+ { $: "hp:value" },
240
+ { accessor }
241
+ );
242
+
243
+ fn(tickContext); // usa ctx.get('hp:value')
244
+
245
+ // Com scope + accessor
246
+ const { fn } = compile<TickContext>(
247
+ { $fn: "add", args: [{ $: "a" }, { $: "b" }] },
248
+ { scope, accessor }
249
+ );
250
+ ```
251
+
252
+ O accessor é propagado para:
253
+ - Referências (`{ $: "path" }`)
254
+ - Shorthand de `$if` (`{ $if: "path", ... }`)
255
+ - Argumentos de `$fn`
256
+ - Steps de `$pipe`
257
+ - Conditions (delegadas para `@statedelta-libs/conditions`)
258
+
259
+ **Performance:** Igual ao acesso direto (~25-30M ops/s).
260
+
224
261
  ## Path Syntax
225
262
 
226
263
  | Path | Resultado |
@@ -253,11 +290,12 @@ cache.clear(); // Limpar
253
290
  | Operação | Velocidade |
254
291
  |----------|------------|
255
292
  | Compile (literal) | ~6.5M ops/s |
256
- | Compile (ref) | ~2.5M ops/s |
293
+ | Compile (ref) | ~3M ops/s |
257
294
  | Compile (fn nested) | ~550K ops/s |
258
295
  | Compile (complex) | ~300K ops/s |
259
- | Execute (ref) | ~28M ops/s |
296
+ | Execute (ref) | ~28-30M ops/s |
260
297
  | Execute (fn nested) | ~9M ops/s |
298
+ | Execute (com accessor) | ~23-30M ops/s |
261
299
 
262
300
  ### compileAST() - AST + new Function
263
301
 
@@ -338,6 +376,7 @@ import type {
338
376
  PipeExpr,
339
377
  Scope,
340
378
  CompileOptions,
379
+ AccessorFn,
341
380
  } from '@statedelta-libs/expressions';
342
381
 
343
382
  // Type guards
package/dist/index.cjs CHANGED
@@ -1 +1 @@
1
- 'use strict';var conditions=require('@statedelta-libs/conditions'),omniAst=require('omni-ast');var m=n=>n!==null&&typeof n=="object"&&"$"in n&&typeof n.$=="string"&&Object.keys(n).length===1,h=n=>n!==null&&typeof n=="object"&&"$if"in n&&"then"in n,E=n=>n!==null&&typeof n=="object"&&"$fn"in n&&typeof n.$fn=="string",C=n=>n!==null&&typeof n=="object"&&"$pipe"in n&&Array.isArray(n.$pipe),M=new Set(["eq","neq","gt","gte","lt","lte","in","notIn","contains","notContains","exists","notExists","matches","notMatches","startsWith","endsWith"]),g=n=>n!==null&&typeof n=="object"&&"path"in n&&"op"in n&&M.has(n.op)&&!("$"in n)&&!("$if"in n)&&!("$fn"in n),y=n=>n!==null&&typeof n=="object"&&"logic"in n&&"conditions"in n,H=n=>g(n)||y(n),W=n=>{if(n===null)return true;let e=typeof n;if(e==="string"||e==="number"||e==="boolean"||Array.isArray(n))return true;if(e==="object"&&n!==null){let t=n,o="path"in t&&"op"in t&&M.has(t.op);return !("$"in t)&&!("$if"in t)&&!("$fn"in t)&&!("$pipe"in t)&&!o&&!("logic"in t)}return false};var R=new Map;function I(n){let e=[],t=n.length,o=0,i="";for(;o<t;){let s=n[o];if(s===".")i&&(e.push({type:"key",value:i}),i=""),o++;else if(s==="["){i&&(e.push({type:"key",value:i}),i=""),o++;let r=o;for(;o<t&&n[o]!=="]";)o++;let c=n.slice(r,o);if(o++,c==="*")e.push({type:"wildcard",value:"*"});else {let f=parseInt(c,10);e.push({type:"index",value:isNaN(f)?c:f});}}else i+=s,o++;}return i&&e.push({type:"key",value:i}),e}function V(n){return n.includes("[*]")}function x(n){let e=R.get(n);return e||(e=V(n)?U(n):Q(n),R.set(n,e),e)}function Q(n){if(!n.includes(".")&&!n.includes("["))return i=>i?.[n];let e=I(n),t=e.length;if(t===2){let[i,s]=e,r=i.value,c=s.value;return f=>f?.[r]?.[c]}if(t===3){let[i,s,r]=e,c=i.value,f=s.value,a=r.value;return u=>u?.[c]?.[f]?.[a]}let o=e.map(i=>i.value);return i=>{let s=i;for(let r=0;r<t&&s!=null;r++)s=s[o[r]];return s}}function U(n){let e=I(n),t=[];for(let o=0;o<e.length;o++)e[o].type==="wildcard"&&t.push(o);return t.length===1?X(e,t[0]):Z(e,t)}function X(n,e){let t=n.slice(0,e).map(r=>r.value),o=n.slice(e+1).map(r=>r.value),i=t.length,s=o.length;if(s===0){if(i===1){let r=t[0];return c=>c?.[r]}return r=>{let c=r;for(let f=0;f<i&&c!=null;f++)c=c[t[f]];return c}}if(s===1){let r=o[0];if(i===1){let c=t[0];return f=>{let a=f?.[c];if(Array.isArray(a))return a.map(u=>u?.[r])}}return c=>{let f=c;for(let a=0;a<i&&f!=null;a++)f=f[t[a]];if(Array.isArray(f))return f.map(a=>a?.[r])}}return r=>{let c=r;for(let f=0;f<i&&c!=null;f++)c=c[t[f]];if(Array.isArray(c))return c.map(f=>{let a=f;for(let u=0;u<s&&a!=null;u++)a=a[o[u]];return a})}}function Z(n,e){let t=[],o=0;for(let s=0;s<e.length;s++){let r=e[s],c=s===e.length-1,f=n.slice(o,r).map(a=>a.value);f.length>0&&t.push({type:"access",keys:f}),t.push({type:c?"map":"flatMap",keys:[]}),o=r+1;}let i=n.slice(o).map(s=>s.value);return s=>{let r=s;for(let c of t){if(r==null)return;if(c.type==="access")for(let f of c.keys){if(r==null)return;r=r[f];}else if(c.type==="flatMap"){if(!Array.isArray(r))return;r=r.flatMap(f=>{let a=f;return Array.isArray(a)?a:[a]});}else if(c.type==="map"){if(!Array.isArray(r))return;i.length>0&&(r=r.map(f=>{let a=f;for(let u of i){if(a==null)return;a=a[u];}return a}));}}return r}}function nn(n,e){return x(e)(n)}function k(n){let e=n.indexOf("[*]");return e===-1?n:n.slice(0,e)}function en(){R.clear();}function tn(){return R.size}function T(n){let e=new Set;return A(n,e),Array.from(e)}function A(n,e){if(n===null||typeof n!="object")return;if(Array.isArray(n)){for(let i=0;i<n.length;i++)A(n[i],e);return}if(m(n)){e.add(k(n.$));return}if(h(n)){if(typeof n.$if=="string"){let i=n.$if.startsWith("!")?n.$if.slice(1):n.$if;e.add(k(i));}else A(n.$if,e);A(n.then,e),n.else!==void 0&&A(n.else,e);return}if(C(n)){for(let i=0;i<n.$pipe.length;i++)A(n.$pipe[i],e);return}if(E(n)){if(n.args)for(let i=0;i<n.args.length;i++)A(n.args[i],e);return}if(g(n)){e.add(k(n.path)),n.value!==void 0&&conditions.isRef(n.value)&&e.add(k(n.value.$));return}if(y(n)){for(let i=0;i<n.conditions.length;i++)A(n.conditions[i],e);return}let t=n,o=Object.keys(t);for(let i=0;i<o.length;i++)A(t[o[i]],e);}function rn(n){return T(n).length>0}function sn(n){return T(n).length===0}function ln(n){return JSON.stringify(n)}function O(n,e={}){let t=e.scope??{},o=b(n,t),i=T(n),s=ln(n);return {fn:o,deps:i,hash:s}}function b(n,e){if(n===null)return ()=>null;if(typeof n!="object")return ()=>n;if(Array.isArray(n)){let t=n.map(o=>b(o,e));return o=>t.map(i=>i(o))}if(m(n))return cn(n);if(h(n))return fn(n,e);if(C(n))return an(n,e);if(E(n))return un(n,e);if(g(n))return conditions.compile(n);if(y(n))return conditions.compile(n);if(W(n)){let t=n,o=Object.keys(t),i=o.map(s=>b(t[s],e));return s=>{let r={};for(let c=0;c<o.length;c++)r[o[c]]=i[c](s);return r}}return ()=>n}function cn(n){return x(n.$)}function fn(n,e){let t;if(typeof n.$if=="string"){let s=n.$if.startsWith("!")?n.$if.slice(1):n.$if,r=x(s);t=n.$if.startsWith("!")?f=>!r(f):f=>!!r(f);}else {let s=b(n.$if,e);t=r=>!!s(r);}let o=b(n.then,e),i=n.else!==void 0?b(n.else,e):()=>{};return s=>t(s)?o(s):i(s)}function an(n,e){let t=n.$pipe;if(t.length===0)return ()=>{};if(t.length===1)return b(t[0],e);let o=b(t[0],e),i=t.slice(1).map(r=>b(r,e)),s=i.length;if(s===1){let[r]=i;return c=>{let f=o(c),a=r(c);return typeof a=="function"?a(f):a}}if(s===2){let[r,c]=i;return f=>{let a=o(f),u=r(f);return a=typeof u=="function"?u(a):u,u=c(f),typeof u=="function"?u(a):u}}if(s===3){let[r,c,f]=i;return a=>{let u=o(a),p=r(a);return u=typeof p=="function"?p(u):p,p=c(a),u=typeof p=="function"?p(u):p,p=f(a),typeof p=="function"?p(u):p}}return r=>{let c=o(r);for(let f=0;f<s;f++){let a=i[f](r);c=typeof a=="function"?a(c):a;}return c}}function un(n,e){let t=n.$fn,o=n.args;if(o===void 0)return ()=>{let r=e[t];if(!r)throw new Error(`Function not found in scope: ${t}`);return r};let i=o.map(r=>b(r,e)),s=i.length;if(s===0)return r=>{let c=e[t];if(!c)throw new Error(`Function not found in scope: ${t}`);return c()};if(s===1){let[r]=i;return c=>{let f=e[t];if(!f)throw new Error(`Function not found in scope: ${t}`);return f(r(c))}}if(s===2){let[r,c]=i;return f=>{let a=e[t];if(!a)throw new Error(`Function not found in scope: ${t}`);return a(r(f),c(f))}}if(s===3){let[r,c,f]=i;return a=>{let u=e[t];if(!u)throw new Error(`Function not found in scope: ${t}`);return u(r(a),c(a),f(a))}}return r=>{let c=e[t];if(!c)throw new Error(`Function not found in scope: ${t}`);return c(...i.map(f=>f(r)))}}function pn(n,e,t={}){return O(n,t).fn(e)}var v=class{constructor(e=1e3){this.cache=new Map,this._maxSize=e;}get(e,t={}){let o=JSON.stringify(e),i=this.cache.get(o);if(i)return this.cache.delete(o),this.cache.set(o,i),i;let s=O(e,t);if(this.cache.size>=this._maxSize){let r=this.cache.keys().next().value;r&&this.cache.delete(r);}return this.cache.set(o,s),s}has(e){return this.cache.has(JSON.stringify(e))}delete(e){return this.cache.delete(JSON.stringify(e))}clear(){this.cache.clear();}get size(){return this.cache.size}get maxSize(){return this._maxSize}set maxSize(e){for(this._maxSize=e;this.cache.size>this._maxSize;){let t=this.cache.keys().next().value;t&&this.cache.delete(t);}}},_=new v;function dn(n,e={}){return _.get(n,e)}function z(n,e="root",t={}){let o=[];return $(n,e,o,t),{valid:o.length===0,errors:o}}function $(n,e,t,o){if(n===null||typeof n!="object")return;if(Array.isArray(n)){for(let r=0;r<n.length;r++)$(n[r],`${e}[${r}]`,t,o);return}if(m(n)){(!n.$||typeof n.$!="string")&&t.push(`${e}: invalid reference, $ must be non-empty string`);return}if(h(n)){typeof n.$if=="string"?(n.$if.startsWith("!")?n.$if.slice(1):n.$if)||t.push(`${e}.$if: empty path in string shorthand`):$(n.$if,`${e}.$if`,t,o),$(n.then,`${e}.then`,t,o),n.else!==void 0&&$(n.else,`${e}.else`,t,o);return}if(C(n)){if(!Array.isArray(n.$pipe)){t.push(`${e}.$pipe: must be an array`);return}if(n.$pipe.length===0){t.push(`${e}.$pipe: must have at least one element`);return}for(let r=0;r<n.$pipe.length;r++)$(n.$pipe[r],`${e}.$pipe[${r}]`,t,o);return}if(E(n)){if(!n.$fn||typeof n.$fn!="string"){t.push(`${e}: invalid function, $fn must be non-empty string`);return}if(o.scope&&!(n.$fn in o.scope)&&t.push(`${e}: function "${n.$fn}" not found in scope`),n.args!==void 0)if(!Array.isArray(n.args))t.push(`${e}.args: must be an array`);else for(let r=0;r<n.args.length;r++)$(n.args[r],`${e}.args[${r}]`,t,o);return}if(g(n)){let r=conditions.validate(n,e);r.valid||t.push(...r.errors);return}if(y(n)){let r=conditions.validate(n,e);r.valid||t.push(...r.errors);return}let i=n,s=Object.keys(i);for(let r=0;r<s.length;r++){let c=s[r];$(i[c],`${e}.${c}`,t,o);}}function mn(n,e={}){let t=z(n,"root",e);if(!t.valid)throw new Error(`Invalid expression: ${t.errors.join("; ")}`)}function gn(n,e={}){return z(n,"root",e).valid}var P="data",J="scope",yn={eq:"===",neq:"!==",gt:">",gte:">=",lt:"<",lte:"<="};function N(n,e={}){let{dataParam:t=P,scopeParam:o=J,noPrefixes:i=false}=e;return d(n,t,o,i)}function d(n,e,t,o){if(n===null)return omniAst.builders.literal(null);if(typeof n=="string")return omniAst.builders.literal(n);if(typeof n=="number")return omniAst.builders.literal(n);if(typeof n=="boolean")return omniAst.builders.literal(n);if(Array.isArray(n))return omniAst.builders.arrayExpression(n.map(i=>d(i,e,t,o)));if(m(n))return hn(n.$,e,o);if(h(n))return Cn(n,e,t,o);if(C(n))return Sn(n.$pipe,e,t,o);if(E(n))return bn(n,e,t,o);if(g(n))return An(n,e,t,o);if(y(n))return $n(n,e,t,o);if(typeof n=="object"){let s=Object.entries(n).map(([r,c])=>omniAst.builders.property(omniAst.builders.identifier(r),d(c,e,t,o)));return omniAst.builders.objectExpression(s)}return omniAst.builders.literal(null)}function hn(n,e,t){return n.includes("[*]")?En(n,e,t):w(n,e,t)}function w(n,e,t){let o=F(n);if(o.length===0)return t?omniAst.builders.identifier("undefined"):omniAst.builders.identifier(e);let i;if(t){let s=o[0];i=omniAst.builders.identifier(s.value);for(let r=1;r<o.length;r++){let c=o[r];c.type==="key"?i=omniAst.builders.memberExpression(i,omniAst.builders.identifier(c.value),false,true):i=omniAst.builders.memberExpression(i,omniAst.builders.literal(c.value),true,true);}}else {i=omniAst.builders.identifier(e);for(let s of o)s.type==="key"?i=omniAst.builders.memberExpression(i,omniAst.builders.identifier(s.value),false,true):i=omniAst.builders.memberExpression(i,omniAst.builders.literal(s.value),true,true);}return i}function En(n,e,t){let o=n.indexOf("[*]"),i=n.slice(0,o),s=n.slice(o+3),r;if(i?r=w(i,e,t):r=t?omniAst.builders.identifier("undefined"):omniAst.builders.identifier(e),!s||s==="")return r;if(s.includes("[*]"))return B(r,s);let c="_i",f=s.startsWith(".")?s.slice(1):s,a=omniAst.builders.identifier(c);if(f){let u=F(f);for(let p of u)p.type==="key"?a=omniAst.builders.memberExpression(a,omniAst.builders.identifier(p.value),false,true):a=omniAst.builders.memberExpression(a,omniAst.builders.literal(p.value),true,true);}return omniAst.builders.callExpression(omniAst.builders.memberExpression(r,omniAst.builders.identifier("map"),false,true),[omniAst.builders.arrowFunctionExpression([omniAst.builders.identifier(c)],a)])}function B(n,e){let t=e.indexOf("[*]"),o=e.slice(0,t),i=e.slice(t+3),s="_i",r=o.startsWith(".")?o.slice(1):o,c=omniAst.builders.identifier(s);if(r){let a=F(r);for(let u of a)u.type==="key"&&(c=omniAst.builders.memberExpression(c,omniAst.builders.identifier(u.value),false,true));}if(i.includes("[*]")){let a=B(c,i);return omniAst.builders.callExpression(omniAst.builders.memberExpression(n,omniAst.builders.identifier("flatMap"),false,true),[omniAst.builders.arrowFunctionExpression([omniAst.builders.identifier(s)],a)])}let f=i.startsWith(".")?i.slice(1):i;if(f){let a=F(f);for(let u of a)u.type==="key"&&(c=omniAst.builders.memberExpression(c,omniAst.builders.identifier(u.value),false,true));}return omniAst.builders.callExpression(omniAst.builders.memberExpression(n,omniAst.builders.identifier("flatMap"),false,true),[omniAst.builders.arrowFunctionExpression([omniAst.builders.identifier(s)],c)])}function Cn(n,e,t,o){let i;if(typeof n.$if=="string"){let c=n.$if.startsWith("!"),f=c?n.$if.slice(1):n.$if,a=w(f,e,o);i=c?omniAst.builders.unaryExpression("!",a):a;}else i=d(n.$if,e,t,o);let s=d(n.then,e,t,o),r=n.else!==void 0?d(n.else,e,t,o):omniAst.builders.identifier("undefined");return omniAst.builders.conditionalExpression(i,s,r)}function bn(n,e,t,o){let i=o?omniAst.builders.identifier(n.$fn):omniAst.builders.memberExpression(omniAst.builders.identifier(t),omniAst.builders.identifier(n.$fn),false,false);if(n.args===void 0)return i;let s=n.args.map(r=>d(r,e,t,o));return omniAst.builders.callExpression(i,s)}function Sn(n,e,t,o){if(n.length===0)return omniAst.builders.identifier("undefined");if(n.length===1)return d(n[0],e,t,o);let i=d(n[0],e,t,o);for(let s=1;s<n.length;s++){let r=d(n[s],e,t,o);i=omniAst.builders.callExpression(r,[i]);}return i}function An(n,e,t,o){let i=w(n.path,e,o),s=n.value!==void 0?m(n.value)?w(n.value.$,e,o):d(n.value,e,t,o):omniAst.builders.literal(null),r=yn[n.op];if(r)return omniAst.builders.binaryExpression(r,i,s);switch(n.op){case "in":return omniAst.builders.callExpression(omniAst.builders.memberExpression(s,omniAst.builders.identifier("includes")),[i]);case "notIn":return omniAst.builders.unaryExpression("!",omniAst.builders.callExpression(omniAst.builders.memberExpression(s,omniAst.builders.identifier("includes")),[i]));case "contains":return omniAst.builders.callExpression(omniAst.builders.memberExpression(i,omniAst.builders.identifier("includes"),false,true),[s]);case "notContains":return omniAst.builders.unaryExpression("!",omniAst.builders.callExpression(omniAst.builders.memberExpression(i,omniAst.builders.identifier("includes"),false,true),[s]));case "exists":return omniAst.builders.binaryExpression("!=",i,omniAst.builders.literal(null));case "notExists":return omniAst.builders.binaryExpression("==",i,omniAst.builders.literal(null));case "matches":return omniAst.builders.callExpression(omniAst.builders.memberExpression(omniAst.builders.newExpression(omniAst.builders.identifier("RegExp"),[s]),omniAst.builders.identifier("test")),[i]);case "notMatches":return omniAst.builders.unaryExpression("!",omniAst.builders.callExpression(omniAst.builders.memberExpression(omniAst.builders.newExpression(omniAst.builders.identifier("RegExp"),[s]),omniAst.builders.identifier("test")),[i]));case "startsWith":return omniAst.builders.callExpression(omniAst.builders.memberExpression(i,omniAst.builders.identifier("startsWith"),false,true),[s]);case "endsWith":return omniAst.builders.callExpression(omniAst.builders.memberExpression(i,omniAst.builders.identifier("endsWith"),false,true),[s]);default:return omniAst.builders.binaryExpression("===",i,s)}}function $n(n,e,t,o){let{logic:i,conditions:s}=n,r=i==="AND"?"&&":"||";if(s.length===0)return omniAst.builders.literal(i==="AND");if(s.length===1)return d(s[0],e,t,o);let c=d(s[0],e,t,o);for(let f=1;f<s.length;f++){let a=d(s[f],e,t,o);c=omniAst.builders.logicalExpression(r,c,a);}return c}function F(n){let e=[],t=n.length,o=0,i="";for(;o<t;){let s=n[o];if(s===".")i&&(e.push({type:"key",value:i}),i=""),o++;else if(s==="["){i&&(e.push({type:"key",value:i}),i=""),o++;let r=o;for(;o<t&&n[o]!=="]";)o++;let c=n.slice(r,o);if(o++,c!=="*"){let f=parseInt(c,10);e.push({type:"index",value:isNaN(f)?c:f});}}else i+=s,o++;}return i&&e.push({type:"key",value:i}),e}function K(n,e=[P]){return omniAst.builders.arrowFunctionExpression(e.map(t=>omniAst.builders.identifier(t)),n)}function j(n){let e=new Set;return S(n,e),e}function S(n,e){if(n===null||typeof n!="object")return;if(Array.isArray(n)){for(let o of n)S(o,e);return}if(m(n))return;if(h(n)){S(n.$if,e),S(n.then,e),n.else!==void 0&&S(n.else,e);return}if(C(n)){for(let o of n.$pipe)S(o,e);return}if(E(n)){if(e.add(n.$fn),n.args)for(let o of n.args)S(o,e);return}if(g(n)){n.value!==void 0&&typeof n.value=="object"&&S(n.value,e);return}if(y(n)){for(let o of n.conditions)S(o,e);return}let t=n;for(let o of Object.keys(t))S(t[o],e);}function G(n){let e=new Set;for(let t of n){let o=t.indexOf("."),i=t.indexOf("["),s=t.length;o!==-1&&(s=Math.min(s,o)),i!==-1&&(s=Math.min(s,i));let r=t.slice(0,s);r&&e.add(r);}return e}function kn(n){return JSON.stringify(n)}function xn(n,e,t){let o=N(n,{noPrefixes:true}),i=omniAst.generate(o),s=e.size>0?`const{${[...e].join(",")}}=data??{};`:"",r=t.size>0?`const{${[...t].join(",")}}=scope;`:"";return r?`(function(scope){${r}return function(data){${s}return ${i}}})`:`(function(){return function(data){${s}return ${i}}})`}function D(n,e={}){let{scope:t={},returnCode:o=false}=e,i=T(n),s=G(i),r=j(n),c=kn(n),f=xn(n,s,r);if(o)return {code:f,deps:i,hash:c,dataRoots:[...s],scopeFns:[...r]};let a;try{a=new Function(`return ${f}`)()(t);}catch(u){throw new Error(`AST compilation failed. If this is due to CSP, use the standard compile() function instead. Error: ${u instanceof Error?u.message:String(u)}`)}return {fn:a,deps:i,hash:c}}function Y(n,e,t={}){let{fn:o}=D(n,t);return o(e)}var ie="0.0.1";exports.ExpressionCache=v;exports.VERSION=ie;exports.assertValid=mn;exports.cache=_;exports.cached=dn;exports.clearPathCache=en;exports.compile=O;exports.compileAST=D;exports.compilePath=x;exports.dslToAST=N;exports.evaluate=pn;exports.evaluateAST=Y;exports.extractDataRoots=G;exports.extractDeps=T;exports.extractScopeFns=j;exports.get=nn;exports.getPathCacheSize=tn;exports.hasDeps=rn;exports.hasWildcard=V;exports.isCondition=g;exports.isConditionExpr=H;exports.isConditionGroup=y;exports.isConditional=h;exports.isFn=E;exports.isLiteral=W;exports.isPipe=C;exports.isPure=sn;exports.isRef=m;exports.isValid=gn;exports.normalizePath=k;exports.validate=z;exports.wrapInFunction=K;
1
+ 'use strict';var conditions=require('@statedelta-libs/conditions'),omniAst=require('omni-ast');var m=n=>n!==null&&typeof n=="object"&&"$"in n&&typeof n.$=="string"&&Object.keys(n).length===1,E=n=>n!==null&&typeof n=="object"&&"$if"in n&&"then"in n,T=n=>n!==null&&typeof n=="object"&&"$fn"in n&&typeof n.$fn=="string",A=n=>n!==null&&typeof n=="object"&&"$pipe"in n&&Array.isArray(n.$pipe),I=new Set(["eq","neq","gt","gte","lt","lte","in","notIn","contains","notContains","exists","notExists","matches","notMatches","startsWith","endsWith"]),g=n=>n!==null&&typeof n=="object"&&"path"in n&&"op"in n&&I.has(n.op)&&!("$"in n)&&!("$if"in n)&&!("$fn"in n),y=n=>n!==null&&typeof n=="object"&&"logic"in n&&"conditions"in n,U=n=>g(n)||y(n),z=n=>{if(n===null)return true;let e=typeof n;if(e==="string"||e==="number"||e==="boolean"||Array.isArray(n))return true;if(e==="object"&&n!==null){let o=n,t="path"in o&&"op"in o&&I.has(o.op);return !("$"in o)&&!("$if"in o)&&!("$fn"in o)&&!("$pipe"in o)&&!t&&!("logic"in o)}return false};var R=new Map;function V(n){let e=[],o=n.length,t=0,i="";for(;t<o;){let s=n[t];if(s===".")i&&(e.push({type:"key",value:i}),i=""),t++;else if(s==="["){i&&(e.push({type:"key",value:i}),i=""),t++;let r=t;for(;t<o&&n[t]!=="]";)t++;let f=n.slice(r,t);if(t++,f==="*")e.push({type:"wildcard",value:"*"});else {let c=parseInt(f,10);e.push({type:"index",value:isNaN(c)?f:c});}}else i+=s,t++;}return i&&e.push({type:"key",value:i}),e}function L(n){return n.includes("[*]")}function O(n){let e=R.get(n);return e||(e=L(n)?Z(n):X(n),R.set(n,e),e)}function X(n){if(!n.includes(".")&&!n.includes("["))return i=>i?.[n];let e=V(n),o=e.length;if(o===2){let[i,s]=e,r=i.value,f=s.value;return c=>c?.[r]?.[f]}if(o===3){let[i,s,r]=e,f=i.value,c=s.value,u=r.value;return a=>a?.[f]?.[c]?.[u]}let t=e.map(i=>i.value);return i=>{let s=i;for(let r=0;r<o&&s!=null;r++)s=s[t[r]];return s}}function Z(n){let e=V(n),o=[];for(let t=0;t<e.length;t++)e[t].type==="wildcard"&&o.push(t);return o.length===1?nn(e,o[0]):en(e,o)}function nn(n,e){let o=n.slice(0,e).map(r=>r.value),t=n.slice(e+1).map(r=>r.value),i=o.length,s=t.length;if(s===0){if(i===1){let r=o[0];return f=>f?.[r]}return r=>{let f=r;for(let c=0;c<i&&f!=null;c++)f=f[o[c]];return f}}if(s===1){let r=t[0];if(i===1){let f=o[0];return c=>{let u=c?.[f];if(Array.isArray(u))return u.map(a=>a?.[r])}}return f=>{let c=f;for(let u=0;u<i&&c!=null;u++)c=c[o[u]];if(Array.isArray(c))return c.map(u=>u?.[r])}}return r=>{let f=r;for(let c=0;c<i&&f!=null;c++)f=f[o[c]];if(Array.isArray(f))return f.map(c=>{let u=c;for(let a=0;a<s&&u!=null;a++)u=u[t[a]];return u})}}function en(n,e){let o=[],t=0;for(let s=0;s<e.length;s++){let r=e[s],f=s===e.length-1,c=n.slice(t,r).map(u=>u.value);c.length>0&&o.push({type:"access",keys:c}),o.push({type:f?"map":"flatMap",keys:[]}),t=r+1;}let i=n.slice(t).map(s=>s.value);return s=>{let r=s;for(let f of o){if(r==null)return;if(f.type==="access")for(let c of f.keys){if(r==null)return;r=r[c];}else if(f.type==="flatMap"){if(!Array.isArray(r))return;r=r.flatMap(c=>{let u=c;return Array.isArray(u)?u:[u]});}else if(f.type==="map"){if(!Array.isArray(r))return;i.length>0&&(r=r.map(c=>{let u=c;for(let a of i){if(u==null)return;u=u[a];}return u}));}}return r}}function tn(n,e){return O(e)(n)}function w(n){let e=n.indexOf("[*]");return e===-1?n:n.slice(0,e)}function on(){R.clear();}function rn(){return R.size}function k(n){let e=new Set;return S(n,e),Array.from(e)}function S(n,e){if(n===null||typeof n!="object")return;if(Array.isArray(n)){for(let i=0;i<n.length;i++)S(n[i],e);return}if(m(n)){e.add(w(n.$));return}if(E(n)){if(typeof n.$if=="string"){let i=n.$if.startsWith("!")?n.$if.slice(1):n.$if;e.add(w(i));}else S(n.$if,e);S(n.then,e),n.else!==void 0&&S(n.else,e);return}if(A(n)){for(let i=0;i<n.$pipe.length;i++)S(n.$pipe[i],e);return}if(T(n)){if(n.args)for(let i=0;i<n.args.length;i++)S(n.args[i],e);return}if(g(n)){e.add(w(n.path)),n.value!==void 0&&conditions.isRef(n.value)&&e.add(w(n.value.$));return}if(y(n)){for(let i=0;i<n.conditions.length;i++)S(n.conditions[i],e);return}let o=n,t=Object.keys(o);for(let i=0;i<t.length;i++)S(o[t[i]],e);}function ln(n){return k(n).length>0}function fn(n){return k(n).length===0}function cn(n){return JSON.stringify(n)}function F(n,e={}){let o=e.scope??{},t=e.accessor,i=C(n,o,t),s=k(n),r=cn(n);return {fn:i,deps:s,hash:r}}function C(n,e,o){if(n===null)return ()=>null;if(typeof n!="object")return ()=>n;if(Array.isArray(n)){let t=n.map(i=>C(i,e,o));return i=>t.map(s=>s(i))}if(m(n))return un(n,o);if(E(n))return an(n,e,o);if(A(n))return pn(n,e,o);if(T(n))return dn(n,e,o);if(g(n))return conditions.compile(n,o?{accessor:o}:void 0);if(y(n))return conditions.compile(n,o?{accessor:o}:void 0);if(z(n)){let t=n,i=Object.keys(t),s=i.map(r=>C(t[r],e,o));return r=>{let f={};for(let c=0;c<i.length;c++)f[i[c]]=s[c](r);return f}}return ()=>n}function q(n,e){return e?o=>e(n,o):O(n)}function un(n,e){return q(n.$,e)}function an(n,e,o){let t;if(typeof n.$if=="string"){let r=n.$if.startsWith("!")?n.$if.slice(1):n.$if,f=q(r,o);t=n.$if.startsWith("!")?u=>!f(u):u=>!!f(u);}else {let r=C(n.$if,e,o);t=f=>!!r(f);}let i=C(n.then,e,o),s=n.else!==void 0?C(n.else,e,o):()=>{};return r=>t(r)?i(r):s(r)}function pn(n,e,o){let t=n.$pipe;if(t.length===0)return ()=>{};if(t.length===1)return C(t[0],e,o);let i=C(t[0],e,o),s=t.slice(1).map(f=>C(f,e,o)),r=s.length;if(r===1){let[f]=s;return c=>{let u=i(c),a=f(c);return typeof a=="function"?a(u):a}}if(r===2){let[f,c]=s;return u=>{let a=i(u),p=f(u);return a=typeof p=="function"?p(a):p,p=c(u),typeof p=="function"?p(a):p}}if(r===3){let[f,c,u]=s;return a=>{let p=i(a),h=f(a);return p=typeof h=="function"?h(p):h,h=c(a),p=typeof h=="function"?h(p):h,h=u(a),typeof h=="function"?h(p):h}}return f=>{let c=i(f);for(let u=0;u<r;u++){let a=s[u](f);c=typeof a=="function"?a(c):a;}return c}}function dn(n,e,o){let t=n.$fn,i=n.args;if(i===void 0)return ()=>{let f=e[t];if(!f)throw new Error(`Function not found in scope: ${t}`);return f};let s=i.map(f=>C(f,e,o)),r=s.length;if(r===0)return f=>{let c=e[t];if(!c)throw new Error(`Function not found in scope: ${t}`);return c()};if(r===1){let[f]=s;return c=>{let u=e[t];if(!u)throw new Error(`Function not found in scope: ${t}`);return u(f(c))}}if(r===2){let[f,c]=s;return u=>{let a=e[t];if(!a)throw new Error(`Function not found in scope: ${t}`);return a(f(u),c(u))}}if(r===3){let[f,c,u]=s;return a=>{let p=e[t];if(!p)throw new Error(`Function not found in scope: ${t}`);return p(f(a),c(a),u(a))}}return f=>{let c=e[t];if(!c)throw new Error(`Function not found in scope: ${t}`);return c(...s.map(u=>u(f)))}}function mn(n,e,o={}){return F(n,o).fn(e)}var v=class{constructor(e=1e3){this.cache=new Map,this._maxSize=e;}get(e,o={}){let t=JSON.stringify(e),i=this.cache.get(t);if(i)return this.cache.delete(t),this.cache.set(t,i),i;let s=F(e,o);if(this.cache.size>=this._maxSize){let r=this.cache.keys().next().value;r&&this.cache.delete(r);}return this.cache.set(t,s),s}has(e){return this.cache.has(JSON.stringify(e))}delete(e){return this.cache.delete(JSON.stringify(e))}clear(){this.cache.clear();}get size(){return this.cache.size}get maxSize(){return this._maxSize}set maxSize(e){for(this._maxSize=e;this.cache.size>this._maxSize;){let o=this.cache.keys().next().value;o&&this.cache.delete(o);}}},J=new v;function gn(n,e={}){return J.get(n,e)}function P(n,e="root",o={}){let t=[];return $(n,e,t,o),{valid:t.length===0,errors:t}}function $(n,e,o,t){if(n===null||typeof n!="object")return;if(Array.isArray(n)){for(let r=0;r<n.length;r++)$(n[r],`${e}[${r}]`,o,t);return}if(m(n)){(!n.$||typeof n.$!="string")&&o.push(`${e}: invalid reference, $ must be non-empty string`);return}if(E(n)){typeof n.$if=="string"?(n.$if.startsWith("!")?n.$if.slice(1):n.$if)||o.push(`${e}.$if: empty path in string shorthand`):$(n.$if,`${e}.$if`,o,t),$(n.then,`${e}.then`,o,t),n.else!==void 0&&$(n.else,`${e}.else`,o,t);return}if(A(n)){if(!Array.isArray(n.$pipe)){o.push(`${e}.$pipe: must be an array`);return}if(n.$pipe.length===0){o.push(`${e}.$pipe: must have at least one element`);return}for(let r=0;r<n.$pipe.length;r++)$(n.$pipe[r],`${e}.$pipe[${r}]`,o,t);return}if(T(n)){if(!n.$fn||typeof n.$fn!="string"){o.push(`${e}: invalid function, $fn must be non-empty string`);return}if(t.scope&&!(n.$fn in t.scope)&&o.push(`${e}: function "${n.$fn}" not found in scope`),n.args!==void 0)if(!Array.isArray(n.args))o.push(`${e}.args: must be an array`);else for(let r=0;r<n.args.length;r++)$(n.args[r],`${e}.args[${r}]`,o,t);return}if(g(n)){let r=conditions.validate(n,e);r.valid||o.push(...r.errors);return}if(y(n)){let r=conditions.validate(n,e);r.valid||o.push(...r.errors);return}let i=n,s=Object.keys(i);for(let r=0;r<s.length;r++){let f=s[r];$(i[f],`${e}.${f}`,o,t);}}function yn(n,e={}){let o=P(n,"root",e);if(!o.valid)throw new Error(`Invalid expression: ${o.errors.join("; ")}`)}function hn(n,e={}){return P(n,"root",e).valid}var D="data",K="scope",En={eq:"===",neq:"!==",gt:">",gte:">=",lt:"<",lte:"<="};function j(n,e={}){let{dataParam:o=D,scopeParam:t=K,noPrefixes:i=false}=e;return d(n,o,t,i)}function d(n,e,o,t){if(n===null)return omniAst.builders.literal(null);if(typeof n=="string")return omniAst.builders.literal(n);if(typeof n=="number")return omniAst.builders.literal(n);if(typeof n=="boolean")return omniAst.builders.literal(n);if(Array.isArray(n))return omniAst.builders.arrayExpression(n.map(i=>d(i,e,o,t)));if(m(n))return Tn(n.$,e,t);if(E(n))return Cn(n,e,o,t);if(A(n))return Sn(n.$pipe,e,o,t);if(T(n))return bn(n,e,o,t);if(g(n))return $n(n,e,o,t);if(y(n))return kn(n,e,o,t);if(typeof n=="object"){let s=Object.entries(n).map(([r,f])=>omniAst.builders.property(omniAst.builders.identifier(r),d(f,e,o,t)));return omniAst.builders.objectExpression(s)}return omniAst.builders.literal(null)}function Tn(n,e,o){return n.includes("[*]")?An(n,e,o):x(n,e,o)}function x(n,e,o){let t=N(n);if(t.length===0)return o?omniAst.builders.identifier("undefined"):omniAst.builders.identifier(e);let i;if(o){let s=t[0];i=omniAst.builders.identifier(s.value);for(let r=1;r<t.length;r++){let f=t[r];f.type==="key"?i=omniAst.builders.memberExpression(i,omniAst.builders.identifier(f.value),false,true):i=omniAst.builders.memberExpression(i,omniAst.builders.literal(f.value),true,true);}}else {i=omniAst.builders.identifier(e);for(let s of t)s.type==="key"?i=omniAst.builders.memberExpression(i,omniAst.builders.identifier(s.value),false,true):i=omniAst.builders.memberExpression(i,omniAst.builders.literal(s.value),true,true);}return i}function An(n,e,o){let t=n.indexOf("[*]"),i=n.slice(0,t),s=n.slice(t+3),r;if(i?r=x(i,e,o):r=o?omniAst.builders.identifier("undefined"):omniAst.builders.identifier(e),!s||s==="")return r;if(s.includes("[*]"))return Y(r,s);let f="_i",c=s.startsWith(".")?s.slice(1):s,u=omniAst.builders.identifier(f);if(c){let a=N(c);for(let p of a)p.type==="key"?u=omniAst.builders.memberExpression(u,omniAst.builders.identifier(p.value),false,true):u=omniAst.builders.memberExpression(u,omniAst.builders.literal(p.value),true,true);}return omniAst.builders.callExpression(omniAst.builders.memberExpression(r,omniAst.builders.identifier("map"),false,true),[omniAst.builders.arrowFunctionExpression([omniAst.builders.identifier(f)],u)])}function Y(n,e){let o=e.indexOf("[*]"),t=e.slice(0,o),i=e.slice(o+3),s="_i",r=t.startsWith(".")?t.slice(1):t,f=omniAst.builders.identifier(s);if(r){let u=N(r);for(let a of u)a.type==="key"&&(f=omniAst.builders.memberExpression(f,omniAst.builders.identifier(a.value),false,true));}if(i.includes("[*]")){let u=Y(f,i);return omniAst.builders.callExpression(omniAst.builders.memberExpression(n,omniAst.builders.identifier("flatMap"),false,true),[omniAst.builders.arrowFunctionExpression([omniAst.builders.identifier(s)],u)])}let c=i.startsWith(".")?i.slice(1):i;if(c){let u=N(c);for(let a of u)a.type==="key"&&(f=omniAst.builders.memberExpression(f,omniAst.builders.identifier(a.value),false,true));}return omniAst.builders.callExpression(omniAst.builders.memberExpression(n,omniAst.builders.identifier("flatMap"),false,true),[omniAst.builders.arrowFunctionExpression([omniAst.builders.identifier(s)],f)])}function Cn(n,e,o,t){let i;if(typeof n.$if=="string"){let f=n.$if.startsWith("!"),c=f?n.$if.slice(1):n.$if,u=x(c,e,t);i=f?omniAst.builders.unaryExpression("!",u):u;}else i=d(n.$if,e,o,t);let s=d(n.then,e,o,t),r=n.else!==void 0?d(n.else,e,o,t):omniAst.builders.identifier("undefined");return omniAst.builders.conditionalExpression(i,s,r)}function bn(n,e,o,t){let i=t?omniAst.builders.identifier(n.$fn):omniAst.builders.memberExpression(omniAst.builders.identifier(o),omniAst.builders.identifier(n.$fn),false,false);if(n.args===void 0)return i;let s=n.args.map(r=>d(r,e,o,t));return omniAst.builders.callExpression(i,s)}function Sn(n,e,o,t){if(n.length===0)return omniAst.builders.identifier("undefined");if(n.length===1)return d(n[0],e,o,t);let i=d(n[0],e,o,t);for(let s=1;s<n.length;s++){let r=d(n[s],e,o,t);i=omniAst.builders.callExpression(r,[i]);}return i}function $n(n,e,o,t){let i=x(n.path,e,t),s=n.value!==void 0?m(n.value)?x(n.value.$,e,t):d(n.value,e,o,t):omniAst.builders.literal(null),r=En[n.op];if(r)return omniAst.builders.binaryExpression(r,i,s);switch(n.op){case "in":return omniAst.builders.callExpression(omniAst.builders.memberExpression(s,omniAst.builders.identifier("includes")),[i]);case "notIn":return omniAst.builders.unaryExpression("!",omniAst.builders.callExpression(omniAst.builders.memberExpression(s,omniAst.builders.identifier("includes")),[i]));case "contains":return omniAst.builders.callExpression(omniAst.builders.memberExpression(i,omniAst.builders.identifier("includes"),false,true),[s]);case "notContains":return omniAst.builders.unaryExpression("!",omniAst.builders.callExpression(omniAst.builders.memberExpression(i,omniAst.builders.identifier("includes"),false,true),[s]));case "exists":return omniAst.builders.binaryExpression("!=",i,omniAst.builders.literal(null));case "notExists":return omniAst.builders.binaryExpression("==",i,omniAst.builders.literal(null));case "matches":return omniAst.builders.callExpression(omniAst.builders.memberExpression(omniAst.builders.newExpression(omniAst.builders.identifier("RegExp"),[s]),omniAst.builders.identifier("test")),[i]);case "notMatches":return omniAst.builders.unaryExpression("!",omniAst.builders.callExpression(omniAst.builders.memberExpression(omniAst.builders.newExpression(omniAst.builders.identifier("RegExp"),[s]),omniAst.builders.identifier("test")),[i]));case "startsWith":return omniAst.builders.callExpression(omniAst.builders.memberExpression(i,omniAst.builders.identifier("startsWith"),false,true),[s]);case "endsWith":return omniAst.builders.callExpression(omniAst.builders.memberExpression(i,omniAst.builders.identifier("endsWith"),false,true),[s]);default:return omniAst.builders.binaryExpression("===",i,s)}}function kn(n,e,o,t){let{logic:i,conditions:s}=n,r=i==="AND"?"&&":"||";if(s.length===0)return omniAst.builders.literal(i==="AND");if(s.length===1)return d(s[0],e,o,t);let f=d(s[0],e,o,t);for(let c=1;c<s.length;c++){let u=d(s[c],e,o,t);f=omniAst.builders.logicalExpression(r,f,u);}return f}function N(n){let e=[],o=n.length,t=0,i="";for(;t<o;){let s=n[t];if(s===".")i&&(e.push({type:"key",value:i}),i=""),t++;else if(s==="["){i&&(e.push({type:"key",value:i}),i=""),t++;let r=t;for(;t<o&&n[t]!=="]";)t++;let f=n.slice(r,t);if(t++,f!=="*"){let c=parseInt(f,10);e.push({type:"index",value:isNaN(c)?f:c});}}else i+=s,t++;}return i&&e.push({type:"key",value:i}),e}function H(n,e=[D]){return omniAst.builders.arrowFunctionExpression(e.map(o=>omniAst.builders.identifier(o)),n)}function G(n){let e=new Set;return b(n,e),e}function b(n,e){if(n===null||typeof n!="object")return;if(Array.isArray(n)){for(let t of n)b(t,e);return}if(m(n))return;if(E(n)){b(n.$if,e),b(n.then,e),n.else!==void 0&&b(n.else,e);return}if(A(n)){for(let t of n.$pipe)b(t,e);return}if(T(n)){if(e.add(n.$fn),n.args)for(let t of n.args)b(t,e);return}if(g(n)){n.value!==void 0&&typeof n.value=="object"&&b(n.value,e);return}if(y(n)){for(let t of n.conditions)b(t,e);return}let o=n;for(let t of Object.keys(o))b(o[t],e);}function W(n){let e=new Set;for(let o of n){let t=o.indexOf("."),i=o.indexOf("["),s=o.length;t!==-1&&(s=Math.min(s,t)),i!==-1&&(s=Math.min(s,i));let r=o.slice(0,s);r&&e.add(r);}return e}function xn(n){return JSON.stringify(n)}function Rn(n,e,o){let t=j(n,{noPrefixes:true}),i=omniAst.generate(t),s=e.size>0?`const{${[...e].join(",")}}=data??{};`:"",r=o.size>0?`const{${[...o].join(",")}}=scope;`:"";return r?`(function(scope){${r}return function(data){${s}return ${i}}})`:`(function(){return function(data){${s}return ${i}}})`}function M(n,e={}){let{scope:o={},returnCode:t=false}=e,i=k(n),s=W(i),r=G(n),f=xn(n),c=Rn(n,s,r);if(t)return {code:c,deps:i,hash:f,dataRoots:[...s],scopeFns:[...r]};let u;try{u=new Function(`return ${c}`)()(o);}catch(a){throw new Error(`AST compilation failed. If this is due to CSP, use the standard compile() function instead. Error: ${a instanceof Error?a.message:String(a)}`)}return {fn:u,deps:i,hash:f}}function Q(n,e,o={}){let{fn:t}=M(n,o);return t(e)}var re="0.0.3";exports.ExpressionCache=v;exports.VERSION=re;exports.assertValid=yn;exports.cache=J;exports.cached=gn;exports.clearPathCache=on;exports.compile=F;exports.compileAST=M;exports.compilePath=O;exports.dslToAST=j;exports.evaluate=mn;exports.evaluateAST=Q;exports.extractDataRoots=W;exports.extractDeps=k;exports.extractScopeFns=G;exports.get=tn;exports.getPathCacheSize=rn;exports.hasDeps=ln;exports.hasWildcard=L;exports.isCondition=g;exports.isConditionExpr=U;exports.isConditionGroup=y;exports.isConditional=E;exports.isFn=T;exports.isLiteral=z;exports.isPipe=A;exports.isPure=fn;exports.isRef=m;exports.isValid=hn;exports.normalizePath=w;exports.validate=P;exports.wrapInFunction=H;
package/dist/index.d.cts CHANGED
@@ -71,6 +71,15 @@ interface CompiledExpression<T = unknown, R = unknown> {
71
71
  * Path getter function
72
72
  */
73
73
  type PathGetter<T = unknown> = (data: T) => unknown;
74
+ /**
75
+ * Accessor customizado para resolver paths
76
+ * Permite usar ctx.get(path) em vez de acesso direto por propriedade
77
+ *
78
+ * @example
79
+ * // Com TickContext
80
+ * const accessor: AccessorFn<TickContext> = (path, ctx) => ctx.get(path);
81
+ */
82
+ type AccessorFn<T = unknown> = (path: string, data: T) => unknown;
74
83
  /**
75
84
  * Validation result
76
85
  */
@@ -86,9 +95,18 @@ type Scope = Record<string, (...args: unknown[]) => unknown>;
86
95
  /**
87
96
  * Options for compilation
88
97
  */
89
- interface CompileOptions {
98
+ interface CompileOptions<T = unknown> {
90
99
  /** Functions available to $fn expressions */
91
100
  scope?: Scope;
101
+ /**
102
+ * Accessor customizado para resolver paths.
103
+ * Quando fornecido, substitui o acesso direto por propriedade.
104
+ *
105
+ * @example
106
+ * // Com TickContext
107
+ * compile(expr, { accessor: (path, ctx) => ctx.get(path) })
108
+ */
109
+ accessor?: AccessorFn<T>;
92
110
  }
93
111
  /**
94
112
  * Check if value is a reference expression
@@ -139,11 +157,12 @@ declare const isLiteral: (v: unknown) => v is Literal;
139
157
  * Compile expression to optimized function
140
158
  *
141
159
  * @param expr - Expression to compile
142
- * @param options - Compile options (scope with functions)
160
+ * @param options - Compile options (scope with functions, accessor)
143
161
  * @returns Compiled expression with fn, deps, and hash
144
162
  *
145
163
  * @example
146
164
  * ```ts
165
+ * // Uso padrão - acesso direto por propriedade
147
166
  * import { add, filter, sum } from '@statedelta-libs/operators';
148
167
  *
149
168
  * const { fn } = compile(
@@ -153,21 +172,40 @@ declare const isLiteral: (v: unknown) => v is Literal;
153
172
  *
154
173
  * fn({ a: 1, b: 2 }); // 3
155
174
  * ```
175
+ *
176
+ * @example
177
+ * ```ts
178
+ * // Com accessor customizado (ex: TickContext)
179
+ * const { fn } = compile(
180
+ * { $: "hp:value" },
181
+ * { accessor: (path, ctx) => ctx.get(path) }
182
+ * );
183
+ *
184
+ * fn(tickContext); // usa ctx.get('hp:value')
185
+ * ```
156
186
  */
157
- declare function compile<T = unknown, R = unknown>(expr: Expression, options?: CompileOptions): CompiledExpression<T, R>;
187
+ declare function compile<T = unknown, R = unknown>(expr: Expression, options?: CompileOptions<T>): CompiledExpression<T, R>;
158
188
  /**
159
189
  * Compile and execute in one step
160
190
  *
161
191
  * @example
162
192
  * ```ts
193
+ * // Uso padrão
163
194
  * evaluate(
164
195
  * { $fn: "add", args: [{ $: "a" }, { $: "b" }] },
165
196
  * { a: 1, b: 2 },
166
197
  * { scope: { add } }
167
198
  * ); // 3
199
+ *
200
+ * // Com accessor customizado
201
+ * evaluate(
202
+ * { $: "hp:value" },
203
+ * tickContext,
204
+ * { accessor: (path, ctx) => ctx.get(path) }
205
+ * );
168
206
  * ```
169
207
  */
170
- declare function evaluate<T = unknown, R = unknown>(expr: Expression, data: T, options?: CompileOptions): R;
208
+ declare function evaluate<T = unknown, R = unknown>(expr: Expression, data: T, options?: CompileOptions<T>): R;
171
209
 
172
210
  /**
173
211
  * @statedelta-libs/expressions - Path Compiler
@@ -506,6 +544,6 @@ declare function evaluateAST<T = unknown, R = unknown>(expr: Expression, data: T
506
544
  * ); // 3
507
545
  * ```
508
546
  */
509
- declare const VERSION = "0.0.1";
547
+ declare const VERSION = "0.0.3";
510
548
 
511
- export { type CompileASTCodeResult, type CompileASTOptions, type CompileOptions, type CompiledExpression, type CompiledFn, type ConditionalExpr, type Expression, ExpressionCache, type FnExpr, type Literal, type PathGetter, type PipeExpr, type RefExpr, type Scope, type TransformOptions, VERSION, type ValidateOptions, type ValidationResult, assertValid, cache, cached, clearPathCache, compile, compileAST, compilePath, dslToAST, evaluate, evaluateAST, extractDataRoots, extractDeps, extractScopeFns, get, getPathCacheSize, hasDeps, hasWildcard, isCondition, isConditionExpr, isConditionGroup, isConditional, isFn, isLiteral, isPipe, isPure, isRef, isValid, normalizePath, validate, wrapInFunction };
549
+ export { type AccessorFn, type CompileASTCodeResult, type CompileASTOptions, type CompileOptions, type CompiledExpression, type CompiledFn, type ConditionalExpr, type Expression, ExpressionCache, type FnExpr, type Literal, type PathGetter, type PipeExpr, type RefExpr, type Scope, type TransformOptions, VERSION, type ValidateOptions, type ValidationResult, assertValid, cache, cached, clearPathCache, compile, compileAST, compilePath, dslToAST, evaluate, evaluateAST, extractDataRoots, extractDeps, extractScopeFns, get, getPathCacheSize, hasDeps, hasWildcard, isCondition, isConditionExpr, isConditionGroup, isConditional, isFn, isLiteral, isPipe, isPure, isRef, isValid, normalizePath, validate, wrapInFunction };
package/dist/index.d.ts CHANGED
@@ -71,6 +71,15 @@ interface CompiledExpression<T = unknown, R = unknown> {
71
71
  * Path getter function
72
72
  */
73
73
  type PathGetter<T = unknown> = (data: T) => unknown;
74
+ /**
75
+ * Accessor customizado para resolver paths
76
+ * Permite usar ctx.get(path) em vez de acesso direto por propriedade
77
+ *
78
+ * @example
79
+ * // Com TickContext
80
+ * const accessor: AccessorFn<TickContext> = (path, ctx) => ctx.get(path);
81
+ */
82
+ type AccessorFn<T = unknown> = (path: string, data: T) => unknown;
74
83
  /**
75
84
  * Validation result
76
85
  */
@@ -86,9 +95,18 @@ type Scope = Record<string, (...args: unknown[]) => unknown>;
86
95
  /**
87
96
  * Options for compilation
88
97
  */
89
- interface CompileOptions {
98
+ interface CompileOptions<T = unknown> {
90
99
  /** Functions available to $fn expressions */
91
100
  scope?: Scope;
101
+ /**
102
+ * Accessor customizado para resolver paths.
103
+ * Quando fornecido, substitui o acesso direto por propriedade.
104
+ *
105
+ * @example
106
+ * // Com TickContext
107
+ * compile(expr, { accessor: (path, ctx) => ctx.get(path) })
108
+ */
109
+ accessor?: AccessorFn<T>;
92
110
  }
93
111
  /**
94
112
  * Check if value is a reference expression
@@ -139,11 +157,12 @@ declare const isLiteral: (v: unknown) => v is Literal;
139
157
  * Compile expression to optimized function
140
158
  *
141
159
  * @param expr - Expression to compile
142
- * @param options - Compile options (scope with functions)
160
+ * @param options - Compile options (scope with functions, accessor)
143
161
  * @returns Compiled expression with fn, deps, and hash
144
162
  *
145
163
  * @example
146
164
  * ```ts
165
+ * // Uso padrão - acesso direto por propriedade
147
166
  * import { add, filter, sum } from '@statedelta-libs/operators';
148
167
  *
149
168
  * const { fn } = compile(
@@ -153,21 +172,40 @@ declare const isLiteral: (v: unknown) => v is Literal;
153
172
  *
154
173
  * fn({ a: 1, b: 2 }); // 3
155
174
  * ```
175
+ *
176
+ * @example
177
+ * ```ts
178
+ * // Com accessor customizado (ex: TickContext)
179
+ * const { fn } = compile(
180
+ * { $: "hp:value" },
181
+ * { accessor: (path, ctx) => ctx.get(path) }
182
+ * );
183
+ *
184
+ * fn(tickContext); // usa ctx.get('hp:value')
185
+ * ```
156
186
  */
157
- declare function compile<T = unknown, R = unknown>(expr: Expression, options?: CompileOptions): CompiledExpression<T, R>;
187
+ declare function compile<T = unknown, R = unknown>(expr: Expression, options?: CompileOptions<T>): CompiledExpression<T, R>;
158
188
  /**
159
189
  * Compile and execute in one step
160
190
  *
161
191
  * @example
162
192
  * ```ts
193
+ * // Uso padrão
163
194
  * evaluate(
164
195
  * { $fn: "add", args: [{ $: "a" }, { $: "b" }] },
165
196
  * { a: 1, b: 2 },
166
197
  * { scope: { add } }
167
198
  * ); // 3
199
+ *
200
+ * // Com accessor customizado
201
+ * evaluate(
202
+ * { $: "hp:value" },
203
+ * tickContext,
204
+ * { accessor: (path, ctx) => ctx.get(path) }
205
+ * );
168
206
  * ```
169
207
  */
170
- declare function evaluate<T = unknown, R = unknown>(expr: Expression, data: T, options?: CompileOptions): R;
208
+ declare function evaluate<T = unknown, R = unknown>(expr: Expression, data: T, options?: CompileOptions<T>): R;
171
209
 
172
210
  /**
173
211
  * @statedelta-libs/expressions - Path Compiler
@@ -506,6 +544,6 @@ declare function evaluateAST<T = unknown, R = unknown>(expr: Expression, data: T
506
544
  * ); // 3
507
545
  * ```
508
546
  */
509
- declare const VERSION = "0.0.1";
547
+ declare const VERSION = "0.0.3";
510
548
 
511
- export { type CompileASTCodeResult, type CompileASTOptions, type CompileOptions, type CompiledExpression, type CompiledFn, type ConditionalExpr, type Expression, ExpressionCache, type FnExpr, type Literal, type PathGetter, type PipeExpr, type RefExpr, type Scope, type TransformOptions, VERSION, type ValidateOptions, type ValidationResult, assertValid, cache, cached, clearPathCache, compile, compileAST, compilePath, dslToAST, evaluate, evaluateAST, extractDataRoots, extractDeps, extractScopeFns, get, getPathCacheSize, hasDeps, hasWildcard, isCondition, isConditionExpr, isConditionGroup, isConditional, isFn, isLiteral, isPipe, isPure, isRef, isValid, normalizePath, validate, wrapInFunction };
549
+ export { type AccessorFn, type CompileASTCodeResult, type CompileASTOptions, type CompileOptions, type CompiledExpression, type CompiledFn, type ConditionalExpr, type Expression, ExpressionCache, type FnExpr, type Literal, type PathGetter, type PipeExpr, type RefExpr, type Scope, type TransformOptions, VERSION, type ValidateOptions, type ValidationResult, assertValid, cache, cached, clearPathCache, compile, compileAST, compilePath, dslToAST, evaluate, evaluateAST, extractDataRoots, extractDeps, extractScopeFns, get, getPathCacheSize, hasDeps, hasWildcard, isCondition, isConditionExpr, isConditionGroup, isConditional, isFn, isLiteral, isPipe, isPure, isRef, isValid, normalizePath, validate, wrapInFunction };
package/dist/index.js CHANGED
@@ -1 +1 @@
1
- import {isRef,compile,validate}from'@statedelta-libs/conditions';import {builders,generate}from'omni-ast';var m=n=>n!==null&&typeof n=="object"&&"$"in n&&typeof n.$=="string"&&Object.keys(n).length===1,h=n=>n!==null&&typeof n=="object"&&"$if"in n&&"then"in n,E=n=>n!==null&&typeof n=="object"&&"$fn"in n&&typeof n.$fn=="string",C=n=>n!==null&&typeof n=="object"&&"$pipe"in n&&Array.isArray(n.$pipe),M=new Set(["eq","neq","gt","gte","lt","lte","in","notIn","contains","notContains","exists","notExists","matches","notMatches","startsWith","endsWith"]),g=n=>n!==null&&typeof n=="object"&&"path"in n&&"op"in n&&M.has(n.op)&&!("$"in n)&&!("$if"in n)&&!("$fn"in n),y=n=>n!==null&&typeof n=="object"&&"logic"in n&&"conditions"in n,H=n=>g(n)||y(n),W=n=>{if(n===null)return true;let e=typeof n;if(e==="string"||e==="number"||e==="boolean"||Array.isArray(n))return true;if(e==="object"&&n!==null){let t=n,o="path"in t&&"op"in t&&M.has(t.op);return !("$"in t)&&!("$if"in t)&&!("$fn"in t)&&!("$pipe"in t)&&!o&&!("logic"in t)}return false};var R=new Map;function I(n){let e=[],t=n.length,o=0,i="";for(;o<t;){let s=n[o];if(s===".")i&&(e.push({type:"key",value:i}),i=""),o++;else if(s==="["){i&&(e.push({type:"key",value:i}),i=""),o++;let r=o;for(;o<t&&n[o]!=="]";)o++;let c=n.slice(r,o);if(o++,c==="*")e.push({type:"wildcard",value:"*"});else {let f=parseInt(c,10);e.push({type:"index",value:isNaN(f)?c:f});}}else i+=s,o++;}return i&&e.push({type:"key",value:i}),e}function V(n){return n.includes("[*]")}function x(n){let e=R.get(n);return e||(e=V(n)?U(n):Q(n),R.set(n,e),e)}function Q(n){if(!n.includes(".")&&!n.includes("["))return i=>i?.[n];let e=I(n),t=e.length;if(t===2){let[i,s]=e,r=i.value,c=s.value;return f=>f?.[r]?.[c]}if(t===3){let[i,s,r]=e,c=i.value,f=s.value,a=r.value;return u=>u?.[c]?.[f]?.[a]}let o=e.map(i=>i.value);return i=>{let s=i;for(let r=0;r<t&&s!=null;r++)s=s[o[r]];return s}}function U(n){let e=I(n),t=[];for(let o=0;o<e.length;o++)e[o].type==="wildcard"&&t.push(o);return t.length===1?X(e,t[0]):Z(e,t)}function X(n,e){let t=n.slice(0,e).map(r=>r.value),o=n.slice(e+1).map(r=>r.value),i=t.length,s=o.length;if(s===0){if(i===1){let r=t[0];return c=>c?.[r]}return r=>{let c=r;for(let f=0;f<i&&c!=null;f++)c=c[t[f]];return c}}if(s===1){let r=o[0];if(i===1){let c=t[0];return f=>{let a=f?.[c];if(Array.isArray(a))return a.map(u=>u?.[r])}}return c=>{let f=c;for(let a=0;a<i&&f!=null;a++)f=f[t[a]];if(Array.isArray(f))return f.map(a=>a?.[r])}}return r=>{let c=r;for(let f=0;f<i&&c!=null;f++)c=c[t[f]];if(Array.isArray(c))return c.map(f=>{let a=f;for(let u=0;u<s&&a!=null;u++)a=a[o[u]];return a})}}function Z(n,e){let t=[],o=0;for(let s=0;s<e.length;s++){let r=e[s],c=s===e.length-1,f=n.slice(o,r).map(a=>a.value);f.length>0&&t.push({type:"access",keys:f}),t.push({type:c?"map":"flatMap",keys:[]}),o=r+1;}let i=n.slice(o).map(s=>s.value);return s=>{let r=s;for(let c of t){if(r==null)return;if(c.type==="access")for(let f of c.keys){if(r==null)return;r=r[f];}else if(c.type==="flatMap"){if(!Array.isArray(r))return;r=r.flatMap(f=>{let a=f;return Array.isArray(a)?a:[a]});}else if(c.type==="map"){if(!Array.isArray(r))return;i.length>0&&(r=r.map(f=>{let a=f;for(let u of i){if(a==null)return;a=a[u];}return a}));}}return r}}function nn(n,e){return x(e)(n)}function k(n){let e=n.indexOf("[*]");return e===-1?n:n.slice(0,e)}function en(){R.clear();}function tn(){return R.size}function T(n){let e=new Set;return A(n,e),Array.from(e)}function A(n,e){if(n===null||typeof n!="object")return;if(Array.isArray(n)){for(let i=0;i<n.length;i++)A(n[i],e);return}if(m(n)){e.add(k(n.$));return}if(h(n)){if(typeof n.$if=="string"){let i=n.$if.startsWith("!")?n.$if.slice(1):n.$if;e.add(k(i));}else A(n.$if,e);A(n.then,e),n.else!==void 0&&A(n.else,e);return}if(C(n)){for(let i=0;i<n.$pipe.length;i++)A(n.$pipe[i],e);return}if(E(n)){if(n.args)for(let i=0;i<n.args.length;i++)A(n.args[i],e);return}if(g(n)){e.add(k(n.path)),n.value!==void 0&&isRef(n.value)&&e.add(k(n.value.$));return}if(y(n)){for(let i=0;i<n.conditions.length;i++)A(n.conditions[i],e);return}let t=n,o=Object.keys(t);for(let i=0;i<o.length;i++)A(t[o[i]],e);}function rn(n){return T(n).length>0}function sn(n){return T(n).length===0}function ln(n){return JSON.stringify(n)}function O(n,e={}){let t=e.scope??{},o=b(n,t),i=T(n),s=ln(n);return {fn:o,deps:i,hash:s}}function b(n,e){if(n===null)return ()=>null;if(typeof n!="object")return ()=>n;if(Array.isArray(n)){let t=n.map(o=>b(o,e));return o=>t.map(i=>i(o))}if(m(n))return cn(n);if(h(n))return fn(n,e);if(C(n))return an(n,e);if(E(n))return un(n,e);if(g(n))return compile(n);if(y(n))return compile(n);if(W(n)){let t=n,o=Object.keys(t),i=o.map(s=>b(t[s],e));return s=>{let r={};for(let c=0;c<o.length;c++)r[o[c]]=i[c](s);return r}}return ()=>n}function cn(n){return x(n.$)}function fn(n,e){let t;if(typeof n.$if=="string"){let s=n.$if.startsWith("!")?n.$if.slice(1):n.$if,r=x(s);t=n.$if.startsWith("!")?f=>!r(f):f=>!!r(f);}else {let s=b(n.$if,e);t=r=>!!s(r);}let o=b(n.then,e),i=n.else!==void 0?b(n.else,e):()=>{};return s=>t(s)?o(s):i(s)}function an(n,e){let t=n.$pipe;if(t.length===0)return ()=>{};if(t.length===1)return b(t[0],e);let o=b(t[0],e),i=t.slice(1).map(r=>b(r,e)),s=i.length;if(s===1){let[r]=i;return c=>{let f=o(c),a=r(c);return typeof a=="function"?a(f):a}}if(s===2){let[r,c]=i;return f=>{let a=o(f),u=r(f);return a=typeof u=="function"?u(a):u,u=c(f),typeof u=="function"?u(a):u}}if(s===3){let[r,c,f]=i;return a=>{let u=o(a),p=r(a);return u=typeof p=="function"?p(u):p,p=c(a),u=typeof p=="function"?p(u):p,p=f(a),typeof p=="function"?p(u):p}}return r=>{let c=o(r);for(let f=0;f<s;f++){let a=i[f](r);c=typeof a=="function"?a(c):a;}return c}}function un(n,e){let t=n.$fn,o=n.args;if(o===void 0)return ()=>{let r=e[t];if(!r)throw new Error(`Function not found in scope: ${t}`);return r};let i=o.map(r=>b(r,e)),s=i.length;if(s===0)return r=>{let c=e[t];if(!c)throw new Error(`Function not found in scope: ${t}`);return c()};if(s===1){let[r]=i;return c=>{let f=e[t];if(!f)throw new Error(`Function not found in scope: ${t}`);return f(r(c))}}if(s===2){let[r,c]=i;return f=>{let a=e[t];if(!a)throw new Error(`Function not found in scope: ${t}`);return a(r(f),c(f))}}if(s===3){let[r,c,f]=i;return a=>{let u=e[t];if(!u)throw new Error(`Function not found in scope: ${t}`);return u(r(a),c(a),f(a))}}return r=>{let c=e[t];if(!c)throw new Error(`Function not found in scope: ${t}`);return c(...i.map(f=>f(r)))}}function pn(n,e,t={}){return O(n,t).fn(e)}var v=class{constructor(e=1e3){this.cache=new Map,this._maxSize=e;}get(e,t={}){let o=JSON.stringify(e),i=this.cache.get(o);if(i)return this.cache.delete(o),this.cache.set(o,i),i;let s=O(e,t);if(this.cache.size>=this._maxSize){let r=this.cache.keys().next().value;r&&this.cache.delete(r);}return this.cache.set(o,s),s}has(e){return this.cache.has(JSON.stringify(e))}delete(e){return this.cache.delete(JSON.stringify(e))}clear(){this.cache.clear();}get size(){return this.cache.size}get maxSize(){return this._maxSize}set maxSize(e){for(this._maxSize=e;this.cache.size>this._maxSize;){let t=this.cache.keys().next().value;t&&this.cache.delete(t);}}},_=new v;function dn(n,e={}){return _.get(n,e)}function z(n,e="root",t={}){let o=[];return $(n,e,o,t),{valid:o.length===0,errors:o}}function $(n,e,t,o){if(n===null||typeof n!="object")return;if(Array.isArray(n)){for(let r=0;r<n.length;r++)$(n[r],`${e}[${r}]`,t,o);return}if(m(n)){(!n.$||typeof n.$!="string")&&t.push(`${e}: invalid reference, $ must be non-empty string`);return}if(h(n)){typeof n.$if=="string"?(n.$if.startsWith("!")?n.$if.slice(1):n.$if)||t.push(`${e}.$if: empty path in string shorthand`):$(n.$if,`${e}.$if`,t,o),$(n.then,`${e}.then`,t,o),n.else!==void 0&&$(n.else,`${e}.else`,t,o);return}if(C(n)){if(!Array.isArray(n.$pipe)){t.push(`${e}.$pipe: must be an array`);return}if(n.$pipe.length===0){t.push(`${e}.$pipe: must have at least one element`);return}for(let r=0;r<n.$pipe.length;r++)$(n.$pipe[r],`${e}.$pipe[${r}]`,t,o);return}if(E(n)){if(!n.$fn||typeof n.$fn!="string"){t.push(`${e}: invalid function, $fn must be non-empty string`);return}if(o.scope&&!(n.$fn in o.scope)&&t.push(`${e}: function "${n.$fn}" not found in scope`),n.args!==void 0)if(!Array.isArray(n.args))t.push(`${e}.args: must be an array`);else for(let r=0;r<n.args.length;r++)$(n.args[r],`${e}.args[${r}]`,t,o);return}if(g(n)){let r=validate(n,e);r.valid||t.push(...r.errors);return}if(y(n)){let r=validate(n,e);r.valid||t.push(...r.errors);return}let i=n,s=Object.keys(i);for(let r=0;r<s.length;r++){let c=s[r];$(i[c],`${e}.${c}`,t,o);}}function mn(n,e={}){let t=z(n,"root",e);if(!t.valid)throw new Error(`Invalid expression: ${t.errors.join("; ")}`)}function gn(n,e={}){return z(n,"root",e).valid}var P="data",J="scope",yn={eq:"===",neq:"!==",gt:">",gte:">=",lt:"<",lte:"<="};function N(n,e={}){let{dataParam:t=P,scopeParam:o=J,noPrefixes:i=false}=e;return d(n,t,o,i)}function d(n,e,t,o){if(n===null)return builders.literal(null);if(typeof n=="string")return builders.literal(n);if(typeof n=="number")return builders.literal(n);if(typeof n=="boolean")return builders.literal(n);if(Array.isArray(n))return builders.arrayExpression(n.map(i=>d(i,e,t,o)));if(m(n))return hn(n.$,e,o);if(h(n))return Cn(n,e,t,o);if(C(n))return Sn(n.$pipe,e,t,o);if(E(n))return bn(n,e,t,o);if(g(n))return An(n,e,t,o);if(y(n))return $n(n,e,t,o);if(typeof n=="object"){let s=Object.entries(n).map(([r,c])=>builders.property(builders.identifier(r),d(c,e,t,o)));return builders.objectExpression(s)}return builders.literal(null)}function hn(n,e,t){return n.includes("[*]")?En(n,e,t):w(n,e,t)}function w(n,e,t){let o=F(n);if(o.length===0)return t?builders.identifier("undefined"):builders.identifier(e);let i;if(t){let s=o[0];i=builders.identifier(s.value);for(let r=1;r<o.length;r++){let c=o[r];c.type==="key"?i=builders.memberExpression(i,builders.identifier(c.value),false,true):i=builders.memberExpression(i,builders.literal(c.value),true,true);}}else {i=builders.identifier(e);for(let s of o)s.type==="key"?i=builders.memberExpression(i,builders.identifier(s.value),false,true):i=builders.memberExpression(i,builders.literal(s.value),true,true);}return i}function En(n,e,t){let o=n.indexOf("[*]"),i=n.slice(0,o),s=n.slice(o+3),r;if(i?r=w(i,e,t):r=t?builders.identifier("undefined"):builders.identifier(e),!s||s==="")return r;if(s.includes("[*]"))return B(r,s);let c="_i",f=s.startsWith(".")?s.slice(1):s,a=builders.identifier(c);if(f){let u=F(f);for(let p of u)p.type==="key"?a=builders.memberExpression(a,builders.identifier(p.value),false,true):a=builders.memberExpression(a,builders.literal(p.value),true,true);}return builders.callExpression(builders.memberExpression(r,builders.identifier("map"),false,true),[builders.arrowFunctionExpression([builders.identifier(c)],a)])}function B(n,e){let t=e.indexOf("[*]"),o=e.slice(0,t),i=e.slice(t+3),s="_i",r=o.startsWith(".")?o.slice(1):o,c=builders.identifier(s);if(r){let a=F(r);for(let u of a)u.type==="key"&&(c=builders.memberExpression(c,builders.identifier(u.value),false,true));}if(i.includes("[*]")){let a=B(c,i);return builders.callExpression(builders.memberExpression(n,builders.identifier("flatMap"),false,true),[builders.arrowFunctionExpression([builders.identifier(s)],a)])}let f=i.startsWith(".")?i.slice(1):i;if(f){let a=F(f);for(let u of a)u.type==="key"&&(c=builders.memberExpression(c,builders.identifier(u.value),false,true));}return builders.callExpression(builders.memberExpression(n,builders.identifier("flatMap"),false,true),[builders.arrowFunctionExpression([builders.identifier(s)],c)])}function Cn(n,e,t,o){let i;if(typeof n.$if=="string"){let c=n.$if.startsWith("!"),f=c?n.$if.slice(1):n.$if,a=w(f,e,o);i=c?builders.unaryExpression("!",a):a;}else i=d(n.$if,e,t,o);let s=d(n.then,e,t,o),r=n.else!==void 0?d(n.else,e,t,o):builders.identifier("undefined");return builders.conditionalExpression(i,s,r)}function bn(n,e,t,o){let i=o?builders.identifier(n.$fn):builders.memberExpression(builders.identifier(t),builders.identifier(n.$fn),false,false);if(n.args===void 0)return i;let s=n.args.map(r=>d(r,e,t,o));return builders.callExpression(i,s)}function Sn(n,e,t,o){if(n.length===0)return builders.identifier("undefined");if(n.length===1)return d(n[0],e,t,o);let i=d(n[0],e,t,o);for(let s=1;s<n.length;s++){let r=d(n[s],e,t,o);i=builders.callExpression(r,[i]);}return i}function An(n,e,t,o){let i=w(n.path,e,o),s=n.value!==void 0?m(n.value)?w(n.value.$,e,o):d(n.value,e,t,o):builders.literal(null),r=yn[n.op];if(r)return builders.binaryExpression(r,i,s);switch(n.op){case "in":return builders.callExpression(builders.memberExpression(s,builders.identifier("includes")),[i]);case "notIn":return builders.unaryExpression("!",builders.callExpression(builders.memberExpression(s,builders.identifier("includes")),[i]));case "contains":return builders.callExpression(builders.memberExpression(i,builders.identifier("includes"),false,true),[s]);case "notContains":return builders.unaryExpression("!",builders.callExpression(builders.memberExpression(i,builders.identifier("includes"),false,true),[s]));case "exists":return builders.binaryExpression("!=",i,builders.literal(null));case "notExists":return builders.binaryExpression("==",i,builders.literal(null));case "matches":return builders.callExpression(builders.memberExpression(builders.newExpression(builders.identifier("RegExp"),[s]),builders.identifier("test")),[i]);case "notMatches":return builders.unaryExpression("!",builders.callExpression(builders.memberExpression(builders.newExpression(builders.identifier("RegExp"),[s]),builders.identifier("test")),[i]));case "startsWith":return builders.callExpression(builders.memberExpression(i,builders.identifier("startsWith"),false,true),[s]);case "endsWith":return builders.callExpression(builders.memberExpression(i,builders.identifier("endsWith"),false,true),[s]);default:return builders.binaryExpression("===",i,s)}}function $n(n,e,t,o){let{logic:i,conditions:s}=n,r=i==="AND"?"&&":"||";if(s.length===0)return builders.literal(i==="AND");if(s.length===1)return d(s[0],e,t,o);let c=d(s[0],e,t,o);for(let f=1;f<s.length;f++){let a=d(s[f],e,t,o);c=builders.logicalExpression(r,c,a);}return c}function F(n){let e=[],t=n.length,o=0,i="";for(;o<t;){let s=n[o];if(s===".")i&&(e.push({type:"key",value:i}),i=""),o++;else if(s==="["){i&&(e.push({type:"key",value:i}),i=""),o++;let r=o;for(;o<t&&n[o]!=="]";)o++;let c=n.slice(r,o);if(o++,c!=="*"){let f=parseInt(c,10);e.push({type:"index",value:isNaN(f)?c:f});}}else i+=s,o++;}return i&&e.push({type:"key",value:i}),e}function K(n,e=[P]){return builders.arrowFunctionExpression(e.map(t=>builders.identifier(t)),n)}function j(n){let e=new Set;return S(n,e),e}function S(n,e){if(n===null||typeof n!="object")return;if(Array.isArray(n)){for(let o of n)S(o,e);return}if(m(n))return;if(h(n)){S(n.$if,e),S(n.then,e),n.else!==void 0&&S(n.else,e);return}if(C(n)){for(let o of n.$pipe)S(o,e);return}if(E(n)){if(e.add(n.$fn),n.args)for(let o of n.args)S(o,e);return}if(g(n)){n.value!==void 0&&typeof n.value=="object"&&S(n.value,e);return}if(y(n)){for(let o of n.conditions)S(o,e);return}let t=n;for(let o of Object.keys(t))S(t[o],e);}function G(n){let e=new Set;for(let t of n){let o=t.indexOf("."),i=t.indexOf("["),s=t.length;o!==-1&&(s=Math.min(s,o)),i!==-1&&(s=Math.min(s,i));let r=t.slice(0,s);r&&e.add(r);}return e}function kn(n){return JSON.stringify(n)}function xn(n,e,t){let o=N(n,{noPrefixes:true}),i=generate(o),s=e.size>0?`const{${[...e].join(",")}}=data??{};`:"",r=t.size>0?`const{${[...t].join(",")}}=scope;`:"";return r?`(function(scope){${r}return function(data){${s}return ${i}}})`:`(function(){return function(data){${s}return ${i}}})`}function D(n,e={}){let{scope:t={},returnCode:o=false}=e,i=T(n),s=G(i),r=j(n),c=kn(n),f=xn(n,s,r);if(o)return {code:f,deps:i,hash:c,dataRoots:[...s],scopeFns:[...r]};let a;try{a=new Function(`return ${f}`)()(t);}catch(u){throw new Error(`AST compilation failed. If this is due to CSP, use the standard compile() function instead. Error: ${u instanceof Error?u.message:String(u)}`)}return {fn:a,deps:i,hash:c}}function Y(n,e,t={}){let{fn:o}=D(n,t);return o(e)}var ie="0.0.1";export{v as ExpressionCache,ie as VERSION,mn as assertValid,_ as cache,dn as cached,en as clearPathCache,O as compile,D as compileAST,x as compilePath,N as dslToAST,pn as evaluate,Y as evaluateAST,G as extractDataRoots,T as extractDeps,j as extractScopeFns,nn as get,tn as getPathCacheSize,rn as hasDeps,V as hasWildcard,g as isCondition,H as isConditionExpr,y as isConditionGroup,h as isConditional,E as isFn,W as isLiteral,C as isPipe,sn as isPure,m as isRef,gn as isValid,k as normalizePath,z as validate,K as wrapInFunction};
1
+ import {isRef,compile,validate}from'@statedelta-libs/conditions';import {builders,generate}from'omni-ast';var m=n=>n!==null&&typeof n=="object"&&"$"in n&&typeof n.$=="string"&&Object.keys(n).length===1,E=n=>n!==null&&typeof n=="object"&&"$if"in n&&"then"in n,T=n=>n!==null&&typeof n=="object"&&"$fn"in n&&typeof n.$fn=="string",A=n=>n!==null&&typeof n=="object"&&"$pipe"in n&&Array.isArray(n.$pipe),I=new Set(["eq","neq","gt","gte","lt","lte","in","notIn","contains","notContains","exists","notExists","matches","notMatches","startsWith","endsWith"]),g=n=>n!==null&&typeof n=="object"&&"path"in n&&"op"in n&&I.has(n.op)&&!("$"in n)&&!("$if"in n)&&!("$fn"in n),y=n=>n!==null&&typeof n=="object"&&"logic"in n&&"conditions"in n,U=n=>g(n)||y(n),z=n=>{if(n===null)return true;let e=typeof n;if(e==="string"||e==="number"||e==="boolean"||Array.isArray(n))return true;if(e==="object"&&n!==null){let o=n,t="path"in o&&"op"in o&&I.has(o.op);return !("$"in o)&&!("$if"in o)&&!("$fn"in o)&&!("$pipe"in o)&&!t&&!("logic"in o)}return false};var R=new Map;function V(n){let e=[],o=n.length,t=0,i="";for(;t<o;){let s=n[t];if(s===".")i&&(e.push({type:"key",value:i}),i=""),t++;else if(s==="["){i&&(e.push({type:"key",value:i}),i=""),t++;let r=t;for(;t<o&&n[t]!=="]";)t++;let f=n.slice(r,t);if(t++,f==="*")e.push({type:"wildcard",value:"*"});else {let c=parseInt(f,10);e.push({type:"index",value:isNaN(c)?f:c});}}else i+=s,t++;}return i&&e.push({type:"key",value:i}),e}function L(n){return n.includes("[*]")}function O(n){let e=R.get(n);return e||(e=L(n)?Z(n):X(n),R.set(n,e),e)}function X(n){if(!n.includes(".")&&!n.includes("["))return i=>i?.[n];let e=V(n),o=e.length;if(o===2){let[i,s]=e,r=i.value,f=s.value;return c=>c?.[r]?.[f]}if(o===3){let[i,s,r]=e,f=i.value,c=s.value,u=r.value;return a=>a?.[f]?.[c]?.[u]}let t=e.map(i=>i.value);return i=>{let s=i;for(let r=0;r<o&&s!=null;r++)s=s[t[r]];return s}}function Z(n){let e=V(n),o=[];for(let t=0;t<e.length;t++)e[t].type==="wildcard"&&o.push(t);return o.length===1?nn(e,o[0]):en(e,o)}function nn(n,e){let o=n.slice(0,e).map(r=>r.value),t=n.slice(e+1).map(r=>r.value),i=o.length,s=t.length;if(s===0){if(i===1){let r=o[0];return f=>f?.[r]}return r=>{let f=r;for(let c=0;c<i&&f!=null;c++)f=f[o[c]];return f}}if(s===1){let r=t[0];if(i===1){let f=o[0];return c=>{let u=c?.[f];if(Array.isArray(u))return u.map(a=>a?.[r])}}return f=>{let c=f;for(let u=0;u<i&&c!=null;u++)c=c[o[u]];if(Array.isArray(c))return c.map(u=>u?.[r])}}return r=>{let f=r;for(let c=0;c<i&&f!=null;c++)f=f[o[c]];if(Array.isArray(f))return f.map(c=>{let u=c;for(let a=0;a<s&&u!=null;a++)u=u[t[a]];return u})}}function en(n,e){let o=[],t=0;for(let s=0;s<e.length;s++){let r=e[s],f=s===e.length-1,c=n.slice(t,r).map(u=>u.value);c.length>0&&o.push({type:"access",keys:c}),o.push({type:f?"map":"flatMap",keys:[]}),t=r+1;}let i=n.slice(t).map(s=>s.value);return s=>{let r=s;for(let f of o){if(r==null)return;if(f.type==="access")for(let c of f.keys){if(r==null)return;r=r[c];}else if(f.type==="flatMap"){if(!Array.isArray(r))return;r=r.flatMap(c=>{let u=c;return Array.isArray(u)?u:[u]});}else if(f.type==="map"){if(!Array.isArray(r))return;i.length>0&&(r=r.map(c=>{let u=c;for(let a of i){if(u==null)return;u=u[a];}return u}));}}return r}}function tn(n,e){return O(e)(n)}function w(n){let e=n.indexOf("[*]");return e===-1?n:n.slice(0,e)}function on(){R.clear();}function rn(){return R.size}function k(n){let e=new Set;return S(n,e),Array.from(e)}function S(n,e){if(n===null||typeof n!="object")return;if(Array.isArray(n)){for(let i=0;i<n.length;i++)S(n[i],e);return}if(m(n)){e.add(w(n.$));return}if(E(n)){if(typeof n.$if=="string"){let i=n.$if.startsWith("!")?n.$if.slice(1):n.$if;e.add(w(i));}else S(n.$if,e);S(n.then,e),n.else!==void 0&&S(n.else,e);return}if(A(n)){for(let i=0;i<n.$pipe.length;i++)S(n.$pipe[i],e);return}if(T(n)){if(n.args)for(let i=0;i<n.args.length;i++)S(n.args[i],e);return}if(g(n)){e.add(w(n.path)),n.value!==void 0&&isRef(n.value)&&e.add(w(n.value.$));return}if(y(n)){for(let i=0;i<n.conditions.length;i++)S(n.conditions[i],e);return}let o=n,t=Object.keys(o);for(let i=0;i<t.length;i++)S(o[t[i]],e);}function ln(n){return k(n).length>0}function fn(n){return k(n).length===0}function cn(n){return JSON.stringify(n)}function F(n,e={}){let o=e.scope??{},t=e.accessor,i=C(n,o,t),s=k(n),r=cn(n);return {fn:i,deps:s,hash:r}}function C(n,e,o){if(n===null)return ()=>null;if(typeof n!="object")return ()=>n;if(Array.isArray(n)){let t=n.map(i=>C(i,e,o));return i=>t.map(s=>s(i))}if(m(n))return un(n,o);if(E(n))return an(n,e,o);if(A(n))return pn(n,e,o);if(T(n))return dn(n,e,o);if(g(n))return compile(n,o?{accessor:o}:void 0);if(y(n))return compile(n,o?{accessor:o}:void 0);if(z(n)){let t=n,i=Object.keys(t),s=i.map(r=>C(t[r],e,o));return r=>{let f={};for(let c=0;c<i.length;c++)f[i[c]]=s[c](r);return f}}return ()=>n}function q(n,e){return e?o=>e(n,o):O(n)}function un(n,e){return q(n.$,e)}function an(n,e,o){let t;if(typeof n.$if=="string"){let r=n.$if.startsWith("!")?n.$if.slice(1):n.$if,f=q(r,o);t=n.$if.startsWith("!")?u=>!f(u):u=>!!f(u);}else {let r=C(n.$if,e,o);t=f=>!!r(f);}let i=C(n.then,e,o),s=n.else!==void 0?C(n.else,e,o):()=>{};return r=>t(r)?i(r):s(r)}function pn(n,e,o){let t=n.$pipe;if(t.length===0)return ()=>{};if(t.length===1)return C(t[0],e,o);let i=C(t[0],e,o),s=t.slice(1).map(f=>C(f,e,o)),r=s.length;if(r===1){let[f]=s;return c=>{let u=i(c),a=f(c);return typeof a=="function"?a(u):a}}if(r===2){let[f,c]=s;return u=>{let a=i(u),p=f(u);return a=typeof p=="function"?p(a):p,p=c(u),typeof p=="function"?p(a):p}}if(r===3){let[f,c,u]=s;return a=>{let p=i(a),h=f(a);return p=typeof h=="function"?h(p):h,h=c(a),p=typeof h=="function"?h(p):h,h=u(a),typeof h=="function"?h(p):h}}return f=>{let c=i(f);for(let u=0;u<r;u++){let a=s[u](f);c=typeof a=="function"?a(c):a;}return c}}function dn(n,e,o){let t=n.$fn,i=n.args;if(i===void 0)return ()=>{let f=e[t];if(!f)throw new Error(`Function not found in scope: ${t}`);return f};let s=i.map(f=>C(f,e,o)),r=s.length;if(r===0)return f=>{let c=e[t];if(!c)throw new Error(`Function not found in scope: ${t}`);return c()};if(r===1){let[f]=s;return c=>{let u=e[t];if(!u)throw new Error(`Function not found in scope: ${t}`);return u(f(c))}}if(r===2){let[f,c]=s;return u=>{let a=e[t];if(!a)throw new Error(`Function not found in scope: ${t}`);return a(f(u),c(u))}}if(r===3){let[f,c,u]=s;return a=>{let p=e[t];if(!p)throw new Error(`Function not found in scope: ${t}`);return p(f(a),c(a),u(a))}}return f=>{let c=e[t];if(!c)throw new Error(`Function not found in scope: ${t}`);return c(...s.map(u=>u(f)))}}function mn(n,e,o={}){return F(n,o).fn(e)}var v=class{constructor(e=1e3){this.cache=new Map,this._maxSize=e;}get(e,o={}){let t=JSON.stringify(e),i=this.cache.get(t);if(i)return this.cache.delete(t),this.cache.set(t,i),i;let s=F(e,o);if(this.cache.size>=this._maxSize){let r=this.cache.keys().next().value;r&&this.cache.delete(r);}return this.cache.set(t,s),s}has(e){return this.cache.has(JSON.stringify(e))}delete(e){return this.cache.delete(JSON.stringify(e))}clear(){this.cache.clear();}get size(){return this.cache.size}get maxSize(){return this._maxSize}set maxSize(e){for(this._maxSize=e;this.cache.size>this._maxSize;){let o=this.cache.keys().next().value;o&&this.cache.delete(o);}}},J=new v;function gn(n,e={}){return J.get(n,e)}function P(n,e="root",o={}){let t=[];return $(n,e,t,o),{valid:t.length===0,errors:t}}function $(n,e,o,t){if(n===null||typeof n!="object")return;if(Array.isArray(n)){for(let r=0;r<n.length;r++)$(n[r],`${e}[${r}]`,o,t);return}if(m(n)){(!n.$||typeof n.$!="string")&&o.push(`${e}: invalid reference, $ must be non-empty string`);return}if(E(n)){typeof n.$if=="string"?(n.$if.startsWith("!")?n.$if.slice(1):n.$if)||o.push(`${e}.$if: empty path in string shorthand`):$(n.$if,`${e}.$if`,o,t),$(n.then,`${e}.then`,o,t),n.else!==void 0&&$(n.else,`${e}.else`,o,t);return}if(A(n)){if(!Array.isArray(n.$pipe)){o.push(`${e}.$pipe: must be an array`);return}if(n.$pipe.length===0){o.push(`${e}.$pipe: must have at least one element`);return}for(let r=0;r<n.$pipe.length;r++)$(n.$pipe[r],`${e}.$pipe[${r}]`,o,t);return}if(T(n)){if(!n.$fn||typeof n.$fn!="string"){o.push(`${e}: invalid function, $fn must be non-empty string`);return}if(t.scope&&!(n.$fn in t.scope)&&o.push(`${e}: function "${n.$fn}" not found in scope`),n.args!==void 0)if(!Array.isArray(n.args))o.push(`${e}.args: must be an array`);else for(let r=0;r<n.args.length;r++)$(n.args[r],`${e}.args[${r}]`,o,t);return}if(g(n)){let r=validate(n,e);r.valid||o.push(...r.errors);return}if(y(n)){let r=validate(n,e);r.valid||o.push(...r.errors);return}let i=n,s=Object.keys(i);for(let r=0;r<s.length;r++){let f=s[r];$(i[f],`${e}.${f}`,o,t);}}function yn(n,e={}){let o=P(n,"root",e);if(!o.valid)throw new Error(`Invalid expression: ${o.errors.join("; ")}`)}function hn(n,e={}){return P(n,"root",e).valid}var D="data",K="scope",En={eq:"===",neq:"!==",gt:">",gte:">=",lt:"<",lte:"<="};function j(n,e={}){let{dataParam:o=D,scopeParam:t=K,noPrefixes:i=false}=e;return d(n,o,t,i)}function d(n,e,o,t){if(n===null)return builders.literal(null);if(typeof n=="string")return builders.literal(n);if(typeof n=="number")return builders.literal(n);if(typeof n=="boolean")return builders.literal(n);if(Array.isArray(n))return builders.arrayExpression(n.map(i=>d(i,e,o,t)));if(m(n))return Tn(n.$,e,t);if(E(n))return Cn(n,e,o,t);if(A(n))return Sn(n.$pipe,e,o,t);if(T(n))return bn(n,e,o,t);if(g(n))return $n(n,e,o,t);if(y(n))return kn(n,e,o,t);if(typeof n=="object"){let s=Object.entries(n).map(([r,f])=>builders.property(builders.identifier(r),d(f,e,o,t)));return builders.objectExpression(s)}return builders.literal(null)}function Tn(n,e,o){return n.includes("[*]")?An(n,e,o):x(n,e,o)}function x(n,e,o){let t=N(n);if(t.length===0)return o?builders.identifier("undefined"):builders.identifier(e);let i;if(o){let s=t[0];i=builders.identifier(s.value);for(let r=1;r<t.length;r++){let f=t[r];f.type==="key"?i=builders.memberExpression(i,builders.identifier(f.value),false,true):i=builders.memberExpression(i,builders.literal(f.value),true,true);}}else {i=builders.identifier(e);for(let s of t)s.type==="key"?i=builders.memberExpression(i,builders.identifier(s.value),false,true):i=builders.memberExpression(i,builders.literal(s.value),true,true);}return i}function An(n,e,o){let t=n.indexOf("[*]"),i=n.slice(0,t),s=n.slice(t+3),r;if(i?r=x(i,e,o):r=o?builders.identifier("undefined"):builders.identifier(e),!s||s==="")return r;if(s.includes("[*]"))return Y(r,s);let f="_i",c=s.startsWith(".")?s.slice(1):s,u=builders.identifier(f);if(c){let a=N(c);for(let p of a)p.type==="key"?u=builders.memberExpression(u,builders.identifier(p.value),false,true):u=builders.memberExpression(u,builders.literal(p.value),true,true);}return builders.callExpression(builders.memberExpression(r,builders.identifier("map"),false,true),[builders.arrowFunctionExpression([builders.identifier(f)],u)])}function Y(n,e){let o=e.indexOf("[*]"),t=e.slice(0,o),i=e.slice(o+3),s="_i",r=t.startsWith(".")?t.slice(1):t,f=builders.identifier(s);if(r){let u=N(r);for(let a of u)a.type==="key"&&(f=builders.memberExpression(f,builders.identifier(a.value),false,true));}if(i.includes("[*]")){let u=Y(f,i);return builders.callExpression(builders.memberExpression(n,builders.identifier("flatMap"),false,true),[builders.arrowFunctionExpression([builders.identifier(s)],u)])}let c=i.startsWith(".")?i.slice(1):i;if(c){let u=N(c);for(let a of u)a.type==="key"&&(f=builders.memberExpression(f,builders.identifier(a.value),false,true));}return builders.callExpression(builders.memberExpression(n,builders.identifier("flatMap"),false,true),[builders.arrowFunctionExpression([builders.identifier(s)],f)])}function Cn(n,e,o,t){let i;if(typeof n.$if=="string"){let f=n.$if.startsWith("!"),c=f?n.$if.slice(1):n.$if,u=x(c,e,t);i=f?builders.unaryExpression("!",u):u;}else i=d(n.$if,e,o,t);let s=d(n.then,e,o,t),r=n.else!==void 0?d(n.else,e,o,t):builders.identifier("undefined");return builders.conditionalExpression(i,s,r)}function bn(n,e,o,t){let i=t?builders.identifier(n.$fn):builders.memberExpression(builders.identifier(o),builders.identifier(n.$fn),false,false);if(n.args===void 0)return i;let s=n.args.map(r=>d(r,e,o,t));return builders.callExpression(i,s)}function Sn(n,e,o,t){if(n.length===0)return builders.identifier("undefined");if(n.length===1)return d(n[0],e,o,t);let i=d(n[0],e,o,t);for(let s=1;s<n.length;s++){let r=d(n[s],e,o,t);i=builders.callExpression(r,[i]);}return i}function $n(n,e,o,t){let i=x(n.path,e,t),s=n.value!==void 0?m(n.value)?x(n.value.$,e,t):d(n.value,e,o,t):builders.literal(null),r=En[n.op];if(r)return builders.binaryExpression(r,i,s);switch(n.op){case "in":return builders.callExpression(builders.memberExpression(s,builders.identifier("includes")),[i]);case "notIn":return builders.unaryExpression("!",builders.callExpression(builders.memberExpression(s,builders.identifier("includes")),[i]));case "contains":return builders.callExpression(builders.memberExpression(i,builders.identifier("includes"),false,true),[s]);case "notContains":return builders.unaryExpression("!",builders.callExpression(builders.memberExpression(i,builders.identifier("includes"),false,true),[s]));case "exists":return builders.binaryExpression("!=",i,builders.literal(null));case "notExists":return builders.binaryExpression("==",i,builders.literal(null));case "matches":return builders.callExpression(builders.memberExpression(builders.newExpression(builders.identifier("RegExp"),[s]),builders.identifier("test")),[i]);case "notMatches":return builders.unaryExpression("!",builders.callExpression(builders.memberExpression(builders.newExpression(builders.identifier("RegExp"),[s]),builders.identifier("test")),[i]));case "startsWith":return builders.callExpression(builders.memberExpression(i,builders.identifier("startsWith"),false,true),[s]);case "endsWith":return builders.callExpression(builders.memberExpression(i,builders.identifier("endsWith"),false,true),[s]);default:return builders.binaryExpression("===",i,s)}}function kn(n,e,o,t){let{logic:i,conditions:s}=n,r=i==="AND"?"&&":"||";if(s.length===0)return builders.literal(i==="AND");if(s.length===1)return d(s[0],e,o,t);let f=d(s[0],e,o,t);for(let c=1;c<s.length;c++){let u=d(s[c],e,o,t);f=builders.logicalExpression(r,f,u);}return f}function N(n){let e=[],o=n.length,t=0,i="";for(;t<o;){let s=n[t];if(s===".")i&&(e.push({type:"key",value:i}),i=""),t++;else if(s==="["){i&&(e.push({type:"key",value:i}),i=""),t++;let r=t;for(;t<o&&n[t]!=="]";)t++;let f=n.slice(r,t);if(t++,f!=="*"){let c=parseInt(f,10);e.push({type:"index",value:isNaN(c)?f:c});}}else i+=s,t++;}return i&&e.push({type:"key",value:i}),e}function H(n,e=[D]){return builders.arrowFunctionExpression(e.map(o=>builders.identifier(o)),n)}function G(n){let e=new Set;return b(n,e),e}function b(n,e){if(n===null||typeof n!="object")return;if(Array.isArray(n)){for(let t of n)b(t,e);return}if(m(n))return;if(E(n)){b(n.$if,e),b(n.then,e),n.else!==void 0&&b(n.else,e);return}if(A(n)){for(let t of n.$pipe)b(t,e);return}if(T(n)){if(e.add(n.$fn),n.args)for(let t of n.args)b(t,e);return}if(g(n)){n.value!==void 0&&typeof n.value=="object"&&b(n.value,e);return}if(y(n)){for(let t of n.conditions)b(t,e);return}let o=n;for(let t of Object.keys(o))b(o[t],e);}function W(n){let e=new Set;for(let o of n){let t=o.indexOf("."),i=o.indexOf("["),s=o.length;t!==-1&&(s=Math.min(s,t)),i!==-1&&(s=Math.min(s,i));let r=o.slice(0,s);r&&e.add(r);}return e}function xn(n){return JSON.stringify(n)}function Rn(n,e,o){let t=j(n,{noPrefixes:true}),i=generate(t),s=e.size>0?`const{${[...e].join(",")}}=data??{};`:"",r=o.size>0?`const{${[...o].join(",")}}=scope;`:"";return r?`(function(scope){${r}return function(data){${s}return ${i}}})`:`(function(){return function(data){${s}return ${i}}})`}function M(n,e={}){let{scope:o={},returnCode:t=false}=e,i=k(n),s=W(i),r=G(n),f=xn(n),c=Rn(n,s,r);if(t)return {code:c,deps:i,hash:f,dataRoots:[...s],scopeFns:[...r]};let u;try{u=new Function(`return ${c}`)()(o);}catch(a){throw new Error(`AST compilation failed. If this is due to CSP, use the standard compile() function instead. Error: ${a instanceof Error?a.message:String(a)}`)}return {fn:u,deps:i,hash:f}}function Q(n,e,o={}){let{fn:t}=M(n,o);return t(e)}var re="0.0.3";export{v as ExpressionCache,re as VERSION,yn as assertValid,J as cache,gn as cached,on as clearPathCache,F as compile,M as compileAST,O as compilePath,j as dslToAST,mn as evaluate,Q as evaluateAST,W as extractDataRoots,k as extractDeps,G as extractScopeFns,tn as get,rn as getPathCacheSize,ln as hasDeps,L as hasWildcard,g as isCondition,U as isConditionExpr,y as isConditionGroup,E as isConditional,T as isFn,z as isLiteral,A as isPipe,fn as isPure,m as isRef,hn as isValid,w as normalizePath,P as validate,H as wrapInFunction};
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@statedelta-libs/expressions",
3
- "version": "0.0.2",
3
+ "version": "0.0.3",
4
4
  "description": "JSON DSL compiler for optimized functions - StateDelta expression engine",
5
5
  "type": "module",
6
6
  "main": "./dist/index.cjs",
@@ -15,7 +15,7 @@
15
15
  },
16
16
  "dependencies": {
17
17
  "omni-ast": "^2.0.0",
18
- "@statedelta-libs/conditions": "^0.0.1"
18
+ "@statedelta-libs/conditions": "^0.1.0"
19
19
  },
20
20
  "files": [
21
21
  "dist",
@@ -44,6 +44,9 @@
44
44
  "publishConfig": {
45
45
  "access": "public"
46
46
  },
47
+ "devDependencies": {
48
+ "@vitest/coverage-v8": "^4.0.16"
49
+ },
47
50
  "scripts": {
48
51
  "build": "tsup",
49
52
  "dev": "tsup --watch",