@contractspec/bundle.library 3.9.7 → 3.9.9

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 (71) hide show
  1. package/.turbo/turbo-build.log +186 -174
  2. package/CHANGELOG.md +96 -0
  3. package/dist/components/docs/DocsIndexPage.js +2 -2
  4. package/dist/components/docs/docsManifest.js +1 -1
  5. package/dist/components/docs/getting-started/DataViewTutorialPage.js +117 -6
  6. package/dist/components/docs/getting-started/index.js +130 -19
  7. package/dist/components/docs/guides/GuideDataExchangeImportTemplatesPage.content.d.ts +6 -0
  8. package/dist/components/docs/guides/GuideDataExchangeImportTemplatesPage.content.js +176 -0
  9. package/dist/components/docs/guides/GuideDataExchangeImportTemplatesPage.d.ts +1 -0
  10. package/dist/components/docs/guides/GuideDataExchangeImportTemplatesPage.js +176 -0
  11. package/dist/components/docs/guides/GuidesIndexPage.js +2 -2
  12. package/dist/components/docs/guides/index.d.ts +1 -0
  13. package/dist/components/docs/guides/index.js +220 -46
  14. package/dist/components/docs/index.js +1195 -276
  15. package/dist/components/docs/libraries/LibrariesApplicationShellPage.content.d.ts +33 -0
  16. package/dist/components/docs/libraries/LibrariesApplicationShellPage.content.js +236 -0
  17. package/dist/components/docs/libraries/LibrariesApplicationShellPage.d.ts +1 -0
  18. package/dist/components/docs/libraries/LibrariesApplicationShellPage.js +236 -0
  19. package/dist/components/docs/libraries/LibrariesDataViewsPage.js +130 -6
  20. package/dist/components/docs/libraries/LibrariesDesignSystemPage.js +102 -3
  21. package/dist/components/docs/libraries/LibrariesOverviewPage.js +1 -1
  22. package/dist/components/docs/libraries/LibrariesPersonalizationPage.js +58 -4
  23. package/dist/components/docs/libraries/LibrariesTranslationRuntimePage.content.d.ts +10 -0
  24. package/dist/components/docs/libraries/LibrariesTranslationRuntimePage.content.js +43 -0
  25. package/dist/components/docs/libraries/LibrariesTranslationRuntimePage.d.ts +1 -0
  26. package/dist/components/docs/libraries/LibrariesTranslationRuntimePage.js +43 -0
  27. package/dist/components/docs/libraries/index.d.ts +2 -0
  28. package/dist/components/docs/libraries/index.js +616 -64
  29. package/dist/components/docs/specs/SpecsDataViewsPage.js +85 -3
  30. package/dist/components/docs/specs/index.js +96 -14
  31. package/dist/index.js +1206 -287
  32. package/dist/node/components/docs/DocsIndexPage.js +2 -2
  33. package/dist/node/components/docs/docsManifest.js +1 -1
  34. package/dist/node/components/docs/getting-started/DataViewTutorialPage.js +117 -6
  35. package/dist/node/components/docs/getting-started/index.js +130 -19
  36. package/dist/node/components/docs/guides/GuideDataExchangeImportTemplatesPage.content.js +175 -0
  37. package/dist/node/components/docs/guides/GuideDataExchangeImportTemplatesPage.js +175 -0
  38. package/dist/node/components/docs/guides/GuidesIndexPage.js +2 -2
  39. package/dist/node/components/docs/guides/index.js +220 -46
  40. package/dist/node/components/docs/index.js +1195 -276
  41. package/dist/node/components/docs/libraries/LibrariesApplicationShellPage.content.js +235 -0
  42. package/dist/node/components/docs/libraries/LibrariesApplicationShellPage.js +235 -0
  43. package/dist/node/components/docs/libraries/LibrariesDataViewsPage.js +130 -6
  44. package/dist/node/components/docs/libraries/LibrariesDesignSystemPage.js +102 -3
  45. package/dist/node/components/docs/libraries/LibrariesOverviewPage.js +1 -1
  46. package/dist/node/components/docs/libraries/LibrariesPersonalizationPage.js +58 -4
  47. package/dist/node/components/docs/libraries/LibrariesTranslationRuntimePage.content.js +42 -0
  48. package/dist/node/components/docs/libraries/LibrariesTranslationRuntimePage.js +42 -0
  49. package/dist/node/components/docs/libraries/index.js +616 -64
  50. package/dist/node/components/docs/specs/SpecsDataViewsPage.js +85 -3
  51. package/dist/node/components/docs/specs/index.js +96 -14
  52. package/dist/node/index.js +1206 -287
  53. package/package.json +98 -26
  54. package/src/components/docs/docsManifest.test.ts +87 -0
  55. package/src/components/docs/docsManifest.ts +98 -1
  56. package/src/components/docs/generated/docs-index.notifications.json +7 -7
  57. package/src/components/docs/getting-started/DataViewTutorialPage.tsx +217 -47
  58. package/src/components/docs/guides/GuideDataExchangeImportTemplatesPage.content.ts +185 -0
  59. package/src/components/docs/guides/GuideDataExchangeImportTemplatesPage.tsx +186 -0
  60. package/src/components/docs/guides/GuidesIndexPage.tsx +49 -42
  61. package/src/components/docs/guides/index.ts +1 -0
  62. package/src/components/docs/libraries/LibrariesApplicationShellPage.content.ts +283 -0
  63. package/src/components/docs/libraries/LibrariesApplicationShellPage.tsx +145 -0
  64. package/src/components/docs/libraries/LibrariesDataViewsPage.tsx +278 -54
  65. package/src/components/docs/libraries/LibrariesDesignSystemPage.tsx +244 -0
  66. package/src/components/docs/libraries/LibrariesOverviewPage.tsx +13 -1
  67. package/src/components/docs/libraries/LibrariesPersonalizationPage.tsx +141 -31
  68. package/src/components/docs/libraries/LibrariesTranslationRuntimePage.content.ts +78 -0
  69. package/src/components/docs/libraries/LibrariesTranslationRuntimePage.tsx +137 -0
  70. package/src/components/docs/libraries/index.ts +2 -0
  71. package/src/components/docs/specs/SpecsDataViewsPage.tsx +278 -116
