@jbrowse/jexl 4.0.1 → 5.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (110) hide show
  1. package/README.md +163 -20
  2. package/dist/Expression.d.ts +16 -0
  3. package/dist/Expression.js +28 -4
  4. package/dist/Expression.js.map +1 -1
  5. package/dist/Jexl.d.ts +20 -8
  6. package/dist/Jexl.js +34 -15
  7. package/dist/Jexl.js.map +1 -1
  8. package/dist/Lexer.d.ts +4 -3
  9. package/dist/Lexer.js +29 -21
  10. package/dist/Lexer.js.map +1 -1
  11. package/dist/analyze.d.ts +84 -0
  12. package/dist/analyze.js +259 -0
  13. package/dist/analyze.js.map +1 -0
  14. package/dist/check.d.ts +109 -0
  15. package/dist/check.js +1267 -0
  16. package/dist/check.js.map +1 -0
  17. package/dist/collections.d.ts +3 -0
  18. package/dist/collections.js +140 -0
  19. package/dist/collections.js.map +1 -0
  20. package/dist/conditions.d.ts +62 -0
  21. package/dist/conditions.js +207 -0
  22. package/dist/conditions.js.map +1 -0
  23. package/dist/errors.d.ts +5 -0
  24. package/dist/errors.js +18 -0
  25. package/dist/errors.js.map +1 -0
  26. package/dist/evaluator/compile.d.ts +10 -7
  27. package/dist/evaluator/compile.js +292 -99
  28. package/dist/evaluator/compile.js.map +1 -1
  29. package/dist/grammar.d.ts +22 -9
  30. package/dist/grammar.js +83 -55
  31. package/dist/grammar.js.map +1 -1
  32. package/dist/index.d.ts +9 -0
  33. package/dist/index.js +16 -1
  34. package/dist/index.js.map +1 -1
  35. package/dist/operators.d.ts +34 -0
  36. package/dist/operators.js +131 -0
  37. package/dist/operators.js.map +1 -0
  38. package/dist/parser/Parser.d.ts +48 -91
  39. package/dist/parser/Parser.js +347 -221
  40. package/dist/parser/Parser.js.map +1 -1
  41. package/dist/types.d.ts +11 -5
  42. package/esm/Expression.d.ts +16 -0
  43. package/esm/Expression.js +28 -4
  44. package/esm/Expression.js.map +1 -1
  45. package/esm/Jexl.d.ts +20 -8
  46. package/esm/Jexl.js +34 -15
  47. package/esm/Jexl.js.map +1 -1
  48. package/esm/Lexer.d.ts +4 -3
  49. package/esm/Lexer.js +29 -21
  50. package/esm/Lexer.js.map +1 -1
  51. package/esm/analyze.d.ts +84 -0
  52. package/esm/analyze.js +256 -0
  53. package/esm/analyze.js.map +1 -0
  54. package/esm/check.d.ts +109 -0
  55. package/esm/check.js +1260 -0
  56. package/esm/check.js.map +1 -0
  57. package/esm/collections.d.ts +3 -0
  58. package/esm/collections.js +137 -0
  59. package/esm/collections.js.map +1 -0
  60. package/esm/conditions.d.ts +62 -0
  61. package/esm/conditions.js +200 -0
  62. package/esm/conditions.js.map +1 -0
  63. package/esm/errors.d.ts +5 -0
  64. package/esm/errors.js +14 -0
  65. package/esm/errors.js.map +1 -0
  66. package/esm/evaluator/compile.d.ts +10 -7
  67. package/esm/evaluator/compile.js +292 -99
  68. package/esm/evaluator/compile.js.map +1 -1
  69. package/esm/grammar.d.ts +22 -9
  70. package/esm/grammar.js +79 -53
  71. package/esm/grammar.js.map +1 -1
  72. package/esm/index.d.ts +9 -0
  73. package/esm/index.js +4 -0
  74. package/esm/index.js.map +1 -1
  75. package/esm/operators.d.ts +34 -0
  76. package/esm/operators.js +123 -0
  77. package/esm/operators.js.map +1 -0
  78. package/esm/parser/Parser.d.ts +48 -91
  79. package/esm/parser/Parser.js +349 -192
  80. package/esm/parser/Parser.js.map +1 -1
  81. package/esm/types.d.ts +11 -5
  82. package/package.json +1 -1
  83. package/src/Expression.ts +34 -4
  84. package/src/Jexl.ts +52 -16
  85. package/src/Lexer.ts +32 -21
  86. package/src/analyze.ts +378 -0
  87. package/src/check.ts +1682 -0
  88. package/src/collections.ts +148 -0
  89. package/src/conditions.ts +262 -0
  90. package/src/errors.ts +15 -0
  91. package/src/evaluator/compile.ts +351 -102
  92. package/src/grammar.ts +137 -55
  93. package/src/index.ts +15 -0
  94. package/src/operators.ts +151 -0
  95. package/src/parser/Parser.ts +389 -199
  96. package/src/types.ts +13 -3
  97. package/dist/parser/handlers.d.ts +0 -115
  98. package/dist/parser/handlers.js +0 -352
  99. package/dist/parser/handlers.js.map +0 -1
  100. package/dist/parser/states.d.ts +0 -47
  101. package/dist/parser/states.js +0 -176
  102. package/dist/parser/states.js.map +0 -1
  103. package/esm/parser/handlers.d.ts +0 -115
  104. package/esm/parser/handlers.js +0 -328
  105. package/esm/parser/handlers.js.map +0 -1
  106. package/esm/parser/states.d.ts +0 -47
  107. package/esm/parser/states.js +0 -140
  108. package/esm/parser/states.js.map +0 -1
  109. package/src/parser/handlers.ts +0 -372
  110. package/src/parser/states.ts +0 -159
