@tanstack/table-core 9.0.0-beta.46 → 9.0.0-beta.47

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 (116) hide show
  1. package/dist/features/column-filtering/columnFilteringFeature.types.d.cts +43 -3
  2. package/dist/features/column-filtering/columnFilteringFeature.types.d.ts +43 -3
  3. package/dist/features/column-filtering/columnFilteringFeature.utils.cjs +18 -9
  4. package/dist/features/column-filtering/columnFilteringFeature.utils.cjs.map +1 -1
  5. package/dist/features/column-filtering/columnFilteringFeature.utils.d.cts +6 -2
  6. package/dist/features/column-filtering/columnFilteringFeature.utils.d.ts +6 -2
  7. package/dist/features/column-filtering/columnFilteringFeature.utils.js +18 -9
  8. package/dist/features/column-filtering/columnFilteringFeature.utils.js.map +1 -1
  9. package/dist/features/column-filtering/createFilteredRowModel.cjs +7 -2
  10. package/dist/features/column-filtering/createFilteredRowModel.cjs.map +1 -1
  11. package/dist/features/column-filtering/createFilteredRowModel.d.cts +6 -2
  12. package/dist/features/column-filtering/createFilteredRowModel.d.ts +6 -2
  13. package/dist/features/column-filtering/createFilteredRowModel.js +7 -2
  14. package/dist/features/column-filtering/createFilteredRowModel.js.map +1 -1
  15. package/dist/features/column-grouping/columnGroupingFeature.types.d.cts +41 -3
  16. package/dist/features/column-grouping/columnGroupingFeature.types.d.ts +41 -3
  17. package/dist/features/column-grouping/columnGroupingFeature.utils.cjs +17 -3
  18. package/dist/features/column-grouping/columnGroupingFeature.utils.cjs.map +1 -1
  19. package/dist/features/column-grouping/columnGroupingFeature.utils.d.cts +5 -0
  20. package/dist/features/column-grouping/columnGroupingFeature.utils.d.ts +5 -0
  21. package/dist/features/column-grouping/columnGroupingFeature.utils.js +17 -3
  22. package/dist/features/column-grouping/columnGroupingFeature.utils.js.map +1 -1
  23. package/dist/features/column-grouping/createGroupedRowModel.cjs +6 -3
  24. package/dist/features/column-grouping/createGroupedRowModel.cjs.map +1 -1
  25. package/dist/features/column-grouping/createGroupedRowModel.d.cts +6 -3
  26. package/dist/features/column-grouping/createGroupedRowModel.d.ts +6 -3
  27. package/dist/features/column-grouping/createGroupedRowModel.js +6 -3
  28. package/dist/features/column-grouping/createGroupedRowModel.js.map +1 -1
  29. package/dist/features/global-filtering/globalFilteringFeature.utils.cjs +3 -1
  30. package/dist/features/global-filtering/globalFilteringFeature.utils.cjs.map +1 -1
  31. package/dist/features/global-filtering/globalFilteringFeature.utils.d.cts +2 -6
  32. package/dist/features/global-filtering/globalFilteringFeature.utils.d.ts +2 -6
  33. package/dist/features/global-filtering/globalFilteringFeature.utils.js +3 -1
  34. package/dist/features/global-filtering/globalFilteringFeature.utils.js.map +1 -1
  35. package/dist/features/row-sorting/createSortedRowModel.cjs +6 -2
  36. package/dist/features/row-sorting/createSortedRowModel.cjs.map +1 -1
  37. package/dist/features/row-sorting/createSortedRowModel.d.cts +6 -2
  38. package/dist/features/row-sorting/createSortedRowModel.d.ts +6 -2
  39. package/dist/features/row-sorting/createSortedRowModel.js +6 -2
  40. package/dist/features/row-sorting/createSortedRowModel.js.map +1 -1
  41. package/dist/features/row-sorting/rowSortingFeature.types.d.cts +31 -2
  42. package/dist/features/row-sorting/rowSortingFeature.types.d.ts +31 -2
  43. package/dist/features/row-sorting/rowSortingFeature.utils.cjs +19 -4
  44. package/dist/features/row-sorting/rowSortingFeature.utils.cjs.map +1 -1
  45. package/dist/features/row-sorting/rowSortingFeature.utils.js +19 -4
  46. package/dist/features/row-sorting/rowSortingFeature.utils.js.map +1 -1
  47. package/dist/fns/aggregationFns.cjs +128 -57
  48. package/dist/fns/aggregationFns.cjs.map +1 -1
  49. package/dist/fns/aggregationFns.d.cts +72 -18
  50. package/dist/fns/aggregationFns.d.ts +72 -18
  51. package/dist/fns/aggregationFns.js +126 -58
  52. package/dist/fns/aggregationFns.js.map +1 -1
  53. package/dist/fns/filterFns.cjs +253 -96
  54. package/dist/fns/filterFns.cjs.map +1 -1
  55. package/dist/fns/filterFns.d.cts +126 -94
  56. package/dist/fns/filterFns.d.ts +126 -94
  57. package/dist/fns/filterFns.js +246 -97
  58. package/dist/fns/filterFns.js.map +1 -1
  59. package/dist/fns/sortFns.cjs +68 -21
  60. package/dist/fns/sortFns.cjs.map +1 -1
  61. package/dist/fns/sortFns.d.cts +48 -15
  62. package/dist/fns/sortFns.d.ts +48 -15
  63. package/dist/fns/sortFns.js +68 -22
  64. package/dist/fns/sortFns.js.map +1 -1
  65. package/dist/helpers/tableFeatures.cjs +5 -4
  66. package/dist/helpers/tableFeatures.cjs.map +1 -1
  67. package/dist/helpers/tableFeatures.d.cts +5 -4
  68. package/dist/helpers/tableFeatures.d.ts +5 -4
  69. package/dist/helpers/tableFeatures.js +5 -4
  70. package/dist/helpers/tableFeatures.js.map +1 -1
  71. package/dist/index.cjs +12 -0
  72. package/dist/index.d.cts +8 -8
  73. package/dist/index.d.ts +8 -8
  74. package/dist/index.js +4 -4
  75. package/dist/types/TableFeatures.d.cts +15 -7
  76. package/dist/types/TableFeatures.d.ts +15 -7
  77. package/dist/types/type-utils.d.cts +8 -1
  78. package/dist/types/type-utils.d.ts +8 -1
  79. package/package.json +1 -1
  80. package/skills/api-not-found/SKILL.md +1 -1
  81. package/skills/client-vs-server/SKILL.md +1 -1
  82. package/skills/column-faceting/SKILL.md +11 -5
  83. package/skills/column-filtering/SKILL.md +8 -3
  84. package/skills/column-ordering/SKILL.md +1 -1
  85. package/skills/column-pinning/SKILL.md +1 -1
  86. package/skills/column-resizing/SKILL.md +1 -1
  87. package/skills/column-sizing/SKILL.md +1 -1
  88. package/skills/column-visibility/SKILL.md +1 -1
  89. package/skills/core/SKILL.md +1 -1
  90. package/skills/custom-features/SKILL.md +1 -1
  91. package/skills/expanding/SKILL.md +1 -1
  92. package/skills/global-filtering/SKILL.md +3 -3
  93. package/skills/grouping/SKILL.md +8 -3
  94. package/skills/migrate-v8-to-v9/SKILL.md +7 -7
  95. package/skills/pagination/SKILL.md +1 -1
  96. package/skills/row-pinning/SKILL.md +1 -1
  97. package/skills/row-selection/SKILL.md +1 -1
  98. package/skills/sorting/SKILL.md +9 -3
  99. package/skills/table-features/SKILL.md +16 -13
  100. package/skills/typescript/SKILL.md +1 -1
  101. package/src/features/column-filtering/columnFilteringFeature.types.ts +60 -0
  102. package/src/features/column-filtering/columnFilteringFeature.utils.ts +33 -19
  103. package/src/features/column-filtering/createFilteredRowModel.ts +13 -3
  104. package/src/features/column-grouping/columnGroupingFeature.types.ts +63 -8
  105. package/src/features/column-grouping/columnGroupingFeature.utils.ts +43 -9
  106. package/src/features/column-grouping/createGroupedRowModel.ts +6 -3
  107. package/src/features/global-filtering/globalFilteringFeature.utils.ts +8 -0
  108. package/src/features/row-sorting/createSortedRowModel.ts +6 -2
  109. package/src/features/row-sorting/rowSortingFeature.types.ts +53 -1
  110. package/src/features/row-sorting/rowSortingFeature.utils.ts +45 -13
  111. package/src/fns/aggregationFns.ts +204 -146
  112. package/src/fns/filterFns.ts +361 -283
  113. package/src/fns/sortFns.ts +95 -78
  114. package/src/helpers/tableFeatures.ts +5 -4
  115. package/src/types/TableFeatures.ts +15 -7
  116. package/src/types/type-utils.ts +8 -0