@@ -0,0 +1,137 @@
1
+ import { CodeBlock, InstallCommand } from '@contractspec/lib.design-system';
2
+ import { HStack, VStack } from '@contractspec/lib.design-system/layout';
3
+ import { List, ListItem } from '@contractspec/lib.design-system/list';
4
+ import {
5
+ Code,
6
+ H1,
7
+ H2,
8
+ H3,
9
+ P,
10
+ Text,
11
+ } from '@contractspec/lib.design-system/typography';
12
+ import Link from '@contractspec/lib.ui-link';
13
+ import { ChevronRight } from 'lucide-react';
14
+ import {
15
+ i18nextAdapterExample,
16
+ ssrHydrationExample,
17
+ translationRuntimeChecks,
18
+ translationRuntimeExample,
19
+ translationRuntimeInstall,
20
+ translationRuntimeLayers,
21
+ translationRuntimePrompt,
22
+ } from './LibrariesTranslationRuntimePage.content';
23
+
24
+ export function LibrariesTranslationRuntimePage() {
25
+ return (
26
+ <VStack className="space-y-8">
27
+ <VStack className="space-y-4">
28
+ <Text className="editorial-kicker">Runtime and adapters</Text>
29
+ <H1 className="font-serif text-4xl tracking-[-0.04em] md:text-5xl">
30
+ Translation runtime and i18next adapter
31
+ </H1>
32
+ <P className="max-w-3xl text-lg text-muted-foreground leading-8">
33
+ Use ContractSpec as the canonical translation contract layer, then
34
+ resolve and format messages through a framework-independent runtime.
35
+ i18next is supported as an optional downstream adapter, not as the
36
+ source of truth.
37
+ </P>
38
+ </VStack>
39
+
40
+ <VStack className="space-y-4">
41
+ <H2 className="font-bold text-2xl">Install the runtime</H2>
42
+ <InstallCommand package={translationRuntimeInstall} />
43
+ <P className="text-muted-foreground">
44
+ <Text>Add </Text>
45
+ <Code>i18next</Code>
46
+ <Text>
47
+ {' '}
48
+ only when an app imports the adapter subpath. Core server, React,
49
+ React Native, CLI, and test code can use the runtime without loading
50
+ i18next.
51
+ </Text>
52
+ </P>
53
+ </VStack>
54
+
55
+ <HStack className="grid gap-4 md:grid-cols-3">
56
+ {translationRuntimeLayers.map((item) => (
57
+ <VStack className="card-subtle space-y-2 p-5" key={item.title}>
58
+ <H3 className="font-semibold text-lg">{item.title}</H3>
59
+ <P className="text-muted-foreground text-sm leading-7">
60
+ {item.body}
61
+ </P>
62
+ </VStack>
63
+ ))}
64
+ </HStack>
65
+
66
+ <VStack className="space-y-4">
67
+ <H2 className="font-bold text-2xl">Use the ContractSpec runtime</H2>
68
+ <P className="text-muted-foreground">
69
+ <Text>The runtime consumes canonical </Text>
70
+ <Code>TranslationSpec[]</Code>
71
+ <Text>
72
+ {' '}
73
+ catalogs, supports BCP 47 tags such as en-US, ar-EG, and zh-Hans,
74
+ and delegates ICU parsing/formatting to a mature formatter engine
75
+ instead of a custom parser.
76
+ </Text>
77
+ </P>
78
+ <CodeBlock language="typescript" code={translationRuntimeExample} />
79
+ </VStack>
80
+
81
+ <VStack className="space-y-4">
82
+ <H2 className="font-bold text-2xl">Project to i18next when needed</H2>
83
+ <P className="text-muted-foreground">
84
+ <Text>Import from </Text>
85
+ <Code>@contractspec/lib.translation-runtime/i18next</Code>
86
+ <Text>
87
+ {' '}
88
+ to export resources by locale, namespace, and message key. The
89
+ namespace defaults to the stable bundle key, dotted message keys
90
+ stay flat with keySeparator false, and metadata remains in a sidecar
91
+ manifest.
92
+ </Text>
93
+ </P>
94
+ <CodeBlock language="typescript" code={i18nextAdapterExample} />
95
+ </VStack>
96
+
97
+ <VStack className="space-y-4">
98
+ <H2 className="font-bold text-2xl">SSR, streaming, and hydration</H2>
99
+ <P className="text-muted-foreground">
100
+ Negotiate locale on the server, preload catalogs needed for streamed
101
+ content, and hydrate the client from the same serialized state. Never
102
+ let client-only language detection choose a different locale after the
103
+ server has rendered.
104
+ </P>
105
+ <CodeBlock language="typescript" code={ssrHydrationExample} />
106
+ </VStack>
107
+
108
+ <VStack className="space-y-4">
109
+ <H2 className="font-bold text-2xl">Production checklist</H2>
110
+ <List className="list-disc space-y-2 pl-6 text-muted-foreground">
111
+ {translationRuntimeChecks.map((item) => (
112
+ <ListItem key={item}>{item}</ListItem>
113
+ ))}
114
+ </List>
115
+ </VStack>
116
+
117
+ <VStack className="space-y-4 rounded-xl border border-border p-6">
118
+ <H2 className="font-bold text-2xl">Agent implementation prompt</H2>
119
+ <P className="text-muted-foreground">
120
+ Use this prompt when asking an agent to wire translations into a web,
121
+ server, or React Native surface without losing ContractSpec ownership.
122
+ </P>
123
+ <CodeBlock language="markdown" code={translationRuntimePrompt} />
124
+ </VStack>
125
+
126
+ <HStack className="flex flex-wrap items-center gap-4 pt-4">
127
+ <Link href="/docs/libraries/contracts" className="btn-ghost">
128
+ <Text>Translation contracts</Text>
129
+ </Link>
130
+ <Link href="/docs/libraries/design-system" className="btn-primary">
131
+ <Text>Design-system integration</Text>
132
+ <ChevronRight size={16} />
133
+ </Link>
134
+ </HStack>
135
+ </VStack>
136
+ );
137
+ }
@@ -1,6 +1,7 @@
1
1
  export { LibrariesAccessibilityPage } from './LibrariesAccessibilityPage';
