@tanstack/vue-table 9.0.0-beta.40 → 9.0.0-beta.42

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.
@@ -1,415 +0,0 @@
1
- ---
2
- name: vue/getting-started
3
- description: >
4
- End-to-end first-table walkthrough for `@tanstack/vue-table` v9. Install the adapter, declare
5
- `features` via `tableFeatures({})` (row model factories and fn registries live here as slots),
6
- build a column helper with both `TFeatures` and `TData` generics, instantiate
7
- `useTable(options, selector?)` from a `<script setup>` block, and render with
8
- `<FlexRender :cell="cell" />` / `:header="header"`. New users land here, not on legacy v8
9
- names like `useVueTable`.
10
- type: lifecycle
11
- library: tanstack-table
12
- framework: vue
13
- library_version: '9.0.0-alpha.48'
14
- requires:
15
- - setup
16
- - column-definitions
17
- - state-management
18
- - vue/table-state
19
- sources:
20
- - docs/installation.md
21
- - docs/framework/vue/vue-table.md
22
- - docs/framework/vue/guide/table-state.md
23
- - examples/vue/basic-use-table/
24
- - examples/vue/basic-use-app-table/
25
- - packages/vue-table/src/useTable.ts
26
- ---
27
-
28
- # Getting Started with @tanstack/vue-table v9
29
-
30
- ## Dependencies
31
-
32
- ```bash
33
- pnpm add @tanstack/vue-table vue
34
- # Optional: external atoms / shared state
35
- pnpm add @tanstack/vue-store
36
- ```
37
-
38
- Vue 3 only. There is no `/legacy` entrypoint for Vue (that exists only for React); migrating
39
- from v8 is a direct rewrite — see `tanstack-table/vue/migrate-v8-to-v9`.
40
-
41
- ## Setup — minimum viable table
42
-
43
- ```vue
44
- <script setup lang="ts">
45
- import { ref } from 'vue'
46
- import {
47
- FlexRender,
48
- createColumnHelper,
49
- tableFeatures,
50
- useTable,
51
- } from '@tanstack/vue-table'
52
-
53
- type Person = { firstName: string; lastName: string; age: number }
54
-
55
- // Stable identities — declare at module scope (outside <script setup> blocks).
56
- const features = tableFeatures({}) // required — even when no features are used
57
- const columnHelper = createColumnHelper<typeof features, Person>() // note: TWO generics
58
-
59
- const columns = columnHelper.columns([
60
- columnHelper.accessor('firstName', { header: 'First' }),
61
- columnHelper.accessor('lastName', { header: 'Last' }),
62
- columnHelper.accessor('age', { header: 'Age' }),
63
- ])
64
-
65
- const data = ref<Person[]>([
66
- { firstName: 'tanner', lastName: 'linsley', age: 24 },
67
- { firstName: 'kevin', lastName: 'vandy', age: 28 },
68
- ])
69
-
70
- const table = useTable({
71
- features,
72
- columns,
73
- data,
74
- })
75
- </script>
76
-
77
- <template>
78
- <table>
79
- <thead>
80
- <tr v-for="hg in table.getHeaderGroups()" :key="hg.id">
81
- <th v-for="h in hg.headers" :key="h.id">
82
- <FlexRender v-if="!h.isPlaceholder" :header="h" />
83
- </th>
84
- </tr>
85
- </thead>
86
- <tbody>
87
- <tr v-for="row in table.getRowModel().rows" :key="row.id">
88
- <td v-for="cell in row.getAllCells()" :key="cell.id">
89
- <FlexRender :cell="cell" />
90
- </td>
91
- </tr>
92
- </tbody>
93
- </table>
94
- </template>
95
- ```
96
-
97
- Source: `examples/vue/basic-use-table/src/App.tsx`, `docs/framework/vue/vue-table.md`.
98
-
99
- ### What's mandatory in v9
100
-
101
- - `features` — built via `tableFeatures({...})`. Empty object is fine for a no-features table,
102
- but the option key must exist. Row model factories and fn registries go here as slots, not
103
- as a separate `rowModels` option.
104
- - `createColumnHelper<typeof features, Person>()` — two generics, in that order. The v8 single
105
- generic does not compile.
106
-
107
- ## Core Patterns
108
-
109
- ### 1. Add a feature: sorting
110
-
111
- ```vue
112
- <script setup lang="ts">
113
- import { ref } from 'vue'
114
- import {
115
- FlexRender,
116
- createColumnHelper,
117
- createSortedRowModel,
118
- rowSortingFeature,
119
- sortFns,
120
- tableFeatures,
121
- useTable,
122
- } from '@tanstack/vue-table'
123
-
124
- const features = tableFeatures({
125
- rowSortingFeature,
126
- sortedRowModel: createSortedRowModel(),
127
- sortFns,
128
- })
129
- const columnHelper = createColumnHelper<typeof features, Person>()
130
- const columns = columnHelper.columns([
131
- columnHelper.accessor('firstName', { header: 'First' }),
132
- columnHelper.accessor('age', { header: 'Age' }),
133
- ])
134
-
135
- const data = ref<Person[]>([])
136
-
137
- const table = useTable({
138
- features,
139
- columns,
140
- data,
141
- })
142
- </script>
143
-
144
- <template>
145
- <thead>
146
- <tr v-for="hg in table.getHeaderGroups()" :key="hg.id">
147
- <th
148
- v-for="h in hg.headers"
149
- :key="h.id"
150
- :class="{ sortable: h.column.getCanSort() }"
151
- @click="h.column.getToggleSortingHandler()?.($event)"
152
- >
153
- <FlexRender v-if="!h.isPlaceholder" :header="h" />
154
- <span v-if="h.column.getIsSorted() === 'asc'"> 🔼</span>
155
- <span v-if="h.column.getIsSorted() === 'desc'"> 🔽</span>
156
- </th>
157
- </tr>
158
- </thead>
159
- </template>
160
- ```
161
-
162
- Three rules:
163
-
164
- 1. Register the feature in `features` (`rowSortingFeature`) along with its row model factory
165
- and fn registry as slots on the same object.
166
- 2. The fn registry (`sortFns`) is what makes filter/sort registries tree-shakeable in v9 — do
167
- not drop it.
168
- 3. Wire UI to the built-in API: `column.getToggleSortingHandler()`, `column.getIsSorted()`.
169
- Do not reimplement sort logic.
170
-
171
- Source: `docs/framework/vue/vue-table.md`, `examples/vue/sorting/`.
172
-
173
- ### 2. Compose features: pagination + filtering on top of sorting
174
-
175
- ```ts
176
- import {
177
- columnFilteringFeature,
178
- createFilteredRowModel,
179
- createPaginatedRowModel,
180
- createSortedRowModel,
181
- filterFns,
182
- rowPaginationFeature,
183
- rowSortingFeature,
184
- sortFns,
185
- tableFeatures,
186
- } from '@tanstack/vue-table'
187
-
188
- const features = tableFeatures({
189
- rowSortingFeature,
190
- rowPaginationFeature,
191
- columnFilteringFeature,
192
- sortedRowModel: createSortedRowModel(),
193
- filteredRowModel: createFilteredRowModel(),
194
- paginatedRowModel: createPaginatedRowModel(),
195
- sortFns,
196
- filterFns,
197
- })
198
- ```
199
-
200
- Then use `table.nextPage()`, `table.setPageIndex(0)`, `table.setColumnFilters(...)`,
201
- `table.setSorting(...)`. The library exposes a state-transition API for every feature — use it.
202
-
203
- ### 3. App-scoped tables with `createTableHook`
204
-
205
- If multiple tables in your app share a `features` object (with its row model factories and conventions), prefer
206
- `createTableHook`. The hook factory returns `useAppTable`, `createAppColumnHelper`, plus
207
- context helpers (`useTableContext`, `useCellContext`, `useHeaderContext`).
208
-
209
- ```ts
210
- // src/hooks/table.ts
211
- import {
212
- createPaginatedRowModel,
213
- createSortedRowModel,
214
- createTableHook,
215
- rowPaginationFeature,
216
- rowSortingFeature,
217
- sortFns,
218
- tableFeatures,
219
- } from '@tanstack/vue-table'
220
-
221
- const features = tableFeatures({
222
- rowSortingFeature,
223
- rowPaginationFeature,
224
- sortedRowModel: createSortedRowModel(),
225
- paginatedRowModel: createPaginatedRowModel(),
226
- sortFns,
227
- })
228
-
229
- export const { useAppTable, createAppColumnHelper } = createTableHook({
230
- features,
231
- })
232
- ```
233
-
234
- ```vue
235
- <script setup lang="ts">
236
- import { useAppTable, createAppColumnHelper } from '@/hooks/table'
237
- import { ref } from 'vue'
238
-
239
- const columnHelper = createAppColumnHelper<Person>()
240
- const columns = columnHelper.columns([
241
- columnHelper.accessor('firstName', { header: 'First' }),
242
- ])
243
-
244
- const data = ref<Person[]>([])
245
- const table = useAppTable({ columns, data })
246
- </script>
247
-
248
- <template>
249
- <table>
250
- <thead>
251
- <tr v-for="hg in table.getHeaderGroups()" :key="hg.id">
252
- <th v-for="h in hg.headers" :key="h.id">
253
- <component :is="table.FlexRender" :header="h" />
254
- </th>
255
- </tr>
256
- </thead>
257
- </table>
258
- </template>
259
- ```
260
-
261
- Source: `examples/vue/basic-use-app-table/src/App.vue`,
262
- `examples/vue/composable-tables/src/hooks/table.ts`.
263
-
264
- ### 4. JSX render functions when templates get noisy
265
-
266
- Vue's JSX support is fine — pass `cell`/`header` props to `<FlexRender>` and the rest is the same.
267
-
268
- ```tsx
269
- // App.tsx
270
- import { defineComponent, ref } from 'vue'
271
- import { FlexRender, tableFeatures, useTable } from '@tanstack/vue-table'
272
-
273
- const features = tableFeatures({})
274
-
275
- export default defineComponent({
276
- setup() {
277
- const data = ref<Person[]>([])
278
- const table = useTable({
279
- features,
280
- columns,
281
- get data() {
282
- return data.value
283
- },
284
- })
285
-
286
- return () => (
287
- <table>
288
- <tbody>
289
- {table.getRowModel().rows.map((row) => (
290
- <tr key={row.id}>
291
- {row.getAllCells().map((cell) => (
292
- <td key={cell.id}>
293
- <FlexRender cell={cell} />
294
- </td>
295
- ))}
296
- </tr>
297
- ))}
298
- </tbody>
299
- </table>
300
- )
301
- },
302
- })
303
- ```
304
-
305
- Source: `examples/vue/basic-use-table/src/App.tsx`.
306
-
307
- ## Common Mistakes
308
-
309
- ### Omitting `features` (CRITICAL)
310
-
311
- ```ts
312
- // ❌ TS error: Property 'features' is missing in type ...
313
- const table = useTable({ columns, data })
314
-
315
- // ✅
316
- const features = tableFeatures({})
317
- const table = useTable({ features, columns, data })
318
- ```
319
-
320
- `features` is required even for the simplest table.
321
-
322
- ### Wrong `createColumnHelper` arity (CRITICAL)
323
-
324
- ```ts
325
- // ❌ v8 single-generic shape — does not compile in v9.
326
- const columnHelper = createColumnHelper<Person>()
327
-
328
- // ✅ v9 — TFeatures FIRST, then TData.
329
- const columnHelper = createColumnHelper<typeof features, Person>()
330
- ```
331
-
332
- ### Omitting the `*Fns` registry from `tableFeatures` (CRITICAL)
333
-
334
- ```ts
335
- // ❌ TS error / runtime missing fns — sort is a no-op.
336
- const features = tableFeatures({
337
- rowSortingFeature,
338
- sortedRowModel: createSortedRowModel(),
339
- // sortFns missing!
340
- })
341
-
342
- // ✅ Register the fn map as a slot alongside the factory.
343
- const features = tableFeatures({
344
- rowSortingFeature,
345
- columnFilteringFeature,
346
- sortedRowModel: createSortedRowModel(),
347
- filteredRowModel: createFilteredRowModel(),
348
- sortFns,
349
- filterFns,
350
- })
351
- ```
352
-
353
- This is what makes v9 tree-shakeable. Filter/sort/aggregation registries are open-ended — do
354
- not cite a number of built-in fns; just pass `filterFns` / `sortFns` / `aggregationFns`.
355
-
356
- ### "API missing" because the feature is not in `features` (CRITICAL, v9-specific)
357
-
358
- ```ts
359
- // ❌ `rowSortingFeature` not registered → `table.setSorting` is `undefined` and a TS error.
360
- const features = tableFeatures({})
361
- const table = useTable({ features, columns, data })
362
- table.setSorting([{ id: 'age', desc: true }]) // missing
363
-
364
- // ✅ Register the feature, its row model factory, and its fn registry in tableFeatures.
365
- const features = tableFeatures({
366
- rowSortingFeature,
367
- sortedRowModel: createSortedRowModel(),
368
- sortFns,
369
- })
370
- const table = useTable({ features, columns, data })
371
- ```
372
-
373
- This is the #1 v9-specific failure mode — features must be declared to surface their APIs.
374
-
375
- ### Reaching for `useVueTable` (HIGH — pre-v9 hallucination)
376
-
377
- `useVueTable` was the v8 name. v9 renamed every adapter to `useTable`. There is no Vue
378
- `/legacy` entrypoint — migration is a rewrite.
379
-
380
- ### Reimplementing built-in state transitions (CRITICAL — #1 AI tell)
381
-
382
- ```ts
383
- // ❌ Hand-rolled sort state.
384
- const sorting = ref<SortingState>([])
385
- const sorted = computed(() => [...data.value].sort(/* … */))
386
-
387
- // ✅ Use the API: table.setSorting / table.toggleSorting / column.getToggleSortingHandler.
388
- ```
389
-
390
- TanStack Table IS the state coordinator. Built-in APIs handle invariants, reset semantics, and
391
- multi-sort correctly.
392
-
393
- ### Unstable references for `features`, `columns`, `data`
394
-
395
- ```vue
396
- <script setup>
397
- // ❌ New identity every component mount, breaks internal memoization.
398
- const features = tableFeatures({ rowSortingFeature })
399
- const columns = [...]
400
- </script>
401
- ```
402
-
403
- Declare `features`, `columnHelper`, and `columns` at **module scope** (top of file, outside
404
- `<script setup>`). For `data`, a stable `ref` is fine — the adapter watches its `.value`.
405
-
406
- ### Using `useReactTable` / `getCoreRowModel()` as an option (CRITICAL — v8 muscle memory)
407
-
408
- Pure v8. Doesn't exist in `@tanstack/vue-table`. See `migrate-v8-to-v9`.
409
-
410
- ## See Also
411
-
412
- - `tanstack-table/vue/table-state` — the reactivity model you'll use as soon as you add features
413
- - `tanstack-table/vue/production-readiness` — once it works, optimize bundle + re-renders
414
- - `tanstack-table/vue/migrate-v8-to-v9` — coming from `useVueTable`
415
- - `tanstack-table/table-core/column-definitions` — column helper deep dive