@@ -1,30 +1,81 @@
1
+ import type {
2
+ AggregationFnDef,
3
+ CreatedAggregationFn,
4
+ } from '../features/column-grouping/columnGroupingFeature.types'
1
5
  import type { RowData } from '../types/type-utils'
2
6
  import type { TableFeatures } from '../types/TableFeatures'
3
7
  import type { Row } from '../types/Row'
4
8
 
9
+ /**
10
+ * Builds an `AggregationFn` from a value-level reducer plus optional
11
+ * `resolveDataValue` and `fromRows` settings.
12
+ *
13
+ * The `aggregate` reducer receives an array of the group rows' values, each
14
+ * already passed through `resolveDataValue` when one is defined. Keeping
15
+ * normalization in the resolver means a variant of an existing aggregation
16
+ * function only has to swap the resolver, not re-implement the computation.
17
+ *
18
+ * The definition is attached to the returned function, so a variant can be
19
+ * created by spreading a built-in aggregation function and overriding what
20
+ * differs. For example, a `min` that works on date columns:
21
+ *
22
+ * ```ts
23
+ * const earliest = constructAggregationFn({
24
+ * ...aggregationFn_min,
25
+ * resolveDataValue: (value) =>
26
+ * value instanceof Date ? value.getTime() : value,
27
+ * })
28
+ * ```
29
+ *
30
+ * The built-in `count`, `first`, and `last` aggregation functions are plain
31
+ * row-level functions instead: they read group position or size and never
32
+ * look at every value, so materializing a values array would be wasted work.
33
+ */
34
+ export function constructAggregationFn<
35
+ TFeatures extends TableFeatures = any,
36
+ TData extends RowData = any,
37
+ >(
38
+ def: AggregationFnDef<TFeatures, TData>,
39
+ ): CreatedAggregationFn<TFeatures, TData> {
40
+ const aggregationFn: CreatedAggregationFn<TFeatures, TData> = Object.assign(
41
+ <TRowFeatures extends TableFeatures, TRowData extends RowData>(
42
+ columnId: string,
43
+ leafRows: Array<Row<TRowFeatures, TRowData>>,
44
+ childRows: Array<Row<TRowFeatures, TRowData>>,
45
+ ): any => {
46
+ const rows = aggregationFn.fromRows === 'childRows' ? childRows : leafRows
47
+ const resolveDataValue = aggregationFn.resolveDataValue
48
+ const values: Array<any> = new Array(rows.length)
49
+ for (let i = 0; i < rows.length; i++) {
50
+ const value = rows[i]!.getValue(columnId)
51
+ values[i] = resolveDataValue ? resolveDataValue(value) : value
52
+ }
53
+ // The def's reducer is typed against the factory's TFeatures/TData;
54
+ // the caller's row generics are erased at this boundary.
55
+ return aggregationFn.aggregate(values, rows as any, columnId)
56
+ },
57
+ def,
58
+ )
59
+ return aggregationFn
60
+ }
61
+
5
62
  /**
6
63
  * Sums numeric child-row values for a grouped column.
7
64
  *
8
65
  * Non-number values contribute `0`. Child rows are used so nested group totals
9
66
  * can reuse already aggregated values.
10
67
  */