2
2
  export { LibrariesAiAgentPage } from './LibrariesAiAgentPage';
3
3
  export { LibrariesAnalyticsPage } from './LibrariesAnalyticsPage';
4
+ export { LibrariesApplicationShellPage } from './LibrariesApplicationShellPage';
4
5
  export { LibrariesContentGenPage } from './LibrariesContentGenPage';
5
6
  export { LibrariesContractsPage } from './LibrariesContractsPage';
6
7
  export { LibrariesCostTrackingPage } from './LibrariesCostTrackingPage';
@@ -23,6 +24,7 @@ export { LibrariesSchemaPage } from './LibrariesSchemaPage';
23
24
  export { LibrariesSLOPage } from './LibrariesSLOPage';
24
25
  export { LibrariesSupportBotPage } from './LibrariesSupportBotPage';
25
26
  export { LibrariesTestingPage } from './LibrariesTestingPage';
27
+ export { LibrariesTranslationRuntimePage } from './LibrariesTranslationRuntimePage';
26
28
  export { LibrariesUIKitPage } from './LibrariesUIKitPage';
27
29
  export { LibrariesUIKitWebPage } from './LibrariesUIKitWebPage';
28
30
  export { LibrariesWorkflowComposerPage } from './LibrariesWorkflowComposerPage';
