@tanstack/db 0.0.13 → 0.0.15

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 (198) hide show
  1. package/dist/cjs/collection.cjs +117 -104
  2. package/dist/cjs/collection.cjs.map +1 -1
  3. package/dist/cjs/collection.d.cts +19 -22
  4. package/dist/cjs/index.cjs +35 -13
  5. package/dist/cjs/index.cjs.map +1 -1
  6. package/dist/cjs/index.d.cts +0 -1
  7. package/dist/cjs/query/builder/functions.cjs +107 -0
  8. package/dist/cjs/query/builder/functions.cjs.map +1 -0
  9. package/dist/cjs/query/builder/functions.d.cts +38 -0
  10. package/dist/cjs/query/builder/index.cjs +499 -0
  11. package/dist/cjs/query/builder/index.cjs.map +1 -0
  12. package/dist/cjs/query/builder/index.d.cts +324 -0
  13. package/dist/cjs/query/builder/ref-proxy.cjs +96 -0
  14. package/dist/cjs/query/builder/ref-proxy.cjs.map +1 -0
  15. package/dist/cjs/query/builder/ref-proxy.d.cts +28 -0
  16. package/dist/cjs/query/builder/types.d.cts +80 -0
  17. package/dist/cjs/query/compiler/evaluators.cjs +261 -0
  18. package/dist/cjs/query/compiler/evaluators.cjs.map +1 -0
  19. package/dist/cjs/query/compiler/evaluators.d.cts +11 -0
  20. package/dist/cjs/query/compiler/group-by.cjs +271 -0
  21. package/dist/cjs/query/compiler/group-by.cjs.map +1 -0
  22. package/dist/cjs/query/compiler/group-by.d.cts +7 -0
  23. package/dist/cjs/query/compiler/index.cjs +181 -0
  24. package/dist/cjs/query/compiler/index.cjs.map +1 -0
  25. package/dist/cjs/query/compiler/index.d.cts +15 -0
  26. package/dist/cjs/query/compiler/joins.cjs +116 -0
  27. package/dist/cjs/query/compiler/joins.cjs.map +1 -0
  28. package/dist/cjs/query/compiler/joins.d.cts +11 -0
  29. package/dist/cjs/query/compiler/order-by.cjs +89 -0
  30. package/dist/cjs/query/compiler/order-by.cjs.map +1 -0
  31. package/dist/cjs/query/compiler/order-by.d.cts +9 -0
  32. package/dist/cjs/query/compiler/select.cjs +57 -0
  33. package/dist/cjs/query/compiler/select.cjs.map +1 -0
  34. package/dist/cjs/query/compiler/select.d.cts +15 -0
  35. package/dist/cjs/query/index.d.cts +6 -5
  36. package/dist/cjs/query/ir.cjs +57 -0
  37. package/dist/cjs/query/ir.cjs.map +1 -0
  38. package/dist/cjs/query/ir.d.cts +81 -0
  39. package/dist/cjs/query/live-query-collection.cjs +224 -0
  40. package/dist/cjs/query/live-query-collection.cjs.map +1 -0
  41. package/dist/cjs/query/live-query-collection.d.cts +124 -0
  42. package/dist/cjs/transactions.cjs +20 -13
  43. package/dist/cjs/transactions.cjs.map +1 -1
  44. package/dist/cjs/transactions.d.cts +13 -4
  45. package/dist/cjs/types.d.cts +14 -1
  46. package/dist/esm/collection.d.ts +19 -22
  47. package/dist/esm/collection.js +118 -105
  48. package/dist/esm/collection.js.map +1 -1
  49. package/dist/esm/index.d.ts +0 -1
  50. package/dist/esm/index.js +34 -12
  51. package/dist/esm/index.js.map +1 -1
  52. package/dist/esm/query/builder/functions.d.ts +38 -0
  53. package/dist/esm/query/builder/functions.js +107 -0
  54. package/dist/esm/query/builder/functions.js.map +1 -0
  55. package/dist/esm/query/builder/index.d.ts +324 -0
  56. package/dist/esm/query/builder/index.js +499 -0
  57. package/dist/esm/query/builder/index.js.map +1 -0
  58. package/dist/esm/query/builder/ref-proxy.d.ts +28 -0
  59. package/dist/esm/query/builder/ref-proxy.js +96 -0
  60. package/dist/esm/query/builder/ref-proxy.js.map +1 -0
  61. package/dist/esm/query/builder/types.d.ts +80 -0
  62. package/dist/esm/query/compiler/evaluators.d.ts +11 -0
  63. package/dist/esm/query/compiler/evaluators.js +261 -0
  64. package/dist/esm/query/compiler/evaluators.js.map +1 -0
  65. package/dist/esm/query/compiler/group-by.d.ts +7 -0
  66. package/dist/esm/query/compiler/group-by.js +271 -0
  67. package/dist/esm/query/compiler/group-by.js.map +1 -0
  68. package/dist/esm/query/compiler/index.d.ts +15 -0
  69. package/dist/esm/query/compiler/index.js +181 -0
  70. package/dist/esm/query/compiler/index.js.map +1 -0
  71. package/dist/esm/query/compiler/joins.d.ts +11 -0
  72. package/dist/esm/query/compiler/joins.js +116 -0
  73. package/dist/esm/query/compiler/joins.js.map +1 -0
  74. package/dist/esm/query/compiler/order-by.d.ts +9 -0
  75. package/dist/esm/query/compiler/order-by.js +89 -0
  76. package/dist/esm/query/compiler/order-by.js.map +1 -0
  77. package/dist/esm/query/compiler/select.d.ts +15 -0
  78. package/dist/esm/query/compiler/select.js +57 -0
  79. package/dist/esm/query/compiler/select.js.map +1 -0
  80. package/dist/esm/query/index.d.ts +6 -5
  81. package/dist/esm/query/ir.d.ts +81 -0
  82. package/dist/esm/query/ir.js +57 -0
  83. package/dist/esm/query/ir.js.map +1 -0
  84. package/dist/esm/query/live-query-collection.d.ts +124 -0
  85. package/dist/esm/query/live-query-collection.js +224 -0
  86. package/dist/esm/query/live-query-collection.js.map +1 -0
  87. package/dist/esm/transactions.d.ts +13 -4
  88. package/dist/esm/transactions.js +20 -13
  89. package/dist/esm/transactions.js.map +1 -1
  90. package/dist/esm/types.d.ts +14 -1
  91. package/package.json +3 -4
  92. package/src/collection.ts +152 -129
  93. package/src/index.ts +0 -1
  94. package/src/query/builder/functions.ts +267 -0
  95. package/src/query/builder/index.ts +648 -0
  96. package/src/query/builder/ref-proxy.ts +156 -0
  97. package/src/query/builder/types.ts +278 -0
  98. package/src/query/compiler/evaluators.ts +315 -0
  99. package/src/query/compiler/group-by.ts +428 -0
  100. package/src/query/compiler/index.ts +276 -0
  101. package/src/query/compiler/joins.ts +228 -0
  102. package/src/query/compiler/order-by.ts +139 -0
  103. package/src/query/compiler/select.ts +173 -0
  104. package/src/query/index.ts +64 -5
  105. package/src/query/ir.ts +128 -0
  106. package/src/query/live-query-collection.ts +509 -0
  107. package/src/transactions.ts +34 -19
  108. package/src/types.ts +16 -1
  109. package/dist/cjs/query/compiled-query.cjs +0 -160
  110. package/dist/cjs/query/compiled-query.cjs.map +0 -1
  111. package/dist/cjs/query/compiled-query.d.cts +0 -20
  112. package/dist/cjs/query/evaluators.cjs +0 -161
  113. package/dist/cjs/query/evaluators.cjs.map +0 -1
  114. package/dist/cjs/query/evaluators.d.cts +0 -14
  115. package/dist/cjs/query/extractors.cjs +0 -122
  116. package/dist/cjs/query/extractors.cjs.map +0 -1
  117. package/dist/cjs/query/extractors.d.cts +0 -22
  118. package/dist/cjs/query/functions.cjs +0 -152
  119. package/dist/cjs/query/functions.cjs.map +0 -1
  120. package/dist/cjs/query/functions.d.cts +0 -21
  121. package/dist/cjs/query/group-by.cjs +0 -88
  122. package/dist/cjs/query/group-by.cjs.map +0 -1
  123. package/dist/cjs/query/group-by.d.cts +0 -40
  124. package/dist/cjs/query/joins.cjs +0 -141
  125. package/dist/cjs/query/joins.cjs.map +0 -1
  126. package/dist/cjs/query/joins.d.cts +0 -14
  127. package/dist/cjs/query/order-by.cjs +0 -185
  128. package/dist/cjs/query/order-by.cjs.map +0 -1
  129. package/dist/cjs/query/order-by.d.cts +0 -3
  130. package/dist/cjs/query/pipeline-compiler.cjs +0 -89
  131. package/dist/cjs/query/pipeline-compiler.cjs.map +0 -1
  132. package/dist/cjs/query/pipeline-compiler.d.cts +0 -10
  133. package/dist/cjs/query/query-builder.cjs +0 -307
  134. package/dist/cjs/query/query-builder.cjs.map +0 -1
  135. package/dist/cjs/query/query-builder.d.cts +0 -225
  136. package/dist/cjs/query/schema.d.cts +0 -100
  137. package/dist/cjs/query/select.cjs +0 -130
  138. package/dist/cjs/query/select.cjs.map +0 -1
  139. package/dist/cjs/query/select.d.cts +0 -3
  140. package/dist/cjs/query/types.d.cts +0 -189
  141. package/dist/cjs/query/utils.cjs +0 -154
  142. package/dist/cjs/query/utils.cjs.map +0 -1
  143. package/dist/cjs/query/utils.d.cts +0 -37
  144. package/dist/cjs/utils.cjs +0 -17
  145. package/dist/cjs/utils.cjs.map +0 -1
  146. package/dist/cjs/utils.d.cts +0 -3
  147. package/dist/esm/query/compiled-query.d.ts +0 -20
  148. package/dist/esm/query/compiled-query.js +0 -160
  149. package/dist/esm/query/compiled-query.js.map +0 -1
  150. package/dist/esm/query/evaluators.d.ts +0 -14
  151. package/dist/esm/query/evaluators.js +0 -161
  152. package/dist/esm/query/evaluators.js.map +0 -1
  153. package/dist/esm/query/extractors.d.ts +0 -22
  154. package/dist/esm/query/extractors.js +0 -122
  155. package/dist/esm/query/extractors.js.map +0 -1
  156. package/dist/esm/query/functions.d.ts +0 -21
  157. package/dist/esm/query/functions.js +0 -152
  158. package/dist/esm/query/functions.js.map +0 -1
  159. package/dist/esm/query/group-by.d.ts +0 -40
  160. package/dist/esm/query/group-by.js +0 -88
  161. package/dist/esm/query/group-by.js.map +0 -1
  162. package/dist/esm/query/joins.d.ts +0 -14
  163. package/dist/esm/query/joins.js +0 -141
  164. package/dist/esm/query/joins.js.map +0 -1
  165. package/dist/esm/query/order-by.d.ts +0 -3
  166. package/dist/esm/query/order-by.js +0 -185
  167. package/dist/esm/query/order-by.js.map +0 -1
  168. package/dist/esm/query/pipeline-compiler.d.ts +0 -10
  169. package/dist/esm/query/pipeline-compiler.js +0 -89
  170. package/dist/esm/query/pipeline-compiler.js.map +0 -1
  171. package/dist/esm/query/query-builder.d.ts +0 -225
  172. package/dist/esm/query/query-builder.js +0 -307
  173. package/dist/esm/query/query-builder.js.map +0 -1
  174. package/dist/esm/query/schema.d.ts +0 -100
  175. package/dist/esm/query/select.d.ts +0 -3
  176. package/dist/esm/query/select.js +0 -130
  177. package/dist/esm/query/select.js.map +0 -1
  178. package/dist/esm/query/types.d.ts +0 -189
  179. package/dist/esm/query/utils.d.ts +0 -37
  180. package/dist/esm/query/utils.js +0 -154
  181. package/dist/esm/query/utils.js.map +0 -1
  182. package/dist/esm/utils.d.ts +0 -3
  183. package/dist/esm/utils.js +0 -17
  184. package/dist/esm/utils.js.map +0 -1
  185. package/src/query/compiled-query.ts +0 -234
  186. package/src/query/evaluators.ts +0 -250
  187. package/src/query/extractors.ts +0 -214
  188. package/src/query/functions.ts +0 -297
  189. package/src/query/group-by.ts +0 -139
  190. package/src/query/joins.ts +0 -260
  191. package/src/query/order-by.ts +0 -264
  192. package/src/query/pipeline-compiler.ts +0 -149
  193. package/src/query/query-builder.ts +0 -902
  194. package/src/query/schema.ts +0 -268
  195. package/src/query/select.ts +0 -208
  196. package/src/query/types.ts +0 -418
  197. package/src/query/utils.ts +0 -245
  198. package/src/utils.ts +0 -15