11
- export function aggregationFn_sum<
12
- TFeatures extends TableFeatures,
13
- TData extends RowData,
14
- >(
15
- columnId: string,
16
- _leafRows: Array<Row<TFeatures, TData>>,
17
- childRows: Array<Row<TFeatures, TData>>,
18
- ) {
19
- // It's faster to just add the aggregations together instead of
20
- // process leaf nodes individually
21
- let sumValue = 0
22
- for (let i = 0; i < childRows.length; i++) {
23
- const nextValue = childRows[i]!.getValue(columnId)
24
- sumValue += typeof nextValue === 'number' ? nextValue : 0
25
- }
26
- return sumValue
27
- }
68
+ export const aggregationFn_sum = constructAggregationFn({
69
+ fromRows: 'childRows',
70
+ aggregate: (values) => {
71
+ let sumValue = 0
72
+ for (let i = 0; i < values.length; i++) {
73
+ const nextValue = values[i]
74
+ sumValue += typeof nextValue === 'number' ? nextValue : 0
75
+ }
76
+ return sumValue
77
+ },
78
+ })
28
79
 
29
80
  /**
30
81
  * Finds the minimum numeric child-row value for a grouped column.
@@ -32,29 +83,24 @@ export function aggregationFn_sum<
32
83
  * Nullish and non-number values are ignored. Returns `undefined` when no
33
84
  * numeric value is found.
34
85
  */