package/esm/grammar.js CHANGED
@@ -2,15 +2,35 @@
2
2
  * Jexl
3
3
  * Copyright 2020 Tom Shawver
4
4
  */
5
- /**
6
- * Returns the binding power of a grammar element, or 0 for elements that
7
- * aren't operators and therefore don't participate in precedence.
8
- */
9
- export function precedenceOf(elem) {
10
- return elem && (elem.type === 'binaryOp' || elem.type === 'unaryOp')
11
- ? elem.precedence
12
- : 0;
13
- }
5
+ /* eslint eqeqeq:0 */
6
+ import { collectionFunctions } from "./collections.js";
7
+ import { addsPairwise, anyPair, isIn, isList, matches, pairwise } from "./operators.js";
8
+ const plus = (left, right) => left + right;
9
+ const minus = (left, right) => left - right;
10
+ const times = (left, right) => left * right;
11
+ const divide = (left, right) => left / right;
12
+ const floorDivide = (left, right) => Math.floor(left / right);
13
+ const modulo = (left, right) => left % right;
14
+ const power = (left, right) => left ** right;
15
+ const loose = (left, right) => left == right;
16
+ // a missing value orders against nothing, as bcftools skips one; JavaScript
17
+ // alone would read null as 0, making [null, 0.2] < 0.05 true
18
+ const greater = (left, right) => left != null && right != null && left > right;
19
+ const atLeast = (left, right) => left != null && right != null && left >= right;
20
+ const less = (left, right) => left != null && right != null && left < right;
21
+ const atMost = (left, right) => left != null && right != null && left <= right;
22
+ // named so the compiler can recognize the built-in forms and short-circuit
23
+ // without the thunks a host's evalOnDemand operator is handed
24
+ export const and = (left, right) => {
25
+ const leftVal = left.eval();
26
+ return leftVal ? right.eval() : leftVal;
27
+ };
28
+ export const or = (left, right) => {
29
+ const leftVal = left.eval();
30
+ return leftVal || right.eval();
31
+ };
32
+ export const nullish = (left, right) => left.eval() ?? right.eval();
33
+ const equals = (left, right) => isList(left, right) ? anyPair(loose, left, right) : left == right;
14
34
  export const getGrammar = () => ({
15
35
  /**
16
36
  * A map of all expression elements to their properties. Note that changes
@@ -29,111 +49,117 @@ export const getGrammar = () => ({
29
49
  ')': { type: 'closeParen' },
30
50
  '?': { type: 'question' },
31
51
  ';': { type: 'semicolon' },
52
+ '=>': { type: 'arrow' },
32
53
  '+': {
33
54
  type: 'binaryOp',
34
55
  precedence: 30,
35
- eval: (left, right) => left + right
56
+ eval: (left, right) => addsPairwise(left, right)
57
+ ? pairwise(plus, left, right)
58
+ : plus(left, right)
36
59
  },
37
60
  '-': {
38
61
  type: 'binaryOp',
39
62
  precedence: 30,
40
- eval: (left, right) => left - right,
41
- unaryEval: (right) => -right
63
+ eval: (left, right) => isList(left, right) ? pairwise(minus, left, right) : minus(left, right),
64
+ unaryEval: (right) => Array.isArray(right)
65
+ ? right.map((value) => -value)
66
+ : -right
42
67
  },
43
68
  '*': {
44
69
  type: 'binaryOp',
45
70
  precedence: 40,
46
- eval: (left, right) => left * right
71
+ eval: (left, right) => isList(left, right) ? pairwise(times, left, right) : times(left, right)
47
72
  },
48
73
  '/': {
49
74
  type: 'binaryOp',
50
75
  precedence: 40,
51
- eval: (left, right) => left / right
76
+ eval: (left, right) => isList(left, right)
77
+ ? pairwise(divide, left, right)
78
+ : divide(left, right)
52
79
  },
53
80
  '//': {
54
81
  type: 'binaryOp',
55
82
  precedence: 40,
56
- eval: (left, right) => Math.floor(left / right)
83
+ eval: (left, right) => isList(left, right)
84
+ ? pairwise(floorDivide, left, right)
85
+ : floorDivide(left, right)
57
86
  },
58
87
  '%': {
59
88
  type: 'binaryOp',
60
89
  precedence: 50,
61
- eval: (left, right) => left % right
90
+ eval: (left, right) => isList(left, right)
91
+ ? pairwise(modulo, left, right)
92
+ : modulo(left, right)
62
93
  },
63
94
  '^': {
64
95
  type: 'binaryOp',
65
96
  precedence: 50,
66
- eval: (left, right) => left ** right
97
+ rightAssociative: true,
98
+ eval: (left, right) => isList(left, right) ? pairwise(power, left, right) : power(left, right)
67
99
  },
68
100
  '==': {
69
101
  type: 'binaryOp',
70
102
  precedence: 20,
71
- eval: (left, right) => left == right
103
+ eval: equals
72
104
  },
73
105
  '!=': {
74
106
  type: 'binaryOp',
75
107
  precedence: 20,
76
- eval: (left, right) => left != right
108
+ eval: (left, right) => !equals(left, right)
109
+ },
110
+ '~': {
111
+ type: 'binaryOp',
112
+ precedence: 20,
113
+ eval: matches
114
+ },
115
+ '!~': {
116
+ type: 'binaryOp',
117
+ precedence: 20,
118
+ eval: (left, right) => !matches(left, right)
77
119
  },
78
120
  '>': {
79
121
  type: 'binaryOp',
80
122
  precedence: 20,
81
- eval: (left, right) => left > right
123
+ eval: (left, right) => isList(left, right)
124
+ ? anyPair(greater, left, right)
125
+ : greater(left, right)
82
126
  },
83
127
  '>=': {
84
128
  type: 'binaryOp',
85
129
  precedence: 20,
86
- eval: (left, right) => left >= right
130
+ eval: (left, right) => isList(left, right)
131
+ ? anyPair(atLeast, left, right)
132
+ : atLeast(left, right)
87
133
  },
88
134
  '<': {
89
135
  type: 'binaryOp',
90
136
  precedence: 20,
91
- eval: (left, right) => left < right
137
+ eval: (left, right) => isList(left, right) ? anyPair(less, left, right) : less(left, right)
92
138
  },
93
139
  '<=': {
94
140
  type: 'binaryOp',
95
141
  precedence: 20,
96
- eval: (left, right) => left <= right
142
+ eval: (left, right) => isList(left, right) ? anyPair(atMost, left, right) : atMost(left, right)
97
143
  },
98
144
  '&&': {
99
145
  type: 'binaryOp',
100
- precedence: 10,
101
- evalOnDemand: (left, right) => {
102
- const leftVal = left.eval();
103
- if (!leftVal) {
104
- return leftVal;
105
- }
106
- return right.eval();
107
- }
146
+ precedence: 11,
147
+ evalOnDemand: and
108
148
  },
109
149
  '||': {
110
150
  type: 'binaryOp',
111
151
  precedence: 10,
112
- evalOnDemand: (left, right) => {
113
- const leftVal = left.eval();
114
- if (leftVal) {
115
- return leftVal;
116
- }
117
- return right.eval();
118
- }
152
+ evalOnDemand: or
153
+ },
154
+ '??': {
155
+ type: 'binaryOp',
156
+ precedence: 10,
157
+ evalOnDemand: nullish
119
158
  },
120
159
  in: {
121
160
  type: 'binaryOp',
122
161
  precedence: 20,
123
- eval: (left, right) => {
124
- if (typeof right === 'string') {
125
- // only a primitive has a meaningful substring form. An absent or
126
- // structured left operand is not "in" a string, and must not be
127
- // coerced to '' — every string contains the empty string, so that
128
- // made `feature.missingAttr in "someString"` true for every feature.
129
- return typeof left === 'string' ||
130
- typeof left === 'number' ||
131
- typeof left === 'boolean'
132
- ? right.includes(String(left))
133
- : false;
134
- }
135
- return Array.isArray(right) ? right.includes(left) : false;
136
- }
162
+ eval: isIn
137
163
  },
138
164
  '!': {
139
165
  type: 'unaryOp',
@@ -162,6 +188,6 @@ export const getGrammar = () => ({
162
188
  * than throw. An error is only appropriate when the function would normally
163
189
  * return a value, but cannot due to some other failure.
164
190
  */
165
- functions: {}
191
+ functions: { ...collectionFunctions }
166
192
  });