@@ -1,161 +0,0 @@
1
- import { evaluateOperandOnNamespacedRow } from "./extractors.js";
2
- import { isValueInArray, convertLikeToRegex, compareValues } from "./utils.js";
3
- function evaluateWhereOnNamespacedRow(namespacedRow, where, mainTableAlias, joinedTableAlias) {
4
- return where.every((item) => {
5
- if (typeof item === `function`) {
6
- return item(namespacedRow);
7
- } else {
8
- return evaluateConditionOnNamespacedRow(
9
- namespacedRow,
10
- item,
11
- mainTableAlias,
12
- joinedTableAlias
13
- );
14
- }
15
- });
16
- }
17
- function evaluateConditionOnNamespacedRow(namespacedRow, condition, mainTableAlias, joinedTableAlias) {
18
- if (condition.length === 3 && !Array.isArray(condition[0])) {
19
- const [left, comparator, right] = condition;
20
- return evaluateSimpleConditionOnNamespacedRow(
21
- namespacedRow,
22
- left,
23
- comparator,
24
- right,
25
- mainTableAlias,
26
- joinedTableAlias
27
- );
28
- }
29
- if (condition.length > 3 && !Array.isArray(condition[0]) && typeof condition[1] === `string` && ![`and`, `or`].includes(condition[1])) {
30
- let result = evaluateSimpleConditionOnNamespacedRow(
31
- namespacedRow,
32
- condition[0],
33
- condition[1],
34
- condition[2],
35
- mainTableAlias,
36
- joinedTableAlias
37
- );
38
- for (let i = 3; i < condition.length; i += 4) {
39
- const logicalOp = condition[i];
40
- if (i + 3 <= condition.length) {
41
- const nextResult = evaluateSimpleConditionOnNamespacedRow(
42
- namespacedRow,
43
- condition[i + 1],
44
- condition[i + 2],
45
- condition[i + 3],
46
- mainTableAlias,
47
- joinedTableAlias
48
- );
49
- if (logicalOp === `and`) {
50
- result = result && nextResult;
51
- } else {
52
- result = result || nextResult;
53
- }
54
- }
55
- }
56
- return result;
57
- }
58
- if (condition.length > 0 && Array.isArray(condition[0])) {
59
- let result = evaluateConditionOnNamespacedRow(
60
- namespacedRow,
61
- condition[0],
62
- mainTableAlias,
63
- joinedTableAlias
64
- );
65
- for (let i = 1; i < condition.length; i += 2) {
66
- if (i + 1 >= condition.length) break;
67
- const operator = condition[i];
68
- const nextCondition = condition[i + 1];
69
- if (operator === `and`) {
70
- result = result && evaluateConditionOnNamespacedRow(
71
- namespacedRow,
72
- nextCondition,
73
- mainTableAlias,
74
- joinedTableAlias
75
- );
76
- } else {
77
- result = result || evaluateConditionOnNamespacedRow(
78
- namespacedRow,
79
- nextCondition,
80
- mainTableAlias,
81
- joinedTableAlias
82
- );
83
- }
84
- }
85
- return result;
86
- }
87
- return true;
88
- }
89
- function evaluateSimpleConditionOnNamespacedRow(namespacedRow, left, comparator, right, mainTableAlias, joinedTableAlias) {
90
- const leftValue = evaluateOperandOnNamespacedRow(
91
- namespacedRow,
92
- left,
93
- mainTableAlias,
94
- joinedTableAlias
95
- );
96
- const rightValue = evaluateOperandOnNamespacedRow(
97
- namespacedRow,
98
- right,
99
- mainTableAlias,
100
- joinedTableAlias
101
- );
102
- switch (comparator) {
103
- case `=`:
104
- return leftValue === rightValue;
105
- case `!=`:
106
- return leftValue !== rightValue;
107
- case `<`:
108
- return compareValues(leftValue, rightValue, `<`);
109
- case `<=`:
110
- return compareValues(leftValue, rightValue, `<=`);
111
- case `>`:
112
- return compareValues(leftValue, rightValue, `>`);
113
- case `>=`:
114
- return compareValues(leftValue, rightValue, `>=`);
115
- case `like`:
116
- case `not like`:
117
- if (typeof leftValue === `string` && typeof rightValue === `string`) {
118
- const pattern = convertLikeToRegex(rightValue);
119
- const matches = new RegExp(`^${pattern}$`, `i`).test(leftValue);
120
- return comparator === `like` ? matches : !matches;
121
- }
122
- return comparator === `like` ? false : true;
123
- case `in`:
124
- if (!Array.isArray(rightValue)) {
125
- return false;
126
- }
127
- if (rightValue.length === 0) {
128
- return false;
129
- }
130
- if (Array.isArray(leftValue)) {
131
- return leftValue.some((item) => isValueInArray(item, rightValue));
132
- }
133
- return isValueInArray(leftValue, rightValue);
134
- case `not in`:
135
- if (!Array.isArray(rightValue)) {
136
- return true;
137
- }
138
- if (rightValue.length === 0) {
139
- return true;
140
- }
141
- if (Array.isArray(leftValue)) {
142
- return !leftValue.some((item) => isValueInArray(item, rightValue));
143
- }
144
- return !isValueInArray(leftValue, rightValue);
145
- case `is`:
146
- return leftValue === rightValue;
147
- case `is not`:
148
- if (rightValue === null) {
149
- return leftValue !== null && leftValue !== void 0;
150
- }
151
- return leftValue !== rightValue;
152
- default:
153
- return false;
154
- }
155
- }
156
- export {
157
- evaluateConditionOnNamespacedRow,
158
- evaluateSimpleConditionOnNamespacedRow,
159
- evaluateWhereOnNamespacedRow
160
- };
161
- //# sourceMappingURL=evaluators.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"evaluators.js","sources":["../../../src/query/evaluators.ts"],"sourcesContent":["import { evaluateOperandOnNamespacedRow } from \"./extractors.js\"\nimport { compareValues, convertLikeToRegex, isValueInArray } from \"./utils.js\"\nimport type {\n Comparator,\n Condition,\n ConditionOperand,\n LogicalOperator,\n SimpleCondition,\n Where,\n WhereCallback,\n} from \"./schema.js\"\nimport type { NamespacedRow } from \"../types.js\"\n\n/**\n * Evaluates a Where clause (which is always an array of conditions and/or callbacks) against a nested row structure\n */\nexport function evaluateWhereOnNamespacedRow(\n namespacedRow: NamespacedRow,\n where: Where,\n mainTableAlias?: string,\n joinedTableAlias?: string\n): boolean {\n // Where is always an array of conditions and/or callbacks\n // Evaluate all items and combine with AND logic\n return where.every((item) => {\n if (typeof item === `function`) {\n return (item as WhereCallback)(namespacedRow)\n } else {\n return evaluateConditionOnNamespacedRow(\n namespacedRow,\n item as Condition,\n mainTableAlias,\n joinedTableAlias\n )\n }\n })\n}\n\n/**\n * Evaluates a condition against a nested row structure\n */\nexport function evaluateConditionOnNamespacedRow(\n namespacedRow: NamespacedRow,\n condition: Condition,\n mainTableAlias?: string,\n joinedTableAlias?: string\n): boolean {\n // Handle simple conditions with exactly 3 elements\n if (condition.length === 3 && !Array.isArray(condition[0])) {\n const [left, comparator, right] = condition as SimpleCondition\n return evaluateSimpleConditionOnNamespacedRow(\n namespacedRow,\n left,\n comparator,\n right,\n mainTableAlias,\n joinedTableAlias\n )\n }\n\n // Handle flat composite conditions (multiple conditions in a single array)\n if (\n condition.length > 3 &&\n !Array.isArray(condition[0]) &&\n typeof condition[1] === `string` &&\n ![`and`, `or`].includes(condition[1] as string)\n ) {\n // Start with the first condition (first 3 elements)\n let result = evaluateSimpleConditionOnNamespacedRow(\n namespacedRow,\n condition[0],\n condition[1] as Comparator,\n condition[2],\n mainTableAlias,\n joinedTableAlias\n )\n\n // Process the rest in groups: logical operator, then 3 elements for each condition\n for (let i = 3; i < condition.length; i += 4) {\n const logicalOp = condition[i] as LogicalOperator\n\n // Make sure we have a complete condition to evaluate\n if (i + 3 <= condition.length) {\n const nextResult = evaluateSimpleConditionOnNamespacedRow(\n namespacedRow,\n condition[i + 1],\n condition[i + 2] as Comparator,\n condition[i + 3],\n mainTableAlias,\n joinedTableAlias\n )\n\n // Apply the logical operator\n if (logicalOp === `and`) {\n result = result && nextResult\n } else {\n // logicalOp === `or`\n result = result || nextResult\n }\n }\n }\n\n return result\n }\n\n // Handle nested composite conditions where the first element is an array\n if (condition.length > 0 && Array.isArray(condition[0])) {\n // Start with the first condition\n let result = evaluateConditionOnNamespacedRow(\n namespacedRow,\n condition[0] as Condition,\n mainTableAlias,\n joinedTableAlias\n )\n\n // Process the rest of the conditions and logical operators in pairs\n for (let i = 1; i < condition.length; i += 2) {\n if (i + 1 >= condition.length) break // Make sure we have a pair\n\n const operator = condition[i] as LogicalOperator\n const nextCondition = condition[i + 1] as Condition\n\n // Apply the logical operator\n if (operator === `and`) {\n result =\n result &&\n evaluateConditionOnNamespacedRow(\n namespacedRow,\n nextCondition,\n mainTableAlias,\n joinedTableAlias\n )\n } else {\n // logicalOp === `or`\n result =\n result ||\n evaluateConditionOnNamespacedRow(\n namespacedRow,\n nextCondition,\n mainTableAlias,\n joinedTableAlias\n )\n }\n }\n\n return result\n }\n\n // Fallback - this should not happen with valid conditions\n return true\n}\n\n/**\n * Evaluates a simple condition against a nested row structure\n */\nexport function evaluateSimpleConditionOnNamespacedRow(\n namespacedRow: Record<string, unknown>,\n left: ConditionOperand,\n comparator: Comparator,\n right: ConditionOperand,\n mainTableAlias?: string,\n joinedTableAlias?: string\n): boolean {\n const leftValue = evaluateOperandOnNamespacedRow(\n namespacedRow,\n left,\n mainTableAlias,\n joinedTableAlias\n )\n\n const rightValue = evaluateOperandOnNamespacedRow(\n namespacedRow,\n right,\n mainTableAlias,\n joinedTableAlias\n )\n\n // The rest of the function remains the same as evaluateSimpleCondition\n switch (comparator) {\n case `=`:\n return leftValue === rightValue\n case `!=`:\n return leftValue !== rightValue\n case `<`:\n return compareValues(leftValue, rightValue, `<`)\n case `<=`:\n return compareValues(leftValue, rightValue, `<=`)\n case `>`:\n return compareValues(leftValue, rightValue, `>`)\n case `>=`:\n return compareValues(leftValue, rightValue, `>=`)\n case `like`:\n case `not like`:\n if (typeof leftValue === `string` && typeof rightValue === `string`) {\n // Convert SQL LIKE pattern to proper regex pattern\n const pattern = convertLikeToRegex(rightValue)\n const matches = new RegExp(`^${pattern}$`, `i`).test(leftValue)\n return comparator === `like` ? matches : !matches\n }\n return comparator === `like` ? false : true\n case `in`:\n // If right value is not an array, we can't do an IN operation\n if (!Array.isArray(rightValue)) {\n return false\n }\n\n // For empty arrays, nothing is contained in them\n if (rightValue.length === 0) {\n return false\n }\n\n // Handle array-to-array comparison (check if any element in leftValue exists in rightValue)\n if (Array.isArray(leftValue)) {\n return leftValue.some((item) => isValueInArray(item, rightValue))\n }\n\n // Handle single value comparison\n return isValueInArray(leftValue, rightValue)\n\n case `not in`:\n // If right value is not an array, everything is \"not in\" it\n if (!Array.isArray(rightValue)) {\n return true\n }\n\n // For empty arrays, everything is \"not in\" them\n if (rightValue.length === 0) {\n return true\n }\n\n // Handle array-to-array comparison (check if no element in leftValue exists in rightValue)\n if (Array.isArray(leftValue)) {\n return !leftValue.some((item) => isValueInArray(item, rightValue))\n }\n\n // Handle single value comparison\n return !isValueInArray(leftValue, rightValue)\n\n case `is`:\n return leftValue === rightValue\n case `is not`:\n // Properly handle null/undefined checks\n if (rightValue === null) {\n return leftValue !== null && leftValue !== undefined\n }\n return leftValue !== rightValue\n default:\n return false\n }\n}\n"],"names":[],"mappings":"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"}
@@ -1,22 +0,0 @@
1
- import { ConditionOperand } from './schema.js';
2
- /**
3
- * Extracts a value from a nested row structure
4
- * @param namespacedRow The nested row structure
5
- * @param columnRef The column reference (may include table.column format)
6
- * @param mainTableAlias The main table alias to check first for columns without table reference
7
- * @param joinedTableAlias The joined table alias to check second for columns without table reference
8
- * @returns The extracted value or undefined if not found
9
- */
10
- export declare function extractValueFromNamespacedRow(namespacedRow: Record<string, unknown>, columnRef: string, mainTableAlias?: string, joinedTableAlias?: string): unknown;
11
- /**
12
- * Evaluates an operand against a nested row structure
13
- */
14
- export declare function evaluateOperandOnNamespacedRow(namespacedRow: Record<string, unknown>, operand: ConditionOperand, mainTableAlias?: string, joinedTableAlias?: string): unknown;
15
- /**
16
- * Extracts a join key value from a row based on the operand
17
- * @param row The data row (not nested)
18
- * @param operand The operand to extract the key from
19
- * @param defaultTableAlias The default table alias
20
- * @returns The extracted key value
21
- */
22
- export declare function extractJoinKey<T extends Record<string, unknown>>(row: T, operand: ConditionOperand, defaultTableAlias?: string): unknown;
@@ -1,122 +0,0 @@
1
- import { isFunctionCall, evaluateFunction } from "./functions.js";
2
- function extractValueFromNamespacedRow(namespacedRow, columnRef, mainTableAlias, joinedTableAlias) {
3
- if (columnRef.includes(`.`)) {
4
- const [tableAlias, colName] = columnRef.split(`.`);
5
- const tableData = namespacedRow[tableAlias];
6
- if (!tableData) {
7
- return null;
8
- }
9
- const value = tableData[colName];
10
- return value;
11
- } else {
12
- if (mainTableAlias && namespacedRow[mainTableAlias]) {
13
- const mainTableData = namespacedRow[mainTableAlias];
14
- if (typeof mainTableData === `object` && columnRef in mainTableData) {
15
- return mainTableData[columnRef];
16
- }
17
- }
18
- if (joinedTableAlias && namespacedRow[joinedTableAlias]) {
19
- const joinedTableData = namespacedRow[joinedTableAlias];
20
- if (typeof joinedTableData === `object` && columnRef in joinedTableData) {
21
- return joinedTableData[columnRef];
22
- }
23
- }
24
- for (const [_tableAlias, tableData] of Object.entries(namespacedRow)) {
25
- if (tableData && typeof tableData === `object` && columnRef in tableData) {
26
- return tableData[columnRef];
27
- }
28
- }
29
- return void 0;
30
- }
31
- }
32
- function evaluateOperandOnNamespacedRow(namespacedRow, operand, mainTableAlias, joinedTableAlias) {
33
- if (typeof operand === `string` && operand.startsWith(`@`)) {
34
- const columnRef = operand.substring(1);
35
- return extractValueFromNamespacedRow(
36
- namespacedRow,
37
- columnRef,
38
- mainTableAlias,
39
- joinedTableAlias
40
- );
41
- }
42
- if (operand && typeof operand === `object` && `col` in operand) {
43
- const colRef = operand.col;
44
- if (typeof colRef === `string`) {
45
- const nestedValue = extractValueFromNamespacedRow(
46
- namespacedRow,
47
- colRef,
48
- mainTableAlias,
49
- joinedTableAlias
50
- );
51
- if (nestedValue === void 0 && colRef in namespacedRow) {
52
- return namespacedRow[colRef];
53
- }
54
- return nestedValue;
55
- }
56
- return void 0;
57
- }
58
- if (operand && typeof operand === `object` && isFunctionCall(operand)) {
59
- const functionName = Object.keys(operand)[0];
60
- const args = operand[functionName];
61
- const evaluatedArgs = Array.isArray(args) ? args.map(
62
- (arg) => evaluateOperandOnNamespacedRow(
63
- namespacedRow,
64
- arg,
65
- mainTableAlias,
66
- joinedTableAlias
67
- )
68
- ) : evaluateOperandOnNamespacedRow(
69
- namespacedRow,
70
- args,
71
- mainTableAlias,
72
- joinedTableAlias
73
- );
74
- return evaluateFunction(
75
- functionName,
76
- evaluatedArgs
77
- );
78
- }
79
- if (operand && typeof operand === `object` && `value` in operand) {
80
- return operand.value;
81
- }
82
- return operand;
83
- }
84
- function extractJoinKey(row, operand, defaultTableAlias) {
85
- let keyValue;
86
- if (typeof operand === `string` && operand.startsWith(`@`)) {
87
- const columnRef = operand.substring(1);
88
- if (columnRef.includes(`.`)) {
89
- const [tableAlias, colName] = columnRef.split(`.`);
90
- if (tableAlias === defaultTableAlias) {
91
- keyValue = row[colName];
92
- } else {
93
- keyValue = void 0;
94
- }
95
- } else {
96
- keyValue = row[columnRef];
97
- }
98
- } else if (operand && typeof operand === `object` && `col` in operand) {
99
- const colRef = operand.col;
100
- if (typeof colRef === `string`) {
101
- if (colRef.includes(`.`)) {
102
- const [tableAlias, colName] = colRef.split(`.`);
103
- if (tableAlias === defaultTableAlias) {
104
- keyValue = row[colName];
105
- } else {
106
- keyValue = void 0;
107
- }
108
- } else {
109
- keyValue = row[colRef];
110
- }
111
- }
112
- } else {
113
- keyValue = operand;
114
- }
115
- return keyValue;
116
- }
117
- export {
118
- evaluateOperandOnNamespacedRow,
119
- extractJoinKey,
120
- extractValueFromNamespacedRow
121
- };
122
- //# sourceMappingURL=extractors.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"extractors.js","sources":["../../../src/query/extractors.ts"],"sourcesContent":["import { evaluateFunction, isFunctionCall } from \"./functions.js\"\nimport type { AllowedFunctionName, ConditionOperand } from \"./schema.js\"\n\n/**\n * Extracts a value from a nested row structure\n * @param namespacedRow The nested row structure\n * @param columnRef The column reference (may include table.column format)\n * @param mainTableAlias The main table alias to check first for columns without table reference\n * @param joinedTableAlias The joined table alias to check second for columns without table reference\n * @returns The extracted value or undefined if not found\n */\nexport function extractValueFromNamespacedRow(\n namespacedRow: Record<string, unknown>,\n columnRef: string,\n mainTableAlias?: string,\n joinedTableAlias?: string\n): unknown {\n // Check if it's a table.column reference\n if (columnRef.includes(`.`)) {\n const [tableAlias, colName] = columnRef.split(`.`) as [string, string]\n\n // Get the table data\n const tableData = namespacedRow[tableAlias] as\n | Record<string, unknown>\n | null\n | undefined\n\n if (!tableData) {\n return null\n }\n\n // Return the column value from that table\n const value = tableData[colName]\n return value\n } else {\n // If no table is specified, first try to find in the main table if provided\n if (mainTableAlias && namespacedRow[mainTableAlias]) {\n const mainTableData = namespacedRow[mainTableAlias] as Record<\n string,\n unknown\n >\n if (typeof mainTableData === `object` && columnRef in mainTableData) {\n return mainTableData[columnRef]\n }\n }\n\n // Then try the joined table if provided\n if (joinedTableAlias && namespacedRow[joinedTableAlias]) {\n const joinedTableData = namespacedRow[joinedTableAlias] as Record<\n string,\n unknown\n >\n if (typeof joinedTableData === `object` && columnRef in joinedTableData) {\n return joinedTableData[columnRef]\n }\n }\n\n // If not found in main or joined table, try to find the column in any table\n for (const [_tableAlias, tableData] of Object.entries(namespacedRow)) {\n if (\n tableData &&\n typeof tableData === `object` &&\n columnRef in (tableData as Record<string, unknown>)\n ) {\n return (tableData as Record<string, unknown>)[columnRef]\n }\n }\n return undefined\n }\n}\n\n/**\n * Evaluates an operand against a nested row structure\n */\nexport function evaluateOperandOnNamespacedRow(\n namespacedRow: Record<string, unknown>,\n operand: ConditionOperand,\n mainTableAlias?: string,\n joinedTableAlias?: string\n): unknown {\n // Handle column references\n if (typeof operand === `string` && operand.startsWith(`@`)) {\n const columnRef = operand.substring(1)\n return extractValueFromNamespacedRow(\n namespacedRow,\n columnRef,\n mainTableAlias,\n joinedTableAlias\n )\n }\n\n // Handle explicit column references\n if (operand && typeof operand === `object` && `col` in operand) {\n const colRef = (operand as { col: unknown }).col\n\n if (typeof colRef === `string`) {\n // First try to extract from nested row structure\n const nestedValue = extractValueFromNamespacedRow(\n namespacedRow,\n colRef,\n mainTableAlias,\n joinedTableAlias\n )\n\n // If not found in nested structure, check if it's a direct property of the row\n // This is important for HAVING clauses that reference aggregated values\n if (nestedValue === undefined && colRef in namespacedRow) {\n return namespacedRow[colRef]\n }\n\n return nestedValue\n }\n\n return undefined\n }\n\n // Handle function calls\n if (operand && typeof operand === `object` && isFunctionCall(operand)) {\n // Get the function name (the only key in the object)\n const functionName = Object.keys(operand)[0] as AllowedFunctionName\n // Get the arguments using type assertion with specific function name\n const args = (operand as any)[functionName]\n\n // If the arguments are a reference or another expression, evaluate them first\n const evaluatedArgs = Array.isArray(args)\n ? args.map((arg) =>\n evaluateOperandOnNamespacedRow(\n namespacedRow,\n arg as ConditionOperand,\n mainTableAlias,\n joinedTableAlias\n )\n )\n : evaluateOperandOnNamespacedRow(\n namespacedRow,\n args as ConditionOperand,\n mainTableAlias,\n joinedTableAlias\n )\n\n // Call the function with the evaluated arguments\n return evaluateFunction(\n functionName,\n evaluatedArgs as ConditionOperand | Array<ConditionOperand>\n )\n }\n\n // Handle explicit literals\n if (operand && typeof operand === `object` && `value` in operand) {\n return (operand as { value: unknown }).value\n }\n\n // Handle literal values\n return operand\n}\n\n/**\n * Extracts a join key value from a row based on the operand\n * @param row The data row (not nested)\n * @param operand The operand to extract the key from\n * @param defaultTableAlias The default table alias\n * @returns The extracted key value\n */\nexport function extractJoinKey<T extends Record<string, unknown>>(\n row: T,\n operand: ConditionOperand,\n defaultTableAlias?: string\n): unknown {\n let keyValue: unknown\n\n // Handle column references (e.g., \"@orders.id\" or \"@id\")\n if (typeof operand === `string` && operand.startsWith(`@`)) {\n const columnRef = operand.substring(1)\n\n // If it contains a dot, extract the table and column\n if (columnRef.includes(`.`)) {\n const [tableAlias, colName] = columnRef.split(`.`) as [string, string]\n // If this is referencing the current table, extract from row directly\n if (tableAlias === defaultTableAlias) {\n keyValue = row[colName]\n } else {\n // This might be a column from another table, return undefined\n keyValue = undefined\n }\n } else {\n // No table specified, look directly in the row\n keyValue = row[columnRef]\n }\n } else if (operand && typeof operand === `object` && `col` in operand) {\n // Handle explicit column references like { col: \"orders.id\" } or { col: \"id\" }\n const colRef = (operand as { col: unknown }).col\n\n if (typeof colRef === `string`) {\n if (colRef.includes(`.`)) {\n const [tableAlias, colName] = colRef.split(`.`) as [string, string]\n // If this is referencing the current table, extract from row directly\n if (tableAlias === defaultTableAlias) {\n keyValue = row[colName]\n } else {\n // This might be a column from another table, return undefined\n keyValue = undefined\n }\n } else {\n // No table specified, look directly in the row\n keyValue = row[colRef]\n }\n }\n } else {\n // Handle literals or other types\n keyValue = operand\n }\n\n return keyValue\n}\n"],"names":[],"mappings":"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"}
@@ -1,21 +0,0 @@
1
- import { AllowedFunctionName } from './schema.js';
2
- /**
3
- * Evaluates a function call with the given name and arguments
4
- * @param functionName The name of the function to evaluate
5
- * @param arg The arguments to pass to the function
6
- * @returns The result of the function call
7
- */
8
- export declare function evaluateFunction(functionName: AllowedFunctionName, arg: unknown): unknown;
9
- /**
10
- * Determines if an object is a function call
11
- * @param obj The object to check
12
- * @returns True if the object is a function call, false otherwise
13
- */
14
- export declare function isFunctionCall(obj: unknown): boolean;
15
- /**
16
- * Extracts the function name and argument from a function call object.
17
- */
18
- export declare function extractFunctionCall(obj: Record<string, unknown>): {
19
- functionName: AllowedFunctionName;
20
- argument: unknown;
21
- };
@@ -1,152 +0,0 @@
1
- function upperFunction(arg) {
2
- if (typeof arg !== `string`) {
3
- throw new Error(`UPPER function expects a string argument`);
4
- }
5
- return arg.toUpperCase();
6
- }
7
- function lowerFunction(arg) {
8
- if (typeof arg !== `string`) {
9
- throw new Error(`LOWER function expects a string argument`);
10
- }
11
- return arg.toLowerCase();
12
- }
13
- function lengthFunction(arg) {
14
- if (typeof arg === `string` || Array.isArray(arg)) {
15
- return arg.length;
16
- }
17
- throw new Error(`LENGTH function expects a string or array argument`);
18
- }
19
- function concatFunction(arg) {
20
- if (!Array.isArray(arg)) {
21
- throw new Error(`CONCAT function expects an array of string arguments`);
22
- }
23
- if (arg.length === 0) {
24
- return ``;
25
- }
26
- for (let i = 0; i < arg.length; i++) {
27
- if (arg[i] !== null && arg[i] !== void 0 && typeof arg[i] !== `string`) {
28
- throw new Error(
29
- `CONCAT function expects all arguments to be strings, but argument at position ${i} is ${typeof arg[i]}`
30
- );
31
- }
32
- }
33
- return arg.map((str) => str === null || str === void 0 ? `` : str).join(``);
34
- }
35
- function coalesceFunction(arg) {
36
- if (!Array.isArray(arg)) {
37
- throw new Error(`COALESCE function expects an array of arguments`);
38
- }
39
- if (arg.length === 0) {
40
- return null;
41
- }
42
- for (const value of arg) {
43
- if (value !== null && value !== void 0) {
44
- return value;
45
- }
46
- }
47
- return null;
48
- }
49
- function dateFunction(arg) {
50
- if (arg instanceof Date) {
51
- return arg;
52
- }
53
- if (arg === null || arg === void 0) {
54
- return null;
55
- }
56
- if (typeof arg === `string` || typeof arg === `number`) {
57
- const date = new Date(arg);
58
- if (isNaN(date.getTime())) {
59
- throw new Error(`DATE function could not parse "${arg}" as a valid date`);
60
- }
61
- return date;
62
- }
63
- throw new Error(`DATE function expects a string, number, or Date argument`);
64
- }
65
- function jsonExtractFunction(arg) {
66
- if (!Array.isArray(arg) || arg.length < 1) {
67
- throw new Error(
68
- `JSON_EXTRACT function expects an array with at least one element [jsonInput, ...pathElements]`
69
- );
70
- }
71
- const [jsonInput, ...pathElements] = arg;
72
- if (jsonInput === null || jsonInput === void 0) {
73
- return null;
74
- }
75
- let jsonData;
76
- if (typeof jsonInput === `string`) {
77
- try {
78
- jsonData = JSON.parse(jsonInput);
79
- } catch (error) {
80
- throw new Error(
81
- `JSON_EXTRACT function could not parse JSON string: ${error instanceof Error ? error.message : String(error)}`
82
- );
83
- }
84
- } else if (typeof jsonInput === `object`) {
85
- jsonData = jsonInput;
86
- } else {
87
- throw new Error(
88
- `JSON_EXTRACT function expects a JSON string or object as the first argument`
89
- );
90
- }
91
- if (pathElements.length === 0) {
92
- return jsonData;
93
- }
94
- let current = jsonData;
95
- for (let i = 0; i < pathElements.length; i++) {
96
- const pathElement = pathElements[i];
97
- if (typeof pathElement !== `string`) {
98
- throw new Error(
99
- `JSON_EXTRACT function expects path elements to be strings, but element at position ${i + 1} is ${typeof pathElement}`
100
- );
101
- }
102
- if (current === null || current === void 0 || typeof current !== `object`) {
103
- return null;
104
- }
105
- current = current[pathElement];
106
- }
107
- return current === void 0 ? null : current;
108
- }
109
- function orderIndexFunction(arg) {
110
- if (arg !== `numeric` && arg !== `fractional` && arg !== true && arg !== `default`) {
111
- throw new Error(
112
- `ORDER_INDEX function expects "numeric", "fractional", "default", or true as argument`
113
- );
114
- }
115
- return null;
116
- }
117
- const functionImplementations = {
118
- // Map function names to their implementation functions
119
- DATE: dateFunction,
120
- JSON_EXTRACT: jsonExtractFunction,
121
- JSON_EXTRACT_PATH: jsonExtractFunction,
122
- // Alias for JSON_EXTRACT
123
- UPPER: upperFunction,
124
- LOWER: lowerFunction,
125
- COALESCE: coalesceFunction,
126
- CONCAT: concatFunction,
127
- LENGTH: lengthFunction,
128
- ORDER_INDEX: orderIndexFunction
129
- };
130
- function evaluateFunction(functionName, arg) {
131
- const implementation = functionImplementations[functionName];
132
- if (!implementation) {
133
- throw new Error(`Unknown function: ${functionName}`);
134
- }
135
- return implementation(arg);
136
- }
137
- function isFunctionCall(obj) {
138
- if (!obj || typeof obj !== `object`) {
139
- return false;
140
- }
141
- const keys = Object.keys(obj);
142
- if (keys.length !== 1) {
143
- return false;
144
- }
145
- const functionName = keys[0];
146
- return Object.keys(functionImplementations).includes(functionName);
147
- }
148
- export {
149
- evaluateFunction,
150
- isFunctionCall
151
- };
152
- //# sourceMappingURL=functions.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"functions.js","sources":["../../../src/query/functions.ts"],"sourcesContent":["import type { AllowedFunctionName } from \"./schema.js\"\n\n/**\n * Type for function implementations\n */\ntype FunctionImplementation = (arg: unknown) => unknown\n\n/**\n * Converts a string to uppercase\n */\nfunction upperFunction(arg: unknown): string {\n if (typeof arg !== `string`) {\n throw new Error(`UPPER function expects a string argument`)\n }\n return arg.toUpperCase()\n}\n\n/**\n * Converts a string to lowercase\n */\nfunction lowerFunction(arg: unknown): string {\n if (typeof arg !== `string`) {\n throw new Error(`LOWER function expects a string argument`)\n }\n return arg.toLowerCase()\n}\n\n/**\n * Returns the length of a string or array\n */\nfunction lengthFunction(arg: unknown): number {\n if (typeof arg === `string` || Array.isArray(arg)) {\n return arg.length\n }\n\n throw new Error(`LENGTH function expects a string or array argument`)\n}\n\n/**\n * Concatenates multiple strings\n */\nfunction concatFunction(arg: unknown): string {\n if (!Array.isArray(arg)) {\n throw new Error(`CONCAT function expects an array of string arguments`)\n }\n\n if (arg.length === 0) {\n return ``\n }\n\n // Check that all arguments are strings\n for (let i = 0; i < arg.length; i++) {\n if (arg[i] !== null && arg[i] !== undefined && typeof arg[i] !== `string`) {\n throw new Error(\n `CONCAT function expects all arguments to be strings, but argument at position ${i} is ${typeof arg[i]}`\n )\n }\n }\n\n // Concatenate strings, treating null and undefined as empty strings\n return arg\n .map((str) => (str === null || str === undefined ? `` : str))\n .join(``)\n}\n\n/**\n * Returns the first non-null, non-undefined value from an array\n */\nfunction coalesceFunction(arg: unknown): unknown {\n if (!Array.isArray(arg)) {\n throw new Error(`COALESCE function expects an array of arguments`)\n }\n\n if (arg.length === 0) {\n return null\n }\n\n // Return the first non-null, non-undefined value\n for (const value of arg) {\n if (value !== null && value !== undefined) {\n return value\n }\n }\n\n // If all values were null or undefined, return null\n return null\n}\n\n/**\n * Creates or converts a value to a Date object\n */\nfunction dateFunction(arg: unknown): Date | null {\n // If the argument is already a Date, return it\n if (arg instanceof Date) {\n return arg\n }\n\n // If the argument is null or undefined, return null\n if (arg === null || arg === undefined) {\n return null\n }\n\n // Handle string and number conversions\n if (typeof arg === `string` || typeof arg === `number`) {\n const date = new Date(arg)\n\n // Check if the date is valid\n if (isNaN(date.getTime())) {\n throw new Error(`DATE function could not parse \"${arg}\" as a valid date`)\n }\n\n return date\n }\n\n throw new Error(`DATE function expects a string, number, or Date argument`)\n}\n\n/**\n * Extracts a value from a JSON string or object using a path.\n * Similar to PostgreSQL's json_extract_path function.\n *\n * Usage: JSON_EXTRACT([jsonInput, 'path', 'to', 'property'])\n * Example: JSON_EXTRACT(['{\"user\": {\"name\": \"John\"}}', 'user', 'name']) returns \"John\"\n */\nfunction jsonExtractFunction(arg: unknown): unknown {\n if (!Array.isArray(arg) || arg.length < 1) {\n throw new Error(\n `JSON_EXTRACT function expects an array with at least one element [jsonInput, ...pathElements]`\n )\n }\n\n const [jsonInput, ...pathElements] = arg\n\n // Handle null or undefined input\n if (jsonInput === null || jsonInput === undefined) {\n return null\n }\n\n // Parse JSON if it's a string\n let jsonData: any\n\n if (typeof jsonInput === `string`) {\n try {\n jsonData = JSON.parse(jsonInput)\n } catch (error) {\n throw new Error(\n `JSON_EXTRACT function could not parse JSON string: ${error instanceof Error ? error.message : String(error)}`\n )\n }\n } else if (typeof jsonInput === `object`) {\n // If already an object, use it directly\n jsonData = jsonInput\n } else {\n throw new Error(\n `JSON_EXTRACT function expects a JSON string or object as the first argument`\n )\n }\n\n // If no path elements, return the parsed JSON\n if (pathElements.length === 0) {\n return jsonData\n }\n\n // Navigate through the path elements\n let current = jsonData\n\n for (let i = 0; i < pathElements.length; i++) {\n const pathElement = pathElements[i]\n\n // Path elements should be strings\n if (typeof pathElement !== `string`) {\n throw new Error(\n `JSON_EXTRACT function expects path elements to be strings, but element at position ${i + 1} is ${typeof pathElement}`\n )\n }\n\n // If current node is null or undefined, or not an object, we can't navigate further\n if (\n current === null ||\n current === undefined ||\n typeof current !== `object`\n ) {\n return null\n }\n\n // Access property\n current = current[pathElement]\n }\n\n // Return null instead of undefined for consistency\n return current === undefined ? null : current\n}\n\n/**\n * Placeholder function for ORDER_INDEX\n * This function doesn't do anything when called directly, as the actual index\n * is provided by the orderBy operator during query execution.\n * The argument can be 'numeric', 'fractional', or any truthy value (defaults to 'numeric')\n */\nfunction orderIndexFunction(arg: unknown): null {\n // This is just a placeholder - the actual index is provided by the orderBy operator\n // The function validates that the argument is one of the expected values\n if (\n arg !== `numeric` &&\n arg !== `fractional` &&\n arg !== true &&\n arg !== `default`\n ) {\n throw new Error(\n `ORDER_INDEX function expects \"numeric\", \"fractional\", \"default\", or true as argument`\n )\n }\n return null\n}\n\n/**\n * Map of function names to their implementations\n */\nconst functionImplementations: Record<\n AllowedFunctionName,\n FunctionImplementation\n> = {\n // Map function names to their implementation functions\n DATE: dateFunction,\n JSON_EXTRACT: jsonExtractFunction,\n JSON_EXTRACT_PATH: jsonExtractFunction, // Alias for JSON_EXTRACT\n UPPER: upperFunction,\n LOWER: lowerFunction,\n COALESCE: coalesceFunction,\n CONCAT: concatFunction,\n LENGTH: lengthFunction,\n ORDER_INDEX: orderIndexFunction,\n}\n\n/**\n * Evaluates a function call with the given name and arguments\n * @param functionName The name of the function to evaluate\n * @param arg The arguments to pass to the function\n * @returns The result of the function call\n */\nexport function evaluateFunction(\n functionName: AllowedFunctionName,\n arg: unknown\n): unknown {\n const implementation = functionImplementations[functionName] as\n | FunctionImplementation\n | undefined // Double check that the implementation is defined\n\n if (!implementation) {\n throw new Error(`Unknown function: ${functionName}`)\n }\n return implementation(arg)\n}\n\n/**\n * Determines if an object is a function call\n * @param obj The object to check\n * @returns True if the object is a function call, false otherwise\n */\nexport function isFunctionCall(obj: unknown): boolean {\n if (!obj || typeof obj !== `object`) {\n return false\n }\n\n const keys = Object.keys(obj)\n if (keys.length !== 1) {\n return false\n }\n\n const functionName = keys[0] as string\n\n // Check if the key is one of the allowed function names\n return Object.keys(functionImplementations).includes(functionName)\n}\n\n/**\n * Extracts the function name and argument from a function call object.\n */\nexport function extractFunctionCall(obj: Record<string, unknown>): {\n functionName: AllowedFunctionName\n argument: unknown\n} {\n const keys = Object.keys(obj)\n if (keys.length !== 1) {\n throw new Error(`Invalid function call: object must have exactly one key`)\n }\n\n const functionName = keys[0] as AllowedFunctionName\n if (!Object.keys(functionImplementations).includes(functionName)) {\n throw new Error(`Invalid function name: ${functionName}`)\n }\n\n return {\n functionName,\n argument: obj[functionName],\n }\n}\n"],"names":[],"mappings":"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"}
@@ -1,40 +0,0 @@
1
- import { ConditionOperand, Query } from './schema.js';
2
- import { NamespacedAndKeyedStream } from '../types.js';
3
- /**
4
- * Process the groupBy clause in a D2QL query
5
- */
6
- export declare function processGroupBy(pipeline: NamespacedAndKeyedStream, query: Query, mainTableAlias: string): NamespacedAndKeyedStream;
7
- /**
8
- * Helper function to get an aggregate function based on the function name
9
- */
10
- export declare function getAggregateFunction(functionName: string, columnRef: string | ConditionOperand, mainTableAlias: string): {
11
- preMap: (data: [string, Record<string, unknown>]) => number;
12
- reduce: (values: [number, number][]) => number;
13
- postMap?: ((result: number) => number) | undefined;
14
- } | {
15
- pipe: (stream: import('@electric-sql/d2mini').IStreamBuilder<[string, Record<string, unknown>]>) => import('@electric-sql/d2mini').IStreamBuilder<import('@electric-sql/d2mini').KeyValue<string, number>>;
16
- } | {
17
- preMap: (data: [string, Record<string, unknown>]) => {
18
- sum: number;
19
- count: number;
20
- };
21
- reduce: (values: [{
22
- sum: number;
23
- count: number;
24
- }, number][]) => {
25
- sum: number;
26
- count: number;
27
- };
28
- postMap?: ((result: {
29
- sum: number;
30
- count: number;
31
- }) => number) | undefined;
32
- } | {
33
- preMap: (data: [string, Record<string, unknown>]) => number[];
34
- reduce: (values: [number[], number][]) => number[];
35
- postMap?: ((result: number[]) => number) | undefined;
36
- } | {
37
- preMap: (data: [string, Record<string, unknown>]) => Map<number, number>;
38
- reduce: (values: [Map<number, number>, number][]) => Map<number, number>;
39
- postMap?: ((result: Map<number, number>) => number) | undefined;
40
- };