Skip to content
This repository was archived by the owner on Oct 26, 2026. It is now read-only.

Commit 699156a

Browse files
objectstack-fleet[bot]claudeos-zhuang
authored
refactor(providers)!: retire the DataSourceProvider, MetadataProvider and ThemeProvider trio and fix the guides that taught them (objectui#13453, part 2) (#13507)
<!-- claude-projects-attribution: {"github_login":"os-elon-musk"} --> _Requested by **Elon** · [project thread](https://claude.ai/code/project/chan_01WedDzV26nniwxv7jC88B9D?thread=cmsg_01WedDzV26nniwxv7jC88B9D4nNtkcxk6i4sCKHsvYsQgG)_ Part of #13453 Clause-②: no (nothing added a consumer or author can target) Metadata-protocol: none ## 维护者速读(草稿) - **改了什么:** `@object-ui/providers` 删掉三个和别的包重名的 Provider:`DataSourceProvider`、`MetadataProvider`、`ThemeProvider`(连同 `useDataSource` / `useMetadata` / `useTheme` 和四个类型)。包里只留上传用的 `UploadProvider` / `useUpload`。同时改好引用它们的地方:byo 示例、README 和架构文档、贡献者技能指南里的一句话、对外发布的 `skills/objectui` 两篇指南。另外把 #13506 已改成私有的 runner 从这几篇指南里拿掉。 - **为什么改:** 这三个名字在 `@object-ui/react`(数据源、主题)和 `@object-ui/app-shell`(元数据)里都有同名但实现不同的版本,console 用的都是那两个包的。providers 这份在三个仓里没有任何代码引用,只出现在文档和一个示例里,AI 和开发者照着文档写,很容易引错包。 - **风险与代价(含回滚):** 对 npm 上的外部使用者是破坏性删除。按版本政策只声明 `minor`,changeset 里写明删了哪些名字,并给出迁移路径。cloud 和外部 npm 依赖方没有测量到。回滚就是 revert 这一个 PR,没有数据或接口协议上的影响。 - **席位意见:** - **你要做的:** 审阅后在本 PR 点 Approve(os-zhuang 或 hotlong 任一人即可),之后由席位落地。 ## What this removes Second of the two PRs the claim amendment (comment 6393918010) cuts on the governed line; PR 1 (#13506, Tier S) merged at `0063f22`. This one is Tier H because it edits `.claude/skills/objectui-contributor/guides/console-development.md` and `skills/objectui/**`. **1. The providers trio.** `packages/providers/src/{DataSourceProvider,MetadataProvider,ThemeProvider}.tsx`, `types.ts`, and their two tests (`spec-symbol-batch7.test.ts`, `theme-mode-spec-parity.test.tsx`) are deleted. The barrel keeps only the upload surface (`UploadProvider`, `useUpload`, the upload adapters), with a note on what retired and where each replacement lives. Removed names: `DataSourceProvider`, `useDataSource`, `MetadataProvider`, `useMetadata`, `ThemeProvider`, `useTheme`, and the types `DataSourceProviderProps`, `MetadataProviderProps`, `ThemePreferenceProviderProps`, `ThemePreference`. Premise correction carried from the claim: `@object-ui/react` does not export `DataSourceProvider`, `useDataSource` or `MetadataProvider`. The replacements are: | Retired (`@object-ui/providers`) | Use instead | |---|---| | `DataSourceProvider` / `useDataSource` | `SchemaRendererProvider` (`dataSource` prop), `@object-ui/react` | | `ThemeProvider` / `useTheme` | `ThemeProvider` / `useTheme`, `@object-ui/react` (`defaultMode`; the old `system` is `auto`; `persist` keeps the choice in `localStorage`) | | `MetadataProvider` / `useMetadata` | `MetadataProvider` / `useMetadata`, `@object-ui/app-shell` | **2. The one code consumer, the byo example.** `examples/byo-backend-console/src/App.tsx` now wraps in `ThemeProvider defaultMode="light" persist storageKey=…` and `SchemaRendererProvider` from `@object-ui/react`; its `@object-ui/providers` dependency and the lockfile entry go. Its README follows. **3. Docs and exemptions that named the trio.** `README.md`, `docs/ARCHITECTURE.md` (its compiled snippets now import the replacements), `examples/README.md`, `packages/providers/README.md`, the `types/src/theme.ts` comments, and two test comments that pointed at the deleted files: `p2-spec-exports.test.ts`, and the `KNOWN_COLLISIONS` note in `one-authority-per-exported-name-6273.test.ts` (no entry changes; it now records that react's `ThemeProvider` is the only one left). `docs/audits/2901-spec-enum-renderer-coverage.md` unlinks the deleted `ThemeProvider.tsx` path (read by `check-doc-links`). **4. Governed text.** - `.claude/skills/objectui-contributor/guides/console-development.md`: the paragraph that called `MetadataProvider` "the one name with two hits" now says the app-shell one is the only one left (`check-skills-paths` reads the deleted path). - `skills/objectui/guides/project-setup.md`: the provider section and the decision matrix teach `SchemaRendererProvider` / `ThemeProvider` (react), `MetadataProvider` (app-shell) and `UploadProvider` (providers); the `@object-ui/runner` section becomes "use `objectui dev`", since #13506 made runner a private workspace app. - `skills/objectui/guides/architecture.md`: the integration-package bullets follow the same split and drop runner. - `skills/objectui/README.md`: runner leaves the Integration package list. ## Census before deleting (lit controls) | Repository | Read at | Searched | Hits outside `packages/providers/src` | Control | |---|---|---|---|---| | objectui | `0063f22` (main) | `git grep` for every removed name and for `from '@object-ui/providers'` | docs and READMEs, the guide files above, and `examples/byo-backend-console/src/App.tsx` (the only code import) | `UploadProvider` imports from `@object-ui/providers` lit in the console | | objectstack | `5874d25` | `@object-ui/providers` | none | `@object-ui/` lit in 150 files | | hotcrm | `a7faf81` | `@object-ui/providers` | none | `@object-ui/` lit in 5 files | | cloud, npm dependents | n/a | **NOT MEASURED**: not reachable from this session | n/a | n/a | ## Changeset `13453-providers-retire-trio.md`: `@object-ui/providers` `minor`, every removed name listed, with the migration above. Never `major`, per the version policy. ## Verification (local, on this head) - **type-check** (`turbo run type-check --continue` under the verify lock, filters providers, types, console, the byo example; 39 tasks with dependencies): 39 successful. - **vitest**: `packages/providers`, `p2-spec-exports.test.ts`, `one-authority-per-exported-name-6273.test.ts`, `check-skills-paths.test.ts`, `check-doc-links.test.ts`, `quick-reference-commands-4149.test.ts`, `check-skill-examples.test.ts`: 7 files, 318 tests passed. - **gates**: `check-doc-links`, `check-changeset-no-major`, `check-changeset-fixed`, and `pnpm exec changeset status --since=origin/main` all exit 0. - Earlier, on the unsplit branch that carried PR 1 plus this diff: whole-package vitest of core, types, providers, collaboration, plugin-detail and react passed (1028 files, 19019 tests). - **NOT MEASURED locally:** `check:readme-exports` and `check:doc-snippets` (need every package's `dist`); CI runs them. ## Still on #13453 after this - `resetActionKeyWarnings` and `clearSharedDiscoveryCache` wait for #13442. - The 122 dead i18n keys, after #13460's PR merges and a claim amendment. - `plugin-ai` and folding `UploadProvider` are out of scope (maintainer's call). --- _Generated by [Claude Code](https://claude.ai/code/session_011yfYeuX2ptMSCcYZiq61tS)_ --------- Co-authored-by: Claude <noreply@anthropic.com> Co-authored-by: os-zhuang <jack@objectstack.ai>
1 parent f27eafa commit 699156a

24 files changed

Lines changed: 144 additions & 593 deletions
Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
---
2+
"@object-ui/providers": minor
3+
---
4+
5+
Clause-②: no
6+
Metadata-protocol: none
7+
8+
**Breaking:** removed `DataSourceProvider` / `useDataSource`, `MetadataProvider` / `useMetadata`, `ThemeProvider` / `useTheme` and the types `DataSourceProviderProps`, `MetadataProviderProps`, `ThemePreferenceProviderProps`, `ThemePreference` (objectui#13453). They duplicated names other ObjectUI packages publish with different implementations. Declared `minor` per the version-alignment policy (a changeset never declares `major`). `UploadProvider`, `useUpload` and the upload adapters are unchanged.
9+
10+
Migration: wrap the tree in `SchemaRendererProvider` from `@object-ui/react` (its `dataSource` prop) instead of `DataSourceProvider`, and pass the adapter to views as before; use `ThemeProvider` / `useTheme` from `@object-ui/react` (`defaultMode`, where the old `system` is `auto`; add `persist` to keep the choice in `localStorage`); use `MetadataProvider` / `useMetadata` from `@object-ui/app-shell`.

‎.claude/skills/objectui-contributor/guides/console-development.md‎

Lines changed: 4 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -404,11 +404,10 @@ prefix across the table.
404404
| `FavoritesProvider` | `packages/app-shell/src/context/FavoritesProvider.tsx` | User's starred/pinned items |
405405
| `ExpressionProvider` | `packages/app-shell/src/providers/ExpressionProvider.tsx` | Expression evaluator instance |
406406

407-
`MetadataProvider` is the one name with two hits in the repo. The console's is the
408-
app-shell file above — it is what `ConsoleShell` / `ConnectedShell` mount and what
409-
`@object-ui/app-shell` re-exports. `packages/providers/src/MetadataProvider.tsx` is an
410-
unrelated, much smaller generic provider (static metadata or one fetch); nothing in the
411-
console path uses it.
407+
`MetadataProvider` is the app-shell file above — it is what `ConsoleShell` /
408+
`ConnectedShell` mount and what `@object-ui/app-shell` re-exports. `@object-ui/providers`
409+
used to publish an unrelated generic provider under the same name; it retired in
410+
objectui#13453, so the app-shell one is the only `MetadataProvider` left.
412411

413412
## Key hooks
414413

‎README.md‎

Lines changed: 7 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,7 @@ Pick the path that matches where you are starting from:
5656
| You want to… | Start here | Install |
5757
|---|---|---|
5858
| Render a JSON schema inside your React app | [`examples/hello-world`](examples/hello-world) | `@object-ui/react @object-ui/components` |
59-
| Embed views in an existing app, against **your own** backend | [`examples/byo-backend-console`](examples/byo-backend-console) | `@object-ui/app-shell @object-ui/plugin-view @object-ui/providers` |
59+
| Embed views in an existing app, against **your own** backend | [`examples/byo-backend-console`](examples/byo-backend-console) | `@object-ui/app-shell @object-ui/plugin-view @object-ui/react` |
6060
| Stand up a complete console on an **ObjectStack** backend | [`examples/console-starter`](examples/console-starter) | fork the example |
6161
| Build a UI from a JSON file, no React code at all | [`@object-ui/cli`](packages/cli) | `npm install -g @object-ui/cli` |
6262

@@ -120,14 +120,14 @@ nothing thrown and one line on the console.
120120
Use the shell and views without the full console infrastructure — your routing, your auth, your API:
121121

122122
```bash
123-
npm install @object-ui/app-shell @object-ui/plugin-view @object-ui/providers
123+
npm install @object-ui/app-shell @object-ui/plugin-view @object-ui/react
124124
```
125125

126126
```tsx
127127
import type { FC } from 'react';
128128
import { AppShell } from '@object-ui/app-shell';
129129
import { ObjectView } from '@object-ui/plugin-view';
130-
import { ThemeProvider, DataSourceProvider, useDataSource } from '@object-ui/providers';
130+
import { ThemeProvider, SchemaRendererProvider } from '@object-ui/react';
131131
import type { DataSource } from '@object-ui/types';
132132

133133
// The two pieces you bring: the backend adapter you implement (see "Custom
@@ -138,19 +138,18 @@ declare const MySidebar: FC;
138138
function MyConsole() {
139139
return (
140140
<ThemeProvider>
141-
<DataSourceProvider dataSource={myAPI}>
141+
<SchemaRendererProvider dataSource={myAPI}>
142142
<AppShell sidebar={<MySidebar />}>
143143
<ContactList />
144144
</AppShell>
145-
</DataSourceProvider>
145+
</SchemaRendererProvider>
146146
</ThemeProvider>
147147
);
148148
}
149149

150150
function ContactList() {
151-
const dataSource = useDataSource();
152151
return (
153-
<ObjectView schema={{ type: 'object-view', objectName: 'contact' }} dataSource={dataSource} />
152+
<ObjectView schema={{ type: 'object-view', objectName: 'contact' }} dataSource={myAPI} />
154153
);
155154
}
156155
```
@@ -380,7 +379,7 @@ Grouped by dependency weight — atoms and fields stay light, heavy widgets live
380379
| Package | Description |
381380
|---------|-------------|
382381
| **[@object-ui/app-shell](./packages/app-shell)** | Minimal application shell — the base of every console |
383-
| **[@object-ui/providers](./packages/providers)** | Theme, data-source, and other reusable context providers |
382+
| **[@object-ui/providers](./packages/providers)** | The upload adapter context the file and image fields upload through |
384383
| **[@object-ui/auth](./packages/auth)** | `AuthProvider`, `useAuth`, `AuthGuard`, sign-in forms |
385384
| **[@object-ui/permissions](./packages/permissions)** | Object / field / row-level permission guards and hooks |
386385
| **[@object-ui/i18n](./packages/i18n)** | Language packs, RTL layout, date and currency formatting |

‎docs/ARCHITECTURE.md‎

Lines changed: 36 additions & 41 deletions
Original file line numberDiff line numberDiff line change
@@ -31,16 +31,18 @@ This document describes the refactored architecture that enables third-party sys
3131

3232
### @object-ui/providers
3333

34-
**Purpose**: Reusable context providers
34+
**Purpose**: The upload adapter context
3535

3636
**Exports**:
37-
- `DataSourceProvider` - Generic data source context
38-
- `MetadataProvider` - Schema/metadata management
39-
- `ThemeProvider` - Theme management
37+
- `UploadProvider` / `useUpload` - The ambient upload adapter the file and image fields upload through
38+
- `createObjectStackUploadAdapter`, `createS3Adapter`, `createAzureBlobAdapter`, `createObjectUrlAdapter`
4039

41-
**Dependencies**: `@object-ui/types`
40+
Its former `DataSourceProvider`, `MetadataProvider` and `ThemeProvider` retired
41+
(objectui#13453). The data source is `SchemaRendererProvider` and the theme is
42+
`ThemeProvider`, both from `@object-ui/react`; metadata is `MetadataProvider` from
43+
`@object-ui/app-shell`.
4244

43-
**Bundle Size**: ~10KB
45+
**Dependencies**: `@object-ui/types`
4446

4547
## Architecture Diagram
4648

@@ -64,15 +66,10 @@ This document describes the refactored architecture that enables third-party sys
6466
└────────────────┬────────────────────────┘
6567
│
6668
┌────────────────┴────────────────────────┐
67-
│ @object-ui/providers │
68-
│ - DataSourceProvider │
69-
│ - MetadataProvider │
70-
│ - ThemeProvider │
71-
└────────────────┬────────────────────────┘
72-
│
73-
┌────────────────┴────────────────────────┐
7469
│ @object-ui/react │
7570
│ - SchemaRenderer │
71+
│ - SchemaRendererProvider (data source) │
72+
│ - ThemeProvider │
7673
│ - useActionRunner │
7774
│ - Component Registry │
7875
└────────────────┬────────────────────────┘
@@ -115,10 +112,9 @@ apps/console (500KB+)
115112
├── Page Rendering
116113
└── Form Rendering
117114
118-
@object-ui/providers (10KB)
119-
├── Generic DataSource
120-
├── Metadata Management
121-
└── Theme System
115+
@object-ui/react
116+
├── SchemaRendererProvider (generic DataSource)
117+
└── ThemeProvider
122118
123119
Third-Party App
124120
├── Custom Routing
@@ -162,32 +158,30 @@ Third-Party App
162158
import { AppShell } from '@object-ui/app-shell';
163159
import type { MinimalAppShellProps } from '@object-ui/app-shell';
164160
import { ObjectView } from '@object-ui/plugin-view';
165-
import { DataSourceProvider, useDataSource } from '@object-ui/providers';
166-
import type { DataSourceProviderProps } from '@object-ui/providers';
161+
import { SchemaRendererProvider } from '@object-ui/react';
162+
import type { DataSource } from '@object-ui/types';
167163

168164
// The two things you bring. Both are typed from the surface these packages
169165
// ship, so this snippet compiles on its own: `myAPI` is your backend adapter
170-
// (the "Custom Data Source Interface" section below is the shape it needs at
171-
// runtime — `DataSourceProvider` declares the prop `any`, so the annotation
172-
// records where the value goes rather than checking it), and `MySidebar` is
173-
// your own component, returning whatever `AppShell` accepts for `sidebar`.
174-
declare const myAPI: DataSourceProviderProps['dataSource'];
166+
// (the "Custom Data Source Interface" section below is the shape it needs),
167+
// and `MySidebar` is your own component, returning whatever `AppShell`
168+
// accepts for `sidebar`.
169+
declare const myAPI: DataSource;
175170
declare function MySidebar(): MinimalAppShellProps['sidebar'];
176171

177172
function MyConsole() {
178173
return (
179-
<DataSourceProvider dataSource={myAPI}>
174+
<SchemaRendererProvider dataSource={myAPI}>
180175
<AppShell sidebar={<MySidebar />}>
181176
<ContactList />
182177
</AppShell>
183-
</DataSourceProvider>
178+
</SchemaRendererProvider>
184179
);
185180
}
186181

187182
function ContactList() {
188-
const dataSource = useDataSource();
189183
return (
190-
<ObjectView schema={{ type: 'object-view', objectName: 'contact' }} dataSource={dataSource} />
184+
<ObjectView schema={{ type: 'object-view', objectName: 'contact' }} dataSource={myAPI} />
191185
);
192186
}
193187
```
@@ -198,8 +192,8 @@ Both files below open with `'use client'`. Under the Next.js App Router every
198192
module under `app/` is a **server** component by default, and the `@object-ui/*`
199193
packages carry no `'use client'` banner of their own — so the client boundary has
200194
to be declared here, in the files that import them. Without the directive the
201-
layout's React context providers and the page's `useDataSource()` hook are both
202-
asked to run on the server, where neither exists.
195+
layout's React context providers and the page's client view are both asked to
196+
run on the server, where neither exists.
203197

204198
`app/layout.tsx`:
205199

@@ -208,7 +202,7 @@ asked to run on the server, where neither exists.
208202

209203
import { AppShell } from '@object-ui/app-shell';
210204
import type { MinimalAppShellProps } from '@object-ui/app-shell';
211-
import { ThemeProvider } from '@object-ui/providers';
205+
import { ThemeProvider } from '@object-ui/react';
212206

213207
export default function RootLayout({ children }: { children: MinimalAppShellProps['children'] }) {
214208
return (
@@ -225,43 +219,44 @@ export default function RootLayout({ children }: { children: MinimalAppShellProp
225219
'use client';
226220

227221
import { ObjectView } from '@object-ui/plugin-view';
228-
import { useDataSource } from '@object-ui/providers';
222+
import type { DataSource } from '@object-ui/types';
223+
224+
// Your backend adapter, imported from your own module.
225+
declare const myAPI: DataSource;
229226

230227
export default function Page({ params }: { params: { object: string } }) {
231-
const dataSource = useDataSource();
232-
return <ObjectView schema={{ type: 'object-view', objectName: params.object }} dataSource={dataSource} />;
228+
return <ObjectView schema={{ type: 'object-view', objectName: params.object }} dataSource={myAPI} />;
233229
}
234230
```
235231

236232
### Example 3: Embedded Widget
237233

238234
```tsx
239235
import { ObjectView } from '@object-ui/plugin-view';
240-
import { DataSourceProvider, useDataSource } from '@object-ui/providers';
241-
import type { DataSourceProviderProps } from '@object-ui/providers';
236+
import { SchemaRendererProvider } from '@object-ui/react';
237+
import type { DataSource } from '@object-ui/types';
242238

243239
// Your backend adapter, as in Example 1 — declared here because every block on
244240
// this page compiles on its own.
245-
declare const myAPI: DataSourceProviderProps['dataSource'];
241+
declare const myAPI: DataSource;
246242

247243
function MyExistingApp() {
248244
return (
249245
<div className="my-app">
250246
<header>My App Header</header>
251247

252248
{/* Embed ObjectUI widget */}
253-
<DataSourceProvider dataSource={myAPI}>
249+
<SchemaRendererProvider dataSource={myAPI}>
254250
<ContactWidget />
255-
</DataSourceProvider>
251+
</SchemaRendererProvider>
256252

257253
<footer>My App Footer</footer>
258254
</div>
259255
);
260256
}
261257

262258
function ContactWidget() {
263-
const dataSource = useDataSource();
264-
return <ObjectView schema={{ type: 'object-view', objectName: 'contact' }} dataSource={dataSource} />;
259+
return <ObjectView schema={{ type: 'object-view', objectName: 'contact' }} dataSource={myAPI} />;
265260
}
266261
```
267262

‎docs/audits/2901-spec-enum-renderer-coverage.md‎

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -76,7 +76,7 @@ The #2897 shape. Validates, renders nothing, nobody knows it should be full.
7676
| 7 chart types draw an **empty plot** | [AdvancedChartImpl.tsx:343](../../packages/plugin-charts/src/AdvancedChartImpl.tsx) | Grid, axes, tooltip and legend all render; every series mark hits `return null`. Looks like an empty dataset. |
7777
| 6 of 9 animation presets do nothing | [useAnimation.ts:64](../../packages/react/src/hooks/useAnimation.ts) | `PRESET_CLASSES` is keyed in **hyphens** (`'slide-up'`), the spec enum in **underscores** (`slide_up`); `rotate`/`flip` absent entirely. Lookup misses → `''` → no animation. |
7878
| 3 of 6 easings emit **invalid CSS** | [useAnimation.ts:112](../../packages/react/src/hooks/useAnimation.ts) | Same split, but `EASING_MAP[easing] \|\| easing` falls through to the raw string. `animationTimingFunction: 'ease_in_out'` — browser drops it, devtools shows the attribute populated. |
79-
| `mode: 'auto'` breaks theming | [ThemeProvider.tsx:38](../../packages/app-shell/src/chrome/ThemeProvider.tsx) + [providers/ThemeProvider.tsx:33](../../packages/providers/src/ThemeProvider.tsx) | Renderer branches on `"system"`; spec says `auto`. `root.classList.add('auto')` matches no Tailwind variant → light theme, OS preference no longer followed, no error. |
79+
| `mode: 'auto'` breaks theming | [ThemeProvider.tsx:38](../../packages/app-shell/src/chrome/ThemeProvider.tsx) + `providers/ThemeProvider.tsx` (retired in objectui#13453) | Renderer branches on `"system"`; spec says `auto`. `root.classList.add('auto')` matches no Tailwind variant → light theme, OS preference no longer followed, no error. |
8080
| Export **PDF** downloads nothing | [ObjectGrid.tsx:1258](../../packages/plugin-grid/src/ObjectGrid.tsx), [ListView.tsx:1611](../../packages/plugin-list/src/ListView.tsx) | Excluded from `serverEligible` and absent from the client fallback. Popover closes, no file. `xlsx` does the same whenever the server path is unavailable. |
8181
| Timeline `scale` blanks the axis | [renderer.tsx:270](../../packages/plugin-timeline/src/renderer.tsx) | `hour`/`quarter`/`year` produce zero header columns. All six are ignored entirely on the default `vertical` variant. |
8282
| All 6 toast positions discarded | [toaster.tsx:15](../../packages/components/src/renderers/feedback/toaster.tsx) | `<SonnerToaster />` with no props, `inputs: []`. |

‎examples/README.md‎

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ Runnable examples that show how to consume ObjectUI in different scenarios. Pick
77
| Example | Use it when… | Backend | Bundle | What it gives you |
88
|---|---|---|---|---|
99
| [`hello-world/`](./hello-world) | You want the smallest possible `<SchemaRenderer>` demo to see the JSON → React pipeline. | None (in-memory schema) | Tiny | A single `App.tsx` rendering one schema. |
10-
| [`byo-backend-console/`](./byo-backend-console) | You want to **embed** ObjectUI into your own app and connect it to **your own** REST/GraphQL backend. | Bring-your-own (mock REST shown) | ~50 KB | `@object-ui/app-shell` + `@object-ui/providers`, custom router, custom `DataSource`. ~100 lines of integration code, no auth, no plugins. |
10+
| [`byo-backend-console/`](./byo-backend-console) | You want to **embed** ObjectUI into your own app and connect it to **your own** REST/GraphQL backend. | Bring-your-own (mock REST shown) | ~50 KB | `@object-ui/app-shell` + `@object-ui/react`, custom router, custom `DataSource`. ~100 lines of integration code, no auth, no plugins. |
1111
| [`console-starter/`](./console-starter) | You want a **fork-ready, opinionated console** with the full plugin set already wired against an **ObjectStack** backend. | ObjectStack (`/api/v1`) | Full | `@object-ui/app-shell` `ConsoleShell` + `AuthProvider` + every `@object-ui/plugin-*` (grid, kanban, calendar, charts, dashboard, designer, detail, form, list, report, view, chatbot). |
1212

1313
> **Rule of thumb:**

‎examples/byo-backend-console/README.md‎

Lines changed: 11 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ This example demonstrates how third-party systems can integrate ObjectUI compone
1010
- ✅ Custom data adapter (mock REST API, not ObjectStack)
1111
- ✅ Using `@object-ui/app-shell` for the page shell
1212
- ✅ Using `@object-ui/plugin-view` for object views (`ObjectView`)
13-
- ✅ Using `@object-ui/providers` for context
13+
- ✅ Using `@object-ui/react` for the theme and the ambient data source
1414
- ✅ No console dependencies
1515
- ✅ ~100 lines of integration code
1616

@@ -65,18 +65,18 @@ object view:
6565
import { Routes, Route, useParams } from 'react-router-dom';
6666
import { AppShell } from '@object-ui/app-shell';
6767
import { ObjectView } from '@object-ui/plugin-view';
68-
import { ThemeProvider, DataSourceProvider } from '@object-ui/providers';
68+
import { ThemeProvider, SchemaRendererProvider } from '@object-ui/react';
6969

7070
function App() {
7171
return (
7272
<ThemeProvider>
73-
<DataSourceProvider dataSource={mockDataSource}>
73+
<SchemaRendererProvider dataSource={mockDataSource}>
7474
<AppShell sidebar={<MySidebar />}>
7575
<Routes>
7676
<Route path="/:objectName" element={<ObjectPage />} />
7777
</Routes>
7878
</AppShell>
79-
</DataSourceProvider>
79+
</SchemaRendererProvider>
8080
</ThemeProvider>
8181
);
8282
}
@@ -101,7 +101,7 @@ function ObjectPage() {
101101
Full control over routes - no predefined structure:
102102

103103
```tsx
104-
import { useDataSource } from '@object-ui/providers';
104+
import { mockDataSource } from './mockDataSource';
105105

106106
function AppRoutes() {
107107
return (
@@ -114,15 +114,13 @@ function AppRoutes() {
114114
);
115115
}
116116

117-
// One small component per object. Inside `DataSourceProvider`, `useDataSource()`
118-
// supplies the data source that `ObjectView` requires.
117+
// One small component per object. `ObjectView` requires its `dataSource`
118+
// prop, so pass your adapter in.
119119
function ObjectListPage({ objectName }: { objectName: string }) {
120-
const dataSource = useDataSource();
121-
122120
return (
123121
<ObjectView
124122
schema={{ type: 'object-view', objectName }}
125-
dataSource={dataSource}
123+
dataSource={mockDataSource}
126124
/>
127125
);
128126
}
@@ -143,11 +141,9 @@ export default function RootLayout({ children }: { children: React.ReactNode })
143141
// app/[object]/page.tsx
144142
'use client';
145143
import { ObjectView } from '@object-ui/plugin-view';
146-
import { useDataSource } from '@object-ui/providers';
144+
import { dataSource } from '../../lib/dataSource'; // your adapter
147145

148146
export default function ObjectPage({ params }: { params: { object: string } }) {
149-
const dataSource = useDataSource();
150-
151147
return (
152148
<ObjectView
153149
schema={{ type: 'object-view', objectName: params.object }}
@@ -182,11 +178,11 @@ function App() {
182178
}
183179

184180
return (
185-
<DataSourceProvider dataSource={myDataSource}>
181+
<SchemaRendererProvider dataSource={myDataSource}>
186182
<AppShell sidebar={<Sidebar onLogout={logout} />}>
187183
{/* ... */}
188184
</AppShell>
189-
</DataSourceProvider>
185+
</SchemaRendererProvider>
190186
);
191187
}
192188
```

‎examples/byo-backend-console/package.json‎

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,6 @@
1616
"@object-ui/components": "workspace:*",
1717
"@object-ui/plugin-form": "workspace:*",
1818
"@object-ui/plugin-view": "workspace:*",
19-
"@object-ui/providers": "workspace:*",
2019
"@object-ui/react": "workspace:*",
2120
"@object-ui/types": "workspace:*",
2221
"react": "19.3.0",

0 commit comments

Comments
 (0)