167
193
  //# sourceMappingURL=grammar.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"grammar.js","sourceRoot":"","sources":["../src/grammar.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAgFH;;;GAGG;AACH,MAAM,UAAU,YAAY,CAAC,IAAgC;IAC3D,OAAO,IAAI,IAAI,CAAC,IAAI,CAAC,IAAI,KAAK,UAAU,IAAI,IAAI,CAAC,IAAI,KAAK,SAAS,CAAC;QAClE,CAAC,CAAC,IAAI,CAAC,UAAU;QACjB,CAAC,CAAC,CAAC,CAAA;AACP,CAAC;AAED,MAAM,CAAC,MAAM,UAAU,GAAG,GAAY,EAAE,CAAC,CAAC;IACxC;;;;OAIG;IACH,QAAQ,EAAE;QACR,GAAG,EAAE,EAAE,IAAI,EAAE,KAAK,EAAE;QACpB,GAAG,EAAE,EAAE,IAAI,EAAE,aAAa,EAAE;QAC5B,GAAG,EAAE,EAAE,IAAI,EAAE,cAAc,EAAE;QAC7B,GAAG,EAAE,EAAE,IAAI,EAAE,UAAU,EAAE;QACzB,GAAG,EAAE,EAAE,IAAI,EAAE,WAAW,EAAE;QAC1B,GAAG,EAAE,EAAE,IAAI,EAAE,OAAO,EAAE;QACtB,GAAG,EAAE,EAAE,IAAI,EAAE,OAAO,EAAE;QACtB,GAAG,EAAE,EAAE,IAAI,EAAE,WAAW,EAAE;QAC1B,GAAG,EAAE,EAAE,IAAI,EAAE,YAAY,EAAE;QAC3B,GAAG,EAAE,EAAE,IAAI,EAAE,UAAU,EAAE;QACzB,GAAG,EAAE,EAAE,IAAI,EAAE,WAAW,EAAE;QAC1B,GAAG,EAAE;YACH,IAAI,EAAE,UAAU;YAChB,UAAU,EAAE,EAAE;YACd,IAAI,EAAE,CAAC,IAAI,EAAE,KAAK,EAAE,EAAE,CAAE,IAAe,GAAI,KAAgB;SAC5D;QACD,GAAG,EAAE;YACH,IAAI,EAAE,UAAU;YAChB,UAAU,EAAE,EAAE;YACd,IAAI,EAAE,CAAC,IAAI,EAAE,KAAK,EAAE,EAAE,CAAE,IAAe,GAAI,KAAgB;YAC3D,SAAS,EAAE,CAAC,KAAK,EAAE,EAAE,CAAC,CAAE,KAAgB;SACzC;QACD,GAAG,EAAE;YACH,IAAI,EAAE,UAAU;YAChB,UAAU,EAAE,EAAE;YACd,IAAI,EAAE,CAAC,IAAI,EAAE,KAAK,EAAE,EAAE,CAAE,IAAe,GAAI,KAAgB;SAC5D;QACD,GAAG,EAAE;YACH,IAAI,EAAE,UAAU;YAChB,UAAU,EAAE,EAAE;YACd,IAAI,EAAE,CAAC,IAAI,EAAE,KAAK,EAAE,EAAE,CAAE,IAAe,GAAI,KAAgB;SAC5D;QACD,IAAI,EAAE;YACJ,IAAI,EAAE,UAAU;YAChB,UAAU,EAAE,EAAE;YACd,IAAI,EAAE,CAAC,IAAI,EAAE,KAAK,EAAE,EAAE,CAAC,IAAI,CAAC,KAAK,CAAE,IAAe,GAAI,KAAgB,CAAC;SACxE;QACD,GAAG,EAAE;YACH,IAAI,EAAE,UAAU;YAChB,UAAU,EAAE,EAAE;YACd,IAAI,EAAE,CAAC,IAAI,EAAE,KAAK,EAAE,EAAE,CAAE,IAAe,GAAI,KAAgB;SAC5D;QACD,GAAG,EAAE;YACH,IAAI,EAAE,UAAU;YAChB,UAAU,EAAE,EAAE;YACd,IAAI,EAAE,CAAC,IAAI,EAAE,KAAK,EAAE,EAAE,CAAE,IAAe,IAAK,KAAgB;SAC7D;QACD,IAAI,EAAE;YACJ,IAAI,EAAE,UAAU;YAChB,UAAU,EAAE,EAAE;YACd,IAAI,EAAE,CAAC,IAAI,EAAE,KAAK,EAAE,EAAE,CAAC,IAAI,IAAI,KAAK;SACrC;QACD,IAAI,EAAE;YACJ,IAAI,EAAE,UAAU;YAChB,UAAU,EAAE,EAAE;YACd,IAAI,EAAE,CAAC,IAAI,EAAE,KAAK,EAAE,EAAE,CAAC,IAAI,IAAI,KAAK;SACrC;QACD,GAAG,EAAE;YACH,IAAI,EAAE,UAAU;YAChB,UAAU,EAAE,EAAE;YACd,IAAI,EAAE,CAAC,IAAI,EAAE,KAAK,EAAE,EAAE,CAAE,IAAe,GAAI,KAAgB;SAC5D;QACD,IAAI,EAAE;YACJ,IAAI,EAAE,UAAU;YAChB,UAAU,EAAE,EAAE;YACd,IAAI,EAAE,CAAC,IAAI,EAAE,KAAK,EAAE,EAAE,CAAE,IAAe,IAAK,KAAgB;SAC7D;QACD,GAAG,EAAE;YACH,IAAI,EAAE,UAAU;YAChB,UAAU,EAAE,EAAE;YACd,IAAI,EAAE,CAAC,IAAI,EAAE,KAAK,EAAE,EAAE,CAAE,IAAe,GAAI,KAAgB;SAC5D;QACD,IAAI,EAAE;YACJ,IAAI,EAAE,UAAU;YAChB,UAAU,EAAE,EAAE;YACd,IAAI,EAAE,CAAC,IAAI,EAAE,KAAK,EAAE,EAAE,CAAE,IAAe,IAAK,KAAgB;SAC7D;QACD,IAAI,EAAE;YACJ,IAAI,EAAE,UAAU;YAChB,UAAU,EAAE,EAAE;YACd,YAAY,EAAE,CAAC,IAAI,EAAE,KAAK,EAAE,EAAE;gBAC5B,MAAM,OAAO,GAAG,IAAI,CAAC,IAAI,EAAE,CAAA;gBAC3B,IAAI,CAAC,OAAO,EAAE,CAAC;oBACb,OAAO,OAAO,CAAA;gBAChB,CAAC;gBACD,OAAO,KAAK,CAAC,IAAI,EAAE,CAAA;YACrB,CAAC;SACF;QACD,IAAI,EAAE;YACJ,IAAI,EAAE,UAAU;YAChB,UAAU,EAAE,EAAE;YACd,YAAY,EAAE,CAAC,IAAI,EAAE,KAAK,EAAE,EAAE;gBAC5B,MAAM,OAAO,GAAG,IAAI,CAAC,IAAI,EAAE,CAAA;gBAC3B,IAAI,OAAO,EAAE,CAAC;oBACZ,OAAO,OAAO,CAAA;gBAChB,CAAC;gBACD,OAAO,KAAK,CAAC,IAAI,EAAE,CAAA;YACrB,CAAC;SACF;QACD,EAAE,EAAE;YACF,IAAI,EAAE,UAAU;YAChB,UAAU,EAAE,EAAE;YACd,IAAI,EAAE,CAAC,IAAI,EAAE,KAAK,EAAE,EAAE;gBACpB,IAAI,OAAO,KAAK,KAAK,QAAQ,EAAE,CAAC;oBAC9B,iEAAiE;oBACjE,gEAAgE;oBAChE,kEAAkE;oBAClE,qEAAqE;oBACrE,OAAO,OAAO,IAAI,KAAK,QAAQ;wBAC7B,OAAO,IAAI,KAAK,QAAQ;wBACxB,OAAO,IAAI,KAAK,SAAS;wBACzB,CAAC,CAAC,KAAK,CAAC,QAAQ,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;wBAC9B,CAAC,CAAC,KAAK,CAAA;gBACX,CAAC;gBACD,OAAO,KAAK,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,KAAK,CAAA;YAC5D,CAAC;SACF;QACD,GAAG,EAAE;YACH,IAAI,EAAE,SAAS;YACf,UAAU,EAAE,QAAQ;YACpB,IAAI,EAAE,CAAC,KAAK,EAAE,EAAE,CAAC,CAAC,KAAK;SACxB;QACD,GAAG,EAAE;YACH,IAAI,EAAE,UAAU;YAChB,UAAU,EAAE,CAAC;YACb,IAAI,EAAE,CAAC,KAAK,EAAE,MAAM,EAAE,EAAE;gBACtB,MAAM,IAAI,KAAK,CAAC,8BAA8B,CAAC,CAAA;YACjD,CAAC;SACF;KACF;IAED;;;;;;;;;;;;;OAaG;IACH,SAAS,EAAE,EAAE;CACd,CAAC,CAAA"}