@@ -1,3 +1,14 @@
1
+ import { CodeBlock } from '@contractspec/lib.design-system';
2
+ import { HStack, VStack } from '@contractspec/lib.design-system/layout';
3
+ import { List, ListItem } from '@contractspec/lib.design-system/list';
4
+ import {
5
+ Code,
6
+ H1,
7
+ H2,
8
+ H3,
9
+ P,
10
+ Text,
11
+ } from '@contractspec/lib.design-system/typography';
1
12
  import Link from '@contractspec/lib.ui-link';
2
13
  import { ChevronRight } from 'lucide-react';
3
14
 
@@ -45,7 +56,76 @@ export const DataGridShowcaseDataView = defineDataView({
45
56
  { key: 'account', label: 'Account', dataPath: 'account', sortable: true },
46
57
  { key: 'owner', label: 'Owner', dataPath: 'owner', sortable: true },
47
58
  { key: 'status', label: 'Status', dataPath: 'status', sortable: true },
48
- { key: 'notes', label: 'Notes', dataPath: 'notes' },
59
+ {
60
+ key: 'arr',
61
+ label: 'ARR',
62
+ dataPath: 'arr',
63
+ sortable: true,
64
+ format: { type: 'currency', currency: 'USD', rounded: true },
65
+ },
66
+ {
67
+ key: 'healthScore',
68
+ label: 'Health score',
69
+ dataPath: 'healthScore',
70
+ format: { type: 'percent', valueScale: 'fraction', maximumFractionDigits: 1 },
71
+ },
72
+ {
73
+ key: 'lastActivityAt',
74
+ label: 'Last activity',
75
+ dataPath: 'lastActivityAt',
76
+ format: { type: 'datetime', dateStyle: 'medium', timeStyle: 'short' },
77
+ },
78
+ {
79
+ key: 'notes',
80
+ label: 'Notes',
81
+ dataPath: 'notes',
82
+ visibility: { minDataDepth: 'detailed' },
83
+ },
84
+ ],
85
+ collection: {
86
+ viewModes: {
87
+ defaultMode: 'table',
88
+ allowedModes: ['list', 'grid', 'table'],
89
+ },
90
+ pagination: {
91
+ pageSize: 25,
92
+ pageSizeOptions: [10, 25, 50],
93
+ },
94
+ toolbar: {
95
+ search: true,
96
+ viewMode: true,
97
+ filters: true,
98
+ density: true,
99
+ dataDepth: true,
100
+ },
101
+ density: 'comfortable',
102
+ dataDepth: 'standard',
103
+ personalization: {
104
+ enabled: true,
105
+ persist: {
106
+ viewMode: true,
107
+ density: true,
108
+ dataDepth: true,
109
+ pageSize: true,
110
+ },
111
+ },
112
+ },
113
+ filters: [
114
+ { key: 'status', label: 'Status', field: 'status', type: 'enum' },
115
+ {
116
+ key: 'arr',
117
+ label: 'ARR',
118
+ field: 'arr',
119
+ type: 'currency',
120
+ valueMode: 'range',
121
+ },
122
+ {
123
+ key: 'lastActivityAt',
124
+ label: 'Last activity',
125
+ field: 'lastActivityAt',
126
+ type: 'datetime',
127
+ valueMode: 'range',
128
+ },
49
129
  ],
50
130
  },