35
- export function aggregationFn_min<
36
- TFeatures extends TableFeatures,
37
- TData extends RowData,
38
- >(
39
- columnId: string,
40
- _leafRows: Array<Row<TFeatures, TData>>,
41
- childRows: Array<Row<TFeatures, TData>>,
42
- ) {
43
- let minValue: number | undefined
44
-
45
- for (let i = 0; i < childRows.length; i++) {
46
- const value = childRows[i]!.getValue(columnId)
47
-
48
- if (
49
- typeof value === 'number' &&
50
- (minValue === undefined || value < minValue)
51
- ) {
52
- minValue = value
86
+ export const aggregationFn_min = constructAggregationFn({
87
+ fromRows: 'childRows',
88
+ aggregate: (values) => {
89
+ let minValue: number | undefined
90
+
91
+ for (let i = 0; i < values.length; i++) {
92
+ const value = values[i]
93
+ if (
94
+ typeof value === 'number' &&
95
+ (minValue === undefined || value < minValue)
96
+ ) {
97
+ minValue = value
98
+ }
53
99
  }
54
- }
55
100
 
56
- return minValue
57
- }
101
+ return minValue
102
+ },
103
+ })
58
104
 
59
105
  /**
60
106
  * Finds the maximum numeric child-row value for a grouped column.
@@ -62,28 +108,24 @@ export function aggregationFn_min<
62
108
  * Nullish and non-number values are ignored. Returns `undefined` when no
63
109
  * numeric value is found.
64
110
  */
65
- export function aggregationFn_max<
66
- TFeatures extends TableFeatures,
67
- TData extends RowData,
68
- >(
69
- columnId: string,
70
- _leafRows: Array<Row<TFeatures, TData>>,
71
- childRows: Array<Row<TFeatures, TData>>,
72
- ) {
73
- let maxValue: number | undefined
74
-
75
- for (let i = 0; i < childRows.length; i++) {
76
- const value = childRows[i]!.getValue(columnId)
77
- if (
78
- typeof value === 'number' &&
79
- (maxValue === undefined || value > maxValue)
80
- ) {
81
- maxValue = value
111
+ export const aggregationFn_max = constructAggregationFn({
112
+ fromRows: 'childRows',
113
+ aggregate: (values) => {
114
+ let maxValue: number | undefined
115
+
116
+ for (let i = 0; i < values.length; i++) {
117
+ const value = values[i]
118
+ if (
119
+ typeof value === 'number' &&
120
+ (maxValue === undefined || value > maxValue)
121
+ ) {
122
+ maxValue = value
123
+ }
82
124
  }
83
- }
84
125
 
85
- return maxValue
86
- }
126
+ return maxValue
127
+ },
128
+ })
87
129
 
88
130
  /**
89
131
  * Finds the numeric extent for a grouped column.
@@ -91,31 +133,27 @@ export function aggregationFn_max<
91
133
  * Returns `[min, max]`, where each entry is `undefined` when no numeric value is
92
134
  * present.
93
135
  */
94
- export function aggregationFn_extent<
95
- TFeatures extends TableFeatures,
96
- TData extends RowData,
97
- >(
98
- columnId: string,
99
- _leafRows: Array<Row<TFeatures, TData>>,
100
- childRows: Array<Row<TFeatures, TData>>,
101
- ) {
102
- let minValue: number | undefined
103
- let maxValue: number | undefined
104
-
105
- for (let i = 0; i < childRows.length; i++) {
106
- const value = childRows[i]!.getValue(columnId)
107
- if (typeof value === 'number') {
108
- if (minValue === undefined) {
109
- minValue = maxValue = value
110
- } else {
111
- if (minValue > value) minValue = value
112
- if (maxValue! < value) maxValue = value
136
+ export const aggregationFn_extent = constructAggregationFn({
137
+ fromRows: 'childRows',
138
+ aggregate: (values) => {
139
+ let minValue: number | undefined
140
+ let maxValue: number | undefined
141
+
142
+ for (let i = 0; i < values.length; i++) {
143
+ const value = values[i]
144
+ if (typeof value === 'number') {
145
+ if (minValue === undefined) {
146
+ minValue = maxValue = value
147
+ } else {
148
+ if (minValue > value) minValue = value
149
+ if (maxValue! < value) maxValue = value
150
+ }
113
151
  }
114
152
  }
115
- }
116
153
 
117
- return [minValue, maxValue]
118
- }
154
+ return [minValue, maxValue]
155
+ },
156
+ })
119
157
 
120
158
  /**
121
159
  * Averages numeric leaf-row values for a grouped column.
@@ -123,31 +161,30 @@ export function aggregationFn_extent<
123
161
  * Number-like values are coerced with unary `+`; nullish and non-numeric values
124
162
  * are ignored.
125
163
  */
126
- export function aggregationFn_mean<
127
- TFeatures extends TableFeatures,
128
- TData extends RowData,
129
- >(columnId: string, leafRows: Array<Row<TFeatures, TData>>) {
130
- let count = 0
131
- let sumValue = 0
132
-
133
- for (let i = 0; i < leafRows.length; i++) {
134
- const value = leafRows[i]!.getValue(columnId)
135
- if (value != null && typeof value === 'number') {
136
- ++count
137
- sumValue += value
138
- } else if (value != null) {
139
- const numValue = +value
140
- if (!Number.isNaN(numValue)) {
164
+ export const aggregationFn_mean = constructAggregationFn({
165
+ aggregate: (values) => {
166
+ let count = 0
167
+ let sumValue = 0
168
+
169
+ for (let i = 0; i < values.length; i++) {
170
+ const value = values[i]
171
+ if (value != null && typeof value === 'number') {
141
172
  ++count
142
- sumValue += numValue
173
+ sumValue += value
174
+ } else if (value != null) {
175
+ const numValue = +value
176
+ if (!Number.isNaN(numValue)) {
177
+ ++count
178
+ sumValue += numValue
179
+ }
143
180
  }
144
181
  }
145
- }
146
182
 
147
- if (count) return sumValue / count
183
+ if (count) return sumValue / count
148
184
 
149
- return
150
- }
185
+ return
186
+ },
187
+ })
151
188
 
152
189
  /**
153
190
  * Computes the median of numeric leaf-row values for a grouped column.
@@ -155,68 +192,52 @@ export function aggregationFn_mean<
155
192
  * All values must be numbers. If any value is non-numeric, or no leaf rows are
156
193
  * present, the result is `undefined`.
157
194
  */
158
- export function aggregationFn_median<
159
- TFeatures extends TableFeatures,
160
- TData extends RowData,
161
- >(columnId: string, leafRows: Array<Row<TFeatures, TData>>) {
162
- if (!leafRows.length) {
163
- return
164
- }
165
-
166
- const values: Array<number> = new Array(leafRows.length)
167
- for (let i = 0; i < leafRows.length; i++) {
168
- const v = leafRows[i]!.getValue(columnId)
169
- if (typeof v !== 'number') return
170
- values[i] = v
171
- }
172
-
173
- if (values.length === 1) {
174
- return values[0]
175
- }
176
-
177
- const mid = Math.floor(values.length / 2)
178
- values.sort((a, b) => a - b)
179
- return values.length % 2 !== 0
180
- ? values[mid]
181
- : (values[mid - 1]! + values[mid]!) / 2
182
- }
195
+ export const aggregationFn_median = constructAggregationFn({
196
+ aggregate: (values: Array<number>) => {
197
+ if (!values.length) {
198
+ return
199
+ }
200
+
201
+ for (let i = 0; i < values.length; i++) {
202
+ if (typeof values[i] !== 'number') return
203
+ }
204
+
205
+ if (values.length === 1) {
206
+ return values[0]
207
+ }
208
+
209
+ const mid = Math.floor(values.length / 2)
210
+ values.sort((a, b) => a - b)
211
+ return values.length % 2 !== 0
212
+ ? values[mid]
213
+ : (values[mid - 1]! + values[mid]!) / 2
214
+ },
215
+ })
183
216
 
184
217
  /**
185
218
  * Collects unique leaf-row values for a grouped column.
186
219
  *
187
220
  * Values are compared with JavaScript `Set` semantics.
188
221
  */
189
- export function aggregationFn_unique<
190
- TFeatures extends TableFeatures,
191
- TData extends RowData,
192
- >(columnId: string, leafRows: Array<Row<TFeatures, TData>>) {
193
- const set = new Set<unknown>()
194
- for (let i = 0; i < leafRows.length; i++) {
195
- set.add(leafRows[i]!.getValue(columnId))
196
- }
197
- return Array.from(set.values())
198
- }
222
+ export const aggregationFn_unique = constructAggregationFn({
223
+ aggregate: (values) => Array.from(new Set(values).values()),
224
+ })
199
225
 
200
226
  /**
201
227
  * Counts unique leaf-row values for a grouped column.
202
228
  *
203
229
  * Values are compared with JavaScript `Set` semantics.
204
230
  */
205
- export function aggregationFn_uniqueCount<
206
- TFeatures extends TableFeatures,
207
- TData extends RowData,
208
- >(columnId: string, leafRows: Array<Row<TFeatures, TData>>) {
209
- const set = new Set<unknown>()
210
- for (let i = 0; i < leafRows.length; i++) {
211
- set.add(leafRows[i]!.getValue(columnId))
212
- }
213
- return set.size
214
- }
231
+ export const aggregationFn_uniqueCount = constructAggregationFn({
232
+ aggregate: (values) => new Set(values).size,
233
+ })
215
234
 
216
235
  /**
217
236
  * Counts the number of leaf rows in the group.
218
237
  *
219
238
  * The column id is ignored because the result is based only on group size.
239
+ * This is a plain row-level function (not built with
240
+ * `constructAggregationFn`) because it never reads row values.
220
241
  */
221
242
  export function aggregationFn_count<
222
243
  TFeatures extends TableFeatures,
@@ -225,10 +246,45 @@ export function aggregationFn_count<
225
246
  return leafRows.length
226
247
  }
227
248
 
249
+ /**
250
+ * Returns the first leaf-row value for a grouped column.
251
+ *
252
+ * This is a plain row-level function (not built with
253
+ * `constructAggregationFn`) because it only reads one positional value.
254
+ */
255
+ export function aggregationFn_first<
256
+ TFeatures extends TableFeatures,
257
+ TData extends RowData,
258
+ >(columnId: string, leafRows: Array<Row<TFeatures, TData>>) {
259
+ return leafRows[0]?.getValue(columnId)
260
+ }
261
+
262
+ /**
263
+ * Returns the last leaf-row value for a grouped column.
264
+ *
265
+ * This is a plain row-level function (not built with
266
+ * `constructAggregationFn`) because it only reads one positional value.
267
+ */
268
+ export function aggregationFn_last<
269
+ TFeatures extends TableFeatures,
270
+ TData extends RowData,
271
+ >(columnId: string, leafRows: Array<Row<TFeatures, TData>>) {
272
+ return leafRows[leafRows.length - 1]?.getValue(columnId)
273
+ }
274
+
228
275
  /**
229
276
  * The built-in aggregation function registry.
230
277
  *
231
- * Pass this object to grouped row model creation or extend it with custom aggregation functions for grouped columns.
278
+ * Registering this full object opts out of tree-shaking: every built-in
279
+ * aggregation function ends up in your bundle. Prefer importing the
280
+ * `aggregationFn_*` functions you actually use and registering just those in
281
+ * the `aggregationFns` slot, or passing them directly to the `aggregationFn`
282
+ * column option.
283
+ *
284
+ * @deprecated Import individual `aggregationFn_*` functions instead for a
285
+ * smaller bundle. This export still works and is not going away in v9, but
286
+ * built-in name resolution (including `aggregationFn: 'auto'`) only finds
287
+ * functions you register yourself.
232
288
  */
233
289
  export const aggregationFns = {
234
290
  sum: aggregationFn_sum,
@@ -240,6 +296,8 @@ export const aggregationFns = {
240
296
  unique: aggregationFn_unique,
241
297
  uniqueCount: aggregationFn_uniqueCount,
242
298
  count: aggregationFn_count,
299
+ first: aggregationFn_first,
300
+ last: aggregationFn_last,
243
301
  }
244
302
 
245
303
  export type BuiltInAggregationFn = keyof typeof aggregationFns