1
+ {"version":3,"file":"grammar.js","sourceRoot":"","sources":["../src/grammar.ts"],"names":[],"mappings":"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"}
package/esm/index.d.ts CHANGED
@@ -1,5 +1,14 @@
1
1
  export { Jexl, default } from './Jexl.ts';
2
+ export type { JexlOptions } from './Jexl.ts';
3
+ export type { GetMember, VariableReader } from './grammar.ts';
2
4
  export { default as Expression } from './Expression.ts';
5
+ export { analyze } from './analyze.ts';
6
+ export { check, print, recordOf, union } from './check.ts';
7
+ export { callSubject, conditions, fromConditions, pathSubject, printCondition } from './conditions.ts';
3
8
  export { default as Lexer } from './Lexer.ts';
9
+ export { JexlSyntaxError } from './errors.ts';
4
10
  export { getGrammar } from './grammar.ts';
11
+ export type * from './analyze.ts';
12
+ export type * from './check.ts';
13
+ export type * from './conditions.ts';
5
14
  export type * from './types.ts';
package/esm/index.js CHANGED
@@ -4,6 +4,10 @@
4
4
  */
5
5
  export { Jexl, default } from "./Jexl.js";
6
6
  export { default as Expression } from "./Expression.js";
7
+ export { analyze } from "./analyze.js";
8
+ export { check, print, recordOf, union } from "./check.js";
9
+ export { callSubject, conditions, fromConditions, pathSubject, printCondition } from "./conditions.js";
7
10
  export { default as Lexer } from "./Lexer.js";