51
131
  });`;
@@ -58,163 +138,245 @@ export const DataGridShowcaseDataView = defineDataView({
58
138
 
59
139
  export function SpecsDataViewsPage() {
60
140
  return (
61
- <div className="space-y-8">
62
- <div className="space-y-4">
63
- <h1 className="font-bold text-4xl">DataViews</h1>
64
- <p className="text-muted-foreground">
65
- A <strong>DataViewSpec</strong> describes how data should be queried,
66
- filtered, sorted, and presented to users. Runtime adapters execute
67
- optimized database queries and serve list views, detail views, and
68
- search interfaces while respecting policy constraints.
69
- </p>
70
- </div>
141
+ <VStack className="space-y-8">
142
+ <VStack className="space-y-4">
143
+ <H1 className="font-bold text-4xl">DataViews</H1>
144
+ <P className="text-muted-foreground">
145
+ A <Text className="font-semibold">DataViewSpec</Text> describes how
146
+ data should be queried, filtered, sorted, and presented to users.
147
+ Runtime adapters execute optimized database queries and serve list
148
+ views, detail views, and search interfaces while respecting policy
149
+ constraints.
150
+ </P>
151
+ </VStack>
71
152
 
72
- <div className="space-y-4">
73
- <h2 className="font-bold text-2xl">Core concepts</h2>
74
- <div className="space-y-3">
75
- <div>
76
- <h3 className="font-semibold text-lg">Data sources</h3>
77
- <p className="text-muted-foreground">
153
+ <VStack className="space-y-4">
154
+ <H2 className="font-bold text-2xl">Core concepts</H2>
155
+ <VStack className="space-y-3">
156
+ <VStack>
157
+ <H3 className="font-semibold text-lg">Data sources</H3>
158
+ <P className="text-muted-foreground">
78
159
  A DataView connects to one or more data sources—databases, APIs,
79
160
  or other capabilities. You specify the source and the fields you
80
161
  want to expose.
81
- </p>
82
- </div>
83
- <div>
84
- <h3 className="font-semibold text-lg">Filtering</h3>
85
- <p className="text-muted-foreground">
162
+ </P>
163
+ </VStack>
164
+ <VStack>
165
+ <H3 className="font-semibold text-lg">Filtering</H3>
166
+ <P className="text-muted-foreground">
86
167
  Define filters that users can apply to narrow down results.
87
- Filters can be simple (e.g., "status equals 'active'") or complex
88
- (e.g., "created within the last 30 days AND assigned to current
89
- user").
90
- </p>
91
- </div>
92
- <div>
93
- <h3 className="font-semibold text-lg">Sorting</h3>
94
- <p className="text-muted-foreground">
168
+ Filters are typed as search, enum, number, percent, currency,
169
+ date, time, datetime, duration, or boolean so renderers and query
170
+ helpers can validate values before execution.
171
+ </P>
172
+ </VStack>
173
+ <VStack>
174
+ <H3 className="font-semibold text-lg">Sorting</H3>
175
+ <P className="text-muted-foreground">
95
176
  Specify which fields can be sorted and the default sort order.
96
177
  ContractSpec generates efficient database queries with proper
97
178
  indexes.
98
- </p>
99
- </div>
100
- <div>
101
- <h3 className="font-semibold text-lg">Pagination</h3>
102
- <p className="text-muted-foreground">
179
+ </P>
180
+ </VStack>
181
+ <VStack>
182
+ <H3 className="font-semibold text-lg">Pagination</H3>
183
+ <P className="text-muted-foreground">
103
184
  DataViews automatically support pagination to handle large
104
185
  datasets. You can configure page size limits and cursor-based or
105
186
  offset-based pagination.
106
- </p>
107
- </div>
108
- <div>
109
- <h3 className="font-semibold text-lg">Aggregations</h3>
110
- <p className="text-muted-foreground">
111
- Compute aggregates like counts, sums, averages, and group-by
112
- operations. These are useful for dashboards and summary views.
113
- </p>
114
- </div>
115
- </div>
116
- </div>
187
+ </P>
188
+ </VStack>
189
+ <VStack>
190
+ <H3 className="font-semibold text-lg">
191
+ Collection modes and data depth
192
+ </H3>
193
+ <P className="text-muted-foreground">
194
+ List, grid, and table views can share a single{' '}
195
+ <Code>view.collection</Code> contract. It declares allowed view
196
+ modes, toolbar controls, page-size defaults, density, data depth,
197
+ and persistence hints. Fields can use{' '}
198
+ <Code>visibility.minDataDepth</Code> so summary views stay light
199
+ while detailed views expose richer context.
200
+ </P>
201
+ </VStack>
202
+ <VStack>
203
+ <H3 className="font-semibold text-lg">Personalization hints</H3>
204
+ <P className="text-muted-foreground">
205
+ The contract layer stays neutral: it can opt into persistence with{' '}
206
+ <Code>view.collection.personalization</Code>, but it does not
207
+ import the personalization runtime. Host apps resolve preferences
208
+ and behavior insights into renderer props.
209
+ </P>
210
+ </VStack>
211
+ </VStack>
212
+ </VStack>
117
213
 
118
- <div className="space-y-4">
119
- <h2 className="font-bold text-2xl">Example DataViewSpec</h2>
120
- <p className="text-muted-foreground">
214
+ <VStack className="space-y-4">
215
+ <H2 className="font-bold text-2xl">Example DataViewSpec</H2>
216
+ <P className="text-muted-foreground">
121
217
  Here is the canonical table contract used by the live{' '}
122
218
  <Link
123
219
  href="/docs/examples/data-grid-showcase"
124
220
  className="text-[color:var(--rust)] underline underline-offset-4"
125
221
  >
126
- Data Grid Showcase
222
+ <Text>Data Grid Showcase</Text>
127
223
  </Link>
128
224
  :
129
- </p>
130
- <div className="overflow-x-auto rounded-lg border border-border bg-background/50 p-4 font-mono text-muted-foreground text-sm">
131
- <pre>{SPECS_DATAVIEWS_EXAMPLE}</pre>
132
- </div>
133
- <p className="text-muted-foreground text-sm">
225
+ </P>
226
+ <CodeBlock language="typescript" code={SPECS_DATAVIEWS_EXAMPLE} />
227
+ <P className="text-muted-foreground text-sm">
134
228
  This one contract drives the DataView lane, while the same rows and
135
229
  controller also feed the raw web primitive, native-first primitive,
136
230
  and composed design-system demos.
137
- </p>
138
- </div>
231
+ </P>
232
+ </VStack>
139
233
 
140
- <div className="space-y-4">
141
- <h2 className="font-bold text-2xl">Policy integration</h2>
142
- <p className="text-muted-foreground">
234
+ <VStack className="space-y-4">
235
+ <H2 className="font-bold text-2xl">Policy integration</H2>
236
+ <P className="text-muted-foreground">
143
237
  DataViews automatically enforce{' '}
144
238
  <Link
145
239
  href="/docs/specs/policy"
146
240
  className="text-violet-400 hover:text-violet-300"
147
241
  >
148
- PolicySpecs
242
+ <Text>PolicySpecs</Text>
149
243
  </Link>
150
244
  . If a user doesn't have permission to see certain fields, those
151
245
  fields are automatically filtered out or redacted. If a user can only
152
246
  see their own data, the query is automatically scoped.
153
- </p>
154
- <p className="text-muted-foreground">
247
+ </P>
248
+ <P className="text-muted-foreground">
155
249
  This means you define the data view once, and it works correctly for
156
250
  all users based on their permissions—no need to write separate queries
157
251
  for different roles.
158
- </p>
159
- </div>
252
+ </P>
253
+ </VStack>
254
+
255
+ <VStack className="space-y-4">
256
+ <H2 className="font-bold text-2xl">Personalized Rendering Pattern</H2>
257
+ <P className="text-muted-foreground">
258
+ To personalize a DataView, keep the spec declarative and resolve
259
+ user-specific defaults at the app boundary. Use{' '}
260
+ <Code>resolveDataViewPreferences</Code> from{' '}
261
+ <Code>@contractspec/lib.personalization/data-view-preferences</Code>
262
+ to compute <Code>viewMode</Code>, <Code>density</Code>,{' '}
263
+ <Code>dataDepth</Code>, and <Code>pageSize</Code>. Pass those values
264
+ to <Code>DataViewRenderer</Code> as controlled or default props, then
265
+ record UI changes with <Code>trackDataViewInteraction</Code>.
266
+ </P>
267
+ <CodeBlock
268
+ language="tsx"
269
+ code={`const resolved = resolveDataViewPreferences({
270
+ spec: DataGridShowcaseDataView,
271
+ preferences: profile.canonical,
272
+ insights,
273
+ record: savedPreference,
274
+ });
275
+
276
+ <DataViewRenderer
277
+ spec={DataGridShowcaseDataView}
278
+ items={rows}
279
+ defaultViewMode={resolved.viewMode}
280
+ defaultDensity={resolved.density}
281
+ defaultDataDepth={resolved.dataDepth}
282
+ />;`}
283
+ />
284
+ </VStack>
160
285
 
161
- <div className="space-y-4">
162
- <h2 className="font-bold text-2xl">Served outputs</h2>
163
- <p className="text-muted-foreground">
286
+ <VStack className="space-y-4">
287
+ <H2 className="font-bold text-2xl">Served outputs</H2>
288
+ <P className="text-muted-foreground">
164
289
  From a DataViewSpec, ContractSpec serves:
165
- </p>
166
- <ul className="list-inside list-disc space-y-2 text-muted-foreground">
167
- <li>
168
- <strong>Database queries</strong> – Optimized SQL or NoSQL queries
169
- executed at runtime
170
- </li>
171
- <li>
172
- <strong>API endpoints</strong> – RESTful or GraphQL endpoints for
173
- fetching data
174
- </li>
175
- <li>
176
- <strong>UI components</strong> List views, tables, cards, and
177
- detail views
178
- </li>
179
- <li>
180
- <strong>Search interfaces</strong> – Full-text search with
181
- autocomplete
182
- </li>
183
- <li>
184
- <strong>Export functions</strong> – CSV, JSON, or Excel exports
185
- </li>
186
- </ul>
187
- </div>
290
+ </P>
291
+ <List className="list-inside list-disc space-y-2 text-muted-foreground">
292
+ <ListItem>
293
+ <Text>
294
+ <Text className="font-semibold">Database queries</Text> –
295
+ Optimized SQL or NoSQL queries executed at runtime
296
+ </Text>
297
+ </ListItem>
298
+ <ListItem>
299
+ <Text>
300
+ <Text className="font-semibold">API endpoints</Text> – RESTful or
301
+ GraphQL endpoints for fetching data
302
+ </Text>
303
+ </ListItem>
304
+ <ListItem>
305
+ <Text>
306
+ <Text className="font-semibold">UI components</Text> – List views,
307
+ tables, cards, and detail views
308
+ </Text>
309
+ </ListItem>
310
+ <ListItem>
311
+ <Text>
312
+ <Text className="font-semibold">Personalized defaults</Text>
313
+ Plain renderer props for preferred mode, density, data depth, and
314
+ page size
315
+ </Text>
316
+ </ListItem>
317
+ <ListItem>
318
+ <Text>
319
+ <Text className="font-semibold">Search interfaces</Text> –
320
+ Full-text search with autocomplete
321
+ </Text>
322
+ </ListItem>
323
+ <ListItem>
324
+ <Text>
325
+ <Text className="font-semibold">Export functions</Text> – CSV,
326
+ JSON, or Excel exports
327
+ </Text>
328
+ </ListItem>
329
+ </List>
330
+ </VStack>
188
331
 
189
- <div className="space-y-4">
190
- <h2 className="font-bold text-2xl">Best practices</h2>
191
- <ul className="list-inside list-disc space-y-2 text-muted-foreground">
192
- <li>
193
- Only expose fields that users actually need—this improves
194
- performance and security.
195
- </li>
196
- <li>Use appropriate indexes for sortable and filterable fields.</li>
197
- <li>
198
- Set reasonable pagination limits to prevent performance issues.
199
- </li>
200
- <li>
201
- Use aggregations sparingly—they can be expensive on large datasets.
202
- </li>
203
- <li>
204
- Test DataViews with realistic data volumes to ensure they perform
205
- well.
206
- </li>
207
- </ul>
208
- </div>
332
+ <VStack className="space-y-4">
333
+ <H2 className="font-bold text-2xl">Best practices</H2>
334
+ <List className="list-inside list-disc space-y-2 text-muted-foreground">
335
+ <ListItem>
336
+ <Text>
337
+ Only expose fields that users actually need—this improves
338
+ performance and security.
339
+ </Text>
340
+ </ListItem>
341
+ <ListItem>
342
+ <Text>
343
+ Use appropriate indexes for sortable and filterable fields.
344
+ </Text>
345
+ </ListItem>
346
+ <ListItem>
347
+ <Text>
348
+ Set reasonable pagination limits to prevent performance issues.
349
+ </Text>
350
+ </ListItem>
351
+ <ListItem>
352
+ <Text>
353
+ Use <Code>allowedModes</Code> to constrain mode switching to
354
+ layouts that the fields and row actions can support.
355
+ </Text>
356
+ </ListItem>
357
+ <ListItem>
358
+ <Text>
359
+ Store preferences only for dimensions enabled by{' '}
360
+ <Code>view.collection.personalization.persist</Code>.
361
+ </Text>
362
+ </ListItem>
363
+ <ListItem>
364
+ <Text>
365
+ Test DataViews with realistic data volumes to ensure they perform
366
+ well.
367
+ </Text>
368
+ </ListItem>
369
+ </List>
370
+ </VStack>
209
371
 
210
- <div className="flex items-center gap-4 pt-4">
372
+ <HStack className="items-center gap-4 pt-4">
211
373
  <Link href="/docs/specs/capabilities" className="btn-ghost">
212
- Previous: Capabilities
374
+ <Text>Previous: Capabilities</Text>
213
375
  </Link>
214
376
  <Link href="/docs/specs/workflows" className="btn-primary">
215
- Next: Workflows <ChevronRight size={16} />
377
+ <Text>Next: Workflows</Text> <ChevronRight size={16} />
216
378
  </Link>
217
- </div>
218
- </div>
379
+ </HStack>
380
+ </VStack>
219
381
  );
220
382
  }