11
+ export { JexlSyntaxError } from "./errors.js";
8
12
  export { getGrammar } from "./grammar.js";
9
13
  //# sourceMappingURL=index.js.map
package/esm/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AACzC,OAAO,EAAE,OAAO,IAAI,UAAU,EAAE,MAAM,iBAAiB,CAAA;AACvD,OAAO,EAAE,OAAO,IAAI,KAAK,EAAE,MAAM,YAAY,CAAA;AAC7C,OAAO,EAAE,UAAU,EAAE,MAAM,cAAc,CAAA"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AAGzC,OAAO,EAAE,OAAO,IAAI,UAAU,EAAE,MAAM,iBAAiB,CAAA;AACvD,OAAO,EAAE,OAAO,EAAE,MAAM,cAAc,CAAA;AACtC,OAAO,EAAE,KAAK,EAAE,KAAK,EAAE,QAAQ,EAAE,KAAK,EAAE,MAAM,YAAY,CAAA;AAC1D,OAAO,EACL,WAAW,EACX,UAAU,EACV,cAAc,EACd,WAAW,EACX,cAAc,EACf,MAAM,iBAAiB,CAAA;AACxB,OAAO,EAAE,OAAO,IAAI,KAAK,EAAE,MAAM,YAAY,CAAA;AAC7C,OAAO,EAAE,eAAe,EAAE,MAAM,aAAa,CAAA;AAC7C,OAAO,EAAE,UAAU,EAAE,MAAM,cAAc,CAAA"}
@@ -0,0 +1,34 @@
1
+ import type { JexlValue } from './types.ts';
2
+ type Test = (left: JexlValue, right: JexlValue) => boolean;
3
+ type Arithmetic = (left: JexlValue, right: JexlValue) => JexlValue;
4
+ export declare function isList(left: JexlValue, right: JexlValue): boolean;
5
+ /**
6
+ * A comparison over list operands: it holds when it holds for any value, as
7
+ * bcftools compares a multi-valued tag, so `AF > 0.05` is true when any
8
+ * allele's frequency is and `CLNSIG == 'Pathogenic'` when any significance is.
9
+ * Each operator calls this only once {@link isList} says it must, so the
10
+ * comparison of two single values stays a direct call V8 can inline.
11
+ */
12
+ export declare function anyPair(test: Test, left: JexlValue, right: JexlValue): boolean;
13
+ /**
14
+ * Whether `+` pairs its operands value by value: only when a list is involved
15
+ * and neither side holds text, so `REF + '>' + ALT` still joins as JavaScript
16
+ * joins, `'A>T,C'`, while `DP + 1` adds.
17
+ */
18
+ export declare function addsPairwise(left: JexlValue, right: JexlValue): boolean;
19
+ /**
20
+ * Arithmetic over list operands, value by value, as bcftools and R apply it:
21
+ * `AC / AN` divides each count, and a list of one, or a lone value, pairs with
22
+ * every value of the other side. Lists of two other lengths have no pairing
23
+ * and yield undefined.
24
+ */
25
+ export declare function pairwise(fn: Arithmetic, left: JexlValue, right: JexlValue): JexlValue;
26
+ /** Whether a value, or any value of a list, matches a pattern string. */
27
+ export declare function matches(value: JexlValue, pattern: JexlValue): boolean;
28
+ /**
29
+ * Whether a value is in a container: a substring of a string, a member of a
30
+ * list or Set, or a key of a Map or plain object. A list on the left is in
31
+ * the container when any of its values is.
32
+ */
33
+ export declare function isIn(left: JexlValue, right: JexlValue): boolean;
34
+ export {};
@@ -0,0 +1,123 @@
1
+ /*
2
+ * Jexl
3
+ * Copyright 2020 Tom Shawver
4
+ */
5
+ export function isList(left, right) {
6
+ return Array.isArray(left) || Array.isArray(right);
7
+ }
8
+ /**
9
+ * A comparison over list operands: it holds when it holds for any value, as
10
+ * bcftools compares a multi-valued tag, so `AF > 0.05` is true when any
11
+ * allele's frequency is and `CLNSIG == 'Pathogenic'` when any significance is.
12
+ * Each operator calls this only once {@link isList} says it must, so the
13
+ * comparison of two single values stays a direct call V8 can inline.
14
+ */
15
+ export function anyPair(test, left, right) {
16
+ return Array.isArray(left)
17
+ ? left.some((l) => anyPair(test, l, right))
18
+ : Array.isArray(right)
19
+ ? right.some((r) => anyPair(test, left, r))
20
+ : test(left, right);
21
+ }
22
+ function hasText(value) {
23
+ return (typeof value === 'string' ||
24
+ (Array.isArray(value) && value.some((item) => typeof item === 'string')));
25
+ }
26
+ /**
27
+ * Whether `+` pairs its operands value by value: only when a list is involved
28
+ * and neither side holds text, so `REF + '>' + ALT` still joins as JavaScript
29
+ * joins, `'A>T,C'`, while `DP + 1` adds.
30
+ */
31
+ export function addsPairwise(left, right) {
32
+ return isList(left, right) && !hasText(left) && !hasText(right);
33
+ }
34
+ /**
35
+ * Arithmetic over list operands, value by value, as bcftools and R apply it:
36
+ * `AC / AN` divides each count, and a list of one, or a lone value, pairs with
37
+ * every value of the other side. Lists of two other lengths have no pairing
38
+ * and yield undefined.
39
+ */
40
+ export function pairwise(fn, left, right) {
41
+ const ls = Array.isArray(left) ? left : [left];
42
+ const rs = Array.isArray(right) ? right : [right];
43
+ if (ls.length !== rs.length && ls.length !== 1 && rs.length !== 1) {
44
+ return undefined;
45
+ }
46
+ const length = ls.length === 1 ? rs.length : ls.length;
47
+ const out = new Array(length);
48
+ for (let i = 0; i < length; i++) {
49
+ out[i] = fn(ls.length === 1 ? ls[0] : ls[i], rs.length === 1 ? rs[0] : rs[i]);
50
+ }
51
+ return out;
52
+ }
53
+ const patterns = new Map();
54
+ const MAX_PATTERNS = 1000;
55
+ /**
56
+ * The regular expression a pattern string stands for. A leading `(?i)`, the
57
+ * inline flag PCRE, Python and Go read, makes it case-insensitive.
58
+ */
59
+ function regex(pattern) {
60
+ let re = patterns.get(pattern);
61
+ if (!re) {
62
+ try {
63
+ re = pattern.startsWith('(?i)')
64
+ ? new RegExp(pattern.slice(4), 'i')
65
+ : new RegExp(pattern);
66
+ }
67
+ catch {
68
+ throw new Error(`Invalid regular expression: ${pattern}`);
69
+ }
70
+ if (patterns.size >= MAX_PATTERNS) {
71
+ patterns.clear();
72
+ }
73
+ patterns.set(pattern, re);
74
+ }
75
+ return re;
76
+ }
77
+ /** Whether a value, or any value of a list, matches a pattern string. */
78
+ export function matches(value, pattern) {
79
+ if (typeof pattern !== 'string') {
80
+ return false;
81
+ }
82
+ const re = regex(pattern);
83
+ const test = (v) => (typeof v === 'string' ||
84
+ typeof v === 'number' ||
85
+ typeof v === 'boolean') &&
86
+ re.test(String(v));
87
+ return Array.isArray(value) ? value.some(test) : test(value);
88
+ }
89
+ /**
90
+ * Whether a value is in a container: a substring of a string, a member of a
91
+ * list or Set, or a key of a Map or plain object. A list on the left is in
92
+ * the container when any of its values is.
93
+ */
94
+ export function isIn(left, right) {
95
+ if (Array.isArray(left)) {
96
+ return left.some((l) => isIn(l, right));
97
+ }
98
+ if (typeof right === 'string') {
99
+ // only a primitive has a meaningful substring form. An absent or
100
+ // structured left operand is not "in" a string, and must not be coerced
101
+ // to '' — every string contains the empty string
102
+ return typeof left === 'string' ||
103
+ typeof left === 'number' ||
104
+ typeof left === 'boolean'
105
+ ? right.includes(String(left))
106
+ : false;
107
+ }
108
+ if (Array.isArray(right)) {
109
+ return right.includes(left);
110
+ }
111
+ if (right instanceof Set || right instanceof Map) {
112
+ return right.has(left);
113
+ }
114
+ if (typeof right === 'object' &&
115
+ right !== null &&
116
+ (typeof left === 'string' ||
117
+ typeof left === 'number' ||
118
+ typeof left === 'boolean')) {
119
+ return Object.hasOwn(right, String(left));
120
+ }
121
+ return false;
122
+ }
123
+ //# sourceMappingURL=operators.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"operators.js","sourceRoot":"","sources":["../src/operators.ts"],"names":[],"mappings":"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"}
@@ -1,104 +1,61 @@
1
+ import { JexlSyntaxError } from '../errors.ts';
1
2
  import type Lexer from '../Lexer.ts';
2
3
  import type { Grammar } from '../grammar.ts';
3
- import type { AstNode, Token } from '../types.ts';
4
+ import type { AstNode, AstNodeUnion, Lambda, ObjectLiteral, TemplateLiteral, TemplatePart, Token } from '../types.ts';
5
+ export { JexlSyntaxError } from '../errors.ts';
4
6
  /**
5
- * The Parser is a state machine that converts tokens from the {@link Lexer}
6
- * into an Abstract Syntax Tree (AST), capable of being evaluated in any
7
- * context by {@link compileAst}. The Parser expects that all tokens
8
- * provided to it are legal and typed properly according to the grammar, but
9
- * accepts that the tokens may still be in an invalid order or in some other
10
- * unparsable configuration that requires it to throw an Error.
11
- * @param {{}} grammar The grammar object to use to parse Jexl strings
12
- * @param {string} [prefix] A string prefix to prepend to the expression string
13
- * for error messaging purposes. This is useful for when a new Parser is
14
- * instantiated to parse an subexpression, as the parent Parser's
15
- * expression string thus far can be passed for a more user-friendly
16
- * error message.
17
- * @param {{}} [stopMap] A mapping of token types to any truthy value. When the
18
- * token type is encountered, the parser will return the mapped value
19
- * instead of boolean false.
7
+ * Converts the tokens from the {@link Lexer} into an Abstract Syntax Tree, for
8
+ * {@link compileAst} to lower to closures. A Pratt parser: each level of the
9
+ * grammar is a method, from `_sequence` (loosest) down to `_primary`, and
10
+ * binary operators are climbed by the precedence the grammar gives them, so
11
+ * operators a host registers slot in without the parser knowing them.
20
12
  */
21
13
  declare class Parser {
22
14
  _grammar: Grammar;
23
15
  _lexer: Lexer;
24
- _state: string;
25
- _tree: AstNode | null;
26
- _exprStr: string;
27
- _stopMap: Record<string, string>;
28
- _cursor?: AstNode | null;
29
- _subParser?: Parser;
30
- _parentStop?: boolean;
31
- _nextIdentEncapsulate?: boolean;
32
- _curObjKey?: string;
33
- _sequenceExpressions?: AstNode[];
34
- constructor(grammar: Grammar, lexer: Lexer, prefix?: string, stopMap?: Record<string, string>);
16
+ _tokens: Token[];
17
+ _pos: number;
18
+ _offset: number;
19
+ _grouped?: WeakSet<AstNode>;
20
+ _lambdaDepth: number;
35
21
  /**
36
- * Processes a new token into the AST and manages the transitions of the state
37
- * machine.
38
- * @param {{type: <string>}} token A token object, as provided by the
39
- * {@link Lexer#tokenize} function.
40
- * @throws {Error} if a token is added when the Parser has been marked as
41
- * complete by {@link #complete}, or if an unexpected token type is added.
42
- * @returns {boolean|*} the stopState value if this parser encountered a token
43
- * in the stopState mapb false if tokens can continue.
44
- */
45
- addToken(token: Token): string | false;
46
- /**
47
- * Processes an array of tokens iteratively through the {@link #addToken}
48
- * function.
49
- * @param {Array<{type: <string>}>} tokens An array of tokens, as provided by
50
- * the {@link Lexer#tokenize} function.
22
+ * @param offset where the tokens start in the source, so that an error
23
+ * inside a template interpolation reports its place in the whole
51
24
  */
25
+ constructor(grammar: Grammar, lexer: Lexer, offset?: number);
26
+ parse(source: string): AstNodeUnion | null;
52
27
  addTokens(tokens: Token[]): void;
53
28
  /**
54
- * Marks this Parser instance as completed and retrieves the full AST.
55
- * @returns {{}|null} a full expression tree, ready for evaluation by the
56
- * {@link compileAst} function, or null if no tokens were passed to
57
- * the parser before complete was called
58
- * @throws {Error} if the parser is not in a state where it's legal to end
59
- * the expression, indicating that the expression is incomplete
60
- */
61
- complete(): AstNode | null;
62
- /**
63
- * Ends a subexpression by completing the subParser and passing its result
64
- * to the subHandler configured in the current state.
65
- * @private
66
- */
67
- _endSubExpression(): void;
68
- /**
69
- * Places a new tree node at the current position of the cursor (to the 'right'
70
- * property) and then advances the cursor to the new node. This function also
71
- * handles setting the parent of the new node.
72
- * @param {{type: <string>}} node A node to be added to the AST
73
- * @private
74
- */
75
- _placeAtCursor(node: AstNode): void;
76
- /**
77
- * Places a tree node before the current position of the cursor, replacing
78
- * the node that the cursor currently points to. This should only be called in
79
- * cases where the cursor is known to exist, and the provided node already
80
- * contains a pointer to what's at the cursor currently.
81
- * @param {{type: <string>}} node A node to be added to the AST
82
- * @private
83
- */
84
- _placeBeforeCursor(node: AstNode): void;
85
- /**
86
- * Sets the parent of a node by creating a non-enumerable _parent property
87
- * that points to the supplied parent argument.
88
- * @param {{type: <string>}} node A node of the AST on which to set a new
89
- * parent
90
- * @param {{type: <string>}} parent An existing node of the AST to serve as the
91
- * parent of the new node
92
- * @private
93
- */
94
- _setParent(node: AstNode, parent: AstNode): void;
95
- /**
96
- * Prepares the Parser to accept a subexpression by (re)instantiating the
97
- * subParser.
98
- * @param {string} [exprStr] The expression string to prefix to the new Parser
99
- * @returns {Parser} the new subParser, also stored on this instance
100
- * @private
101
- */
102
- _startSubExpression(exprStr?: string): Parser;
29
+ * @returns the expression tree, or null for an expression with no tokens
30
+ * @throws {JexlSyntaxError} if the tokens do not form exactly one expression
31
+ */
32
+ complete(): AstNodeUnion | null;
33
+ _sequence(): AstNodeUnion;
34
+ _assignment(): AstNodeUnion;
35
+ _atLambda(): boolean;
36
+ /** Parses the lambda {@link _atLambda} found, whose shape it has checked. */
37
+ _lambda(): Lambda;
38
+ _ternary(): AstNodeUnion;
39
+ /**
40
+ * Parses operands joined by binary operators that bind tighter than `floor`.
41
+ * One exactly at `floor` binds only when it continues a right-associative
42
+ * chain, which is how `a ^ b ^ c` groups from the right.
43
+ */
44
+ _binary(floor: number, rightAssociative?: boolean): AstNodeUnion;
45
+ /** `a ?? b || c` has no grouping a reader can guess; JS refuses it too. */
46
+ _mixesNullish(operator: string, ...operands: AstNodeUnion[]): boolean;
47
+ _unary(): AstNodeUnion;
48
+ _postfix(subject: AstNodeUnion): AstNodeUnion;
49
+ _primary(): AstNodeUnion;
50
+ _list(close: string): AstNode[];
51
+ _object(): ObjectLiteral;
52
+ _template(tokenParts: TemplatePart[], index: number): TemplateLiteral;
53
+ _peek(): Token | undefined;
54
+ _next(): Token;
55
+ _eat(type: string): boolean;
56
+ _expect(type: string): Token;
57
+ _unexpected(index: number): JexlSyntaxError;
58
+ _error(message: string, index: number): JexlSyntaxError;
59
+ _offsetOf(index: number): number;
103
60
  }
104
61
  export default Parser;