@immediately-run/grove 0.1.2 → 0.1.3
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.
- package/README.md +43 -115
- package/llms.txt +5 -2
- package/package.json +10 -8
- package/src/App.tsx +11 -7
- package/src/GroveApp.css +484 -152
- package/src/GroveWiki.tsx +105 -30
- package/src/components/AssetImage.tsx +1 -12
- package/src/components/Backlinks.tsx +2 -2
- package/src/components/Catalogue.test.tsx +157 -0
- package/src/components/ContentTheme.test.tsx +146 -0
- package/src/components/ContentTheme.tsx +111 -0
- package/src/components/DocList.infinite.test.tsx +177 -0
- package/src/components/DocList.tsx +82 -9
- package/src/components/Drawer.tsx +14 -2
- package/src/components/EntryHeader.tsx +23 -12
- package/src/components/EntryImage.test.tsx +210 -0
- package/src/components/EntryImage.tsx +47 -0
- package/src/components/Galleries.test.tsx +98 -0
- package/src/components/GroveAgent.test.tsx +330 -0
- package/src/components/GroveAgent.tsx +269 -150
- package/src/components/GroveNav.test.tsx +145 -5
- package/src/components/GroveNav.tsx +51 -8
- package/src/components/Icon.tsx +0 -1
- package/src/components/InlineProse.tsx +37 -0
- package/src/components/LayoutGallery.tsx +65 -0
- package/src/components/PageView.tsx +18 -3
- package/src/components/Search.test.tsx +113 -0
- package/src/components/Search.tsx +53 -18
- package/src/components/Sidebar.test.tsx +135 -0
- package/src/components/Sidebar.tsx +114 -12
- package/src/components/TableOfContents.test.tsx +27 -16
- package/src/components/ThemeAssets.test.tsx +109 -0
- package/src/components/ThemeAssets.tsx +63 -0
- package/src/components/ThemeGallery.tsx +31 -0
- package/src/components/Timeline.tsx +5 -2
- package/src/components/WikiLink.tsx +2 -2
- package/src/data/catalogue.ts +54 -0
- package/src/data/themeFonts.ts +58 -0
- package/src/data/themes.ts +16 -7
- package/src/hooks/{useCorpusMetadata.ts → useBundleMetadata.ts} +6 -6
- package/src/hooks/useContentComponents.ts +1 -1
- package/src/hooks/useEditAffordance.ts +17 -4
- package/src/hooks/useOverlayFocusDismiss.test.tsx +139 -0
- package/src/hooks/useOverlayFocusDismiss.ts +118 -0
- package/src/hooks/useScrollReset.test.tsx +132 -0
- package/src/hooks/useScrollReset.ts +52 -0
- package/src/index.css +9 -2
- package/src/lib/agentPrompt.test.ts +96 -0
- package/src/lib/agentPrompt.ts +86 -0
- package/src/lib/agentTools.test.ts +115 -0
- package/src/lib/agentTools.ts +132 -0
- package/src/lib/agentTranscript.ts +50 -0
- package/src/lib/assetPath.test.ts +36 -0
- package/src/lib/assetPath.ts +42 -0
- package/src/lib/collectionCalls.test.ts +69 -0
- package/src/lib/content.test.ts +10 -2
- package/src/lib/content.ts +7 -0
- package/src/lib/contentStylesheet.test.ts +80 -0
- package/src/lib/contentStylesheet.ts +103 -0
- package/src/lib/corpusScan.test.ts +37 -3
- package/src/lib/corpusScan.ts +17 -2
- package/src/lib/inlineProse.parity.test.ts +52 -0
- package/src/lib/layout.ts +29 -0
- package/src/lib/pageVariants.test.tsx +87 -0
- package/src/lib/queries.test.ts +33 -1
- package/src/lib/queries.ts +33 -1
- package/src/lib/reachCard.test.ts +94 -0
- package/src/lib/reachCard.ts +112 -0
- package/src/lib/shell.ts +7 -0
- package/src/lib/starterSweep.test.tsx +160 -0
- package/src/lib/starterSweep.ts +97 -0
- package/src/lib/themeAssets.test.ts +135 -0
- package/src/lib/themeAssets.ts +143 -0
- package/src/lib/themeSelection.test.ts +2 -2
- package/src/mdxComponents.ts +4 -0
- package/viewer-manifest.schema.json +37 -0
- package/viewer.manifest.json +132 -6
package/README.md
CHANGED
|
@@ -1,122 +1,50 @@
|
|
|
1
|
-
#
|
|
1
|
+
# Grove — the wiki viewer for [immediately.run](https://immediately.run)
|
|
2
|
+
|
|
3
|
+
Grove renders an MDX corpus as a wiki: plain interlinked entries with frontmatter,
|
|
4
|
+
a sidebar, search, backlinks, tags, timelines — transpiled in the browser, no
|
|
5
|
+
server, no build step at runtime. It ships three ways:
|
|
6
|
+
|
|
7
|
+
1. **As a fork** — copy this repo, replace `content/` with your entries, push,
|
|
8
|
+
open it on immediately.run. Your corpus, your code, one repo.
|
|
9
|
+
2. **As the dispatched viewer** — a corpus mounted into a running Grove via the
|
|
10
|
+
`open-wiki` task; the wiki is somebody else's directory and Grove reads it
|
|
11
|
+
through the mount (the engine never assumes it owns the corpus).
|
|
12
|
+
3. **As a pinned library** — `@immediately-run/grove` as an ordinary npm
|
|
13
|
+
dependency: compose `src/lib.ts`'s helpers and the component vocabulary into
|
|
14
|
+
your own viewer.
|
|
15
|
+
|
|
16
|
+
The composition surface — every component, its tier and overridability, the
|
|
17
|
+
frontmatter keys the engine reads — is declared in
|
|
18
|
+
[`viewer.manifest.json`](./viewer.manifest.json) and summarized in [`llms.txt`](./llms.txt).
|
|
19
|
+
The themes and layouts are compared live by the `Themes` and `Layouts` entries of
|
|
20
|
+
the sample corpus; the theming contract (token-only themes, declared faces,
|
|
21
|
+
checked contrast) is stated in [`THEMING.md`](./THEMING.md). What the engine owns
|
|
22
|
+
versus what content may reach is [`docs/ENGINE_BOUNDARY.md`](./docs/ENGINE_BOUNDARY.md).
|
|
23
|
+
|
|
24
|
+
## Running locally
|
|
2
25
|
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
## Try it instantly
|
|
8
|
-
|
|
9
|
-
Try this template on [immediately.run](https://immediately.run/present/github/immediately-run/new-project-template/main/files/src/App.tsx)
|
|
10
|
-
|
|
11
|
-
> Using this as a starting point for your own app? After you push to your repo,
|
|
12
|
-
> update the link above to
|
|
13
|
-
> `https://immediately.run/present/github/<owner>/<repo>/<ref>/files/src/App.tsx`.
|
|
14
|
-
|
|
15
|
-
## Use this template
|
|
16
|
-
|
|
17
|
-
1. Create a new repo from this template (or copy the files).
|
|
18
|
-
2. `npm install`
|
|
19
|
-
3. `npm run dev` and start editing `src/App.tsx`.
|
|
20
|
-
4. Push to GitHub and open it on immediately.run with the link above.
|
|
21
|
-
|
|
22
|
-
## Fast loading on immediately.run (auto-cache)
|
|
23
|
-
|
|
24
|
-
immediately.run normally reads your sources from the GitHub API, which is slow
|
|
25
|
-
and rate-limited for anonymous visitors. This template ships a GitHub Action
|
|
26
|
-
([`.github/workflows/cache.yml`](./.github/workflows/cache.yml)) that, on every
|
|
27
|
-
push to `main`, builds a pre-cached zip of your repo and publishes it to your
|
|
28
|
-
repo's **own GitHub Pages**. immediately.run finds it automatically at
|
|
29
|
-
`https://<owner>.github.io/<repo>/cached_repositories/main.zip` and loads from
|
|
30
|
-
there — falling back to the API if it's missing.
|
|
31
|
-
|
|
32
|
-
The cache also embeds a manifest sidecar, so visitors can push edits back to
|
|
33
|
-
GitHub even when the app was loaded from the zip.
|
|
34
|
-
|
|
35
|
-
**Setup:** push to `main` and the workflow does the rest. When the immediately-run
|
|
36
|
-
org's **deploy GitHub App** has **Pages: write** + **Administration: write** and its
|
|
37
|
-
`DEPLOY_APP_ID` / `DEPLOY_APP_PRIVATE_KEY` are org secrets, the workflow **enables
|
|
38
|
-
Pages for you** on the first run — no manual step. Otherwise, do it once:
|
|
39
|
-
**Settings → Pages → Build and deployment → Source: GitHub Actions**. (The cache may
|
|
40
|
-
lag a push by up to ~10 minutes of GitHub Pages CDN caching.)
|
|
41
|
-
|
|
42
|
-
### Always run the newest commit
|
|
43
|
-
|
|
44
|
-
By default the cached version is served even if it's a few minutes behind
|
|
45
|
-
`main`. If your app must always reflect the very latest commit, add this to
|
|
46
|
-
`package.json`:
|
|
47
|
-
|
|
48
|
-
```jsonc
|
|
49
|
-
{
|
|
50
|
-
"immediately.run": {
|
|
51
|
-
"requireLatest": true
|
|
52
|
-
}
|
|
53
|
-
}
|
|
54
|
-
```
|
|
55
|
-
|
|
56
|
-
immediately.run still boots instantly from the cache, then checks in the
|
|
57
|
-
background (one API request) whether the cache is current and, if not, reloads
|
|
58
|
-
from GitHub.
|
|
59
|
-
|
|
60
|
-
## How it's organized
|
|
61
|
-
|
|
62
|
-
immediately.run renders the **default export of `src/App.tsx`** — that's the
|
|
63
|
-
entry point, not `main.tsx`.
|
|
64
|
-
|
|
65
|
-
```
|
|
66
|
-
src/
|
|
67
|
-
main.tsx # local vite dev/build entry only — immediately.run IGNORES this
|
|
68
|
-
App.tsx # ROOT: default export + imports the global CSS
|
|
69
|
-
index.css # fonts, design tokens (dark + light), resets
|
|
70
|
-
App.css # layout + component styles
|
|
71
|
-
mdx.d.ts # type shim so `import X from './x.mdx'` works
|
|
72
|
-
components/ # one default-exported React component per file
|
|
73
|
-
data/ # typed data arrays (NO components/JSX here)
|
|
74
|
-
hooks/ # custom hooks (NO components here)
|
|
75
|
-
assets/ # images you import, e.g. import logo from './assets/logo.png'
|
|
76
|
-
```
|
|
77
|
-
|
|
78
|
-
The included page shows the core patterns: a data array mapped to cards
|
|
79
|
-
(`data/features.ts` → `components/Features.tsx`), a custom hook
|
|
80
|
-
(`hooks/useTheme.ts` → `components/ThemeSwitch.tsx`), and local React state
|
|
81
|
-
(`components/Counter.tsx`).
|
|
82
|
-
|
|
83
|
-
## Filesystem access (`fs`)
|
|
84
|
-
|
|
85
|
-
immediately.run apps can read and write a filesystem by importing `fs` (async
|
|
86
|
-
only — `fs.promises.*` and callback style). This template has local-dev support
|
|
87
|
-
for it built in via [`@immediately-run/dev-fs`](https://github.com/immediately-run/dev-fs),
|
|
88
|
-
a Vite plugin (already wired into `vite.config.ts`) that bridges the same
|
|
89
|
-
filesystem to your real local disk during `vite dev`. See that repo for the
|
|
90
|
-
supported API and details.
|
|
91
|
-
|
|
92
|
-
```ts
|
|
93
|
-
import fs from 'fs'
|
|
94
|
-
|
|
95
|
-
await fs.promises.writeFile('/data/notes.txt', 'hello', 'utf8')
|
|
96
|
-
const text = await fs.promises.readFile('/data/notes.txt', 'utf8')
|
|
26
|
+
```bash
|
|
27
|
+
npm install
|
|
28
|
+
npm run dev # vite dev server — the sample handbook
|
|
29
|
+
npm run verify # lint + build + tests + the manifest/contrast/token gates
|
|
97
30
|
```
|
|
98
31
|
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
See [`CLAUDE.md`](./CLAUDE.md) for the full list. The essentials:
|
|
32
|
+
On immediately.run, open
|
|
33
|
+
`https://immediately.run/present/github/<owner>/grove/main/files/content/home.mdx`
|
|
34
|
+
(fork) — or dispatch it at any wiki directory with the platform's file picker.
|
|
35
|
+
A GitHub Action (`.github/workflows/cache.yml`) publishes a pre-cached zip to
|
|
36
|
+
this repo's own Pages on every push to `main`, so anonymous loads are fast.
|
|
105
37
|
|
|
106
|
-
|
|
107
|
-
- **A file that exports a component exports *only* components** — data, consts,
|
|
108
|
-
and helpers go in `data/`, `hooks/`, or `lib/`. `npm run lint` enforces this.
|
|
109
|
-
- **Pull colors, fonts, radii, and shadows from the tokens in `index.css`**
|
|
110
|
-
rather than hard-coding values.
|
|
38
|
+
## Authoring entries
|
|
111
39
|
|
|
112
|
-
|
|
40
|
+
Entries are `.mdx` files under `content/` with YAML frontmatter (`title`, `tags`,
|
|
41
|
+
`date`, `nav`, `order`, plus the engine keys in the manifest: `site`, `theme`,
|
|
42
|
+
`layout`, `view`, `frame`, `render`, `cover`, …). Interlink with wiki links;
|
|
43
|
+
declare a picture per entry with `cover:`; group a folder with a
|
|
44
|
+
`content/<dir>/_layout.mdx` starter. The built-in agent answers questions about
|
|
45
|
+
the corpus over the host's chat slot — ask it where things are before editing.
|
|
113
46
|
|
|
114
|
-
|
|
47
|
+
## License
|
|
115
48
|
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
npm run dev # local dev server
|
|
119
|
-
npm run build # tsc -b && vite build — must pass with no type errors
|
|
120
|
-
npm run lint # eslint — enforces the React Fast Refresh / HMR rule
|
|
121
|
-
npm run preview # serve the production build
|
|
122
|
-
```
|
|
49
|
+
Apache-2.0. Bundled fonts in `assets/fonts/` carry their own notices
|
|
50
|
+
(OFL / USWDS) alongside.
|
package/llms.txt
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
# @immediately-run/grove — the viewer kit for directory-as-content wikis
|
|
2
2
|
|
|
3
|
-
> The Grove viewer: a kit of React components, layouts and themes for building immediately.run wikis. Composable as a fork, a dispatch target, or a pinned library. (v0.1.
|
|
3
|
+
> The Grove viewer: a kit of React components, layouts and themes for building immediately.run wikis. Composable as a fork, a dispatch target, or a pinned library. (v0.1.3)
|
|
4
4
|
|
|
5
5
|
Grove is NOT a wiki engine: routing, MDX compilation, the frontmatter index, link
|
|
6
6
|
spaces and heading anchors live in the sandbox + `@immediately-run/sdk`. What this
|
|
@@ -69,7 +69,7 @@ is one corpus's conventions (declared by that corpus, not this repo).
|
|
|
69
69
|
- `ChildPages` (engine, overridable) — The entries nested under this one.
|
|
70
70
|
- `Directory` (engine, overridable) — The entries under one corpus directory. Props: path: string?.
|
|
71
71
|
- `DirectoryList` (engine, overridable) — A folder listing as a table, with metadata columns chosen by `columns` and narrowed to those the rows actually carry. Props: path: string?, title: string?, columns: string?, sort: string?, hidden: boolean?.
|
|
72
|
-
- `DocList` (engine, overridable) — A queried list of entries — the generic index primitive. Props: tag: string?, limit: number?.
|
|
72
|
+
- `DocList` (engine, overridable) — A queried list of entries — the generic index primitive. paginate="infinite" windows it with a sentinel and a stated end (R3-314); the attribute must be a literal. Props: tag: string?, limit: number?, paginate: 'infinite'?, batch: number?.
|
|
73
73
|
- `DocsByTag` (engine, overridable) — Entries grouped under one tag. Props: tag: string?.
|
|
74
74
|
- `FamilyTree` (engine, overridable) — A relationship graph rendered from frontmatter links. Props: children: node?.
|
|
75
75
|
- `GroveFooter` (chrome, overridable) — The site footer.
|
|
@@ -79,6 +79,7 @@ is one corpus's conventions (declared by that corpus, not this repo).
|
|
|
79
79
|
- `Infobox` (engine, overridable) — The boxed summary panel a wiki entry carries beside its lede. Props: title: string?, children: node?.
|
|
80
80
|
- `Kbd` (engine, overridable) — A keyboard key. Props: children: node?.
|
|
81
81
|
- `KeyValue` (engine, overridable) — A definition-list row for infobox-style facts. Props: children: node?.
|
|
82
|
+
- `LayoutGallery` (engine, overridable) — The layouts gallery: the starters, page variants and collection shapes grouped by their three mechanisms, enumerated from this manifest.
|
|
82
83
|
- `Lede` (engine, overridable) — The opening paragraph, set apart typographically. Props: children: node?.
|
|
83
84
|
- `More` (engine, overridable) — A 'read more' pointer to a related entry. Props: href: string?, children: node?.
|
|
84
85
|
- `Outlet` (engine, LOCKED) — The layout chain's inward slot. NOT overridable — the chain's nesting is engine mechanics, and replacing it detaches every layer from the page it wraps.
|
|
@@ -88,6 +89,7 @@ is one corpus's conventions (declared by that corpus, not this repo).
|
|
|
88
89
|
- `TableOfContents` (engine, overridable) — The on-this-page heading list, which keeps the active entry in view as the reader scrolls. Props: entryKey: string?, title: string?, className: string?.
|
|
89
90
|
- `TagCloud` (engine, overridable) — Every tag in the corpus, weighted by use. Props: limit: number?.
|
|
90
91
|
- `TagList` (engine, overridable) — The tags of one entry, as links to their indexes. Props: tags: string[]?.
|
|
92
|
+
- `ThemeGallery` (engine, overridable) — The themes gallery: one row per shipped theme, enumerated from this manifest — adding a theme adds a row with no edit to the entry.
|
|
91
93
|
- `Timeline` (engine, overridable) — A dated sequence of entries or events. Props: children: node?.
|
|
92
94
|
- `Toc` (engine, overridable) — The table of contents derived from the entry's heading anchors. Props: depth: number?.
|
|
93
95
|
|
|
@@ -102,6 +104,7 @@ is one corpus's conventions (declared by that corpus, not this repo).
|
|
|
102
104
|
- `nav`
|
|
103
105
|
- `order`
|
|
104
106
|
- `tags`
|
|
107
|
+
- `cover`
|
|
105
108
|
|
|
106
109
|
Unknown keys pass through (carried, unread) — a corpus may keep its own vocabulary.
|
|
107
110
|
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@immediately-run/grove",
|
|
3
|
-
"version": "0.1.
|
|
3
|
+
"version": "0.1.3",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"main": "src/main.tsx",
|
|
6
6
|
"immediately.run": {
|
|
@@ -18,7 +18,8 @@
|
|
|
18
18
|
}
|
|
19
19
|
],
|
|
20
20
|
"requests": {
|
|
21
|
-
"task:invoke": {}
|
|
21
|
+
"task:invoke": {},
|
|
22
|
+
"llm:chat": {}
|
|
22
23
|
}
|
|
23
24
|
},
|
|
24
25
|
"scripts": {
|
|
@@ -27,18 +28,20 @@
|
|
|
27
28
|
"lint": "eslint .",
|
|
28
29
|
"test": "vitest run",
|
|
29
30
|
"preview": "vite preview",
|
|
30
|
-
"verify": "npm run check:llms && npm run check:engine-api:selftest && npm run check:engine-api && npm run check:manifest && npm run check:deps && npm run check:theme-contrast && npm run lint && npm run build && npm run test",
|
|
31
|
+
"verify": "npm run check:llms && npm run check:engine-api:selftest && npm run check:engine-api && npm run check:manifest && npm run check:deps && npm run check:published && npm run check:theme-contrast && npm run check:theme-token-only && npm run lint && npm run build && npm run test",
|
|
31
32
|
"check:theme-contrast": "node scripts/check-theme-contrast.mjs --self-test && node scripts/check-theme-contrast.mjs",
|
|
33
|
+
"check:theme-token-only": "node scripts/check-theme-token-only.mjs --self-test && node scripts/check-theme-token-only.mjs",
|
|
32
34
|
"check:manifest": "node scripts/check-manifest.mjs",
|
|
33
35
|
"check:deps": "node scripts/check-app-dependencies.mjs --self-test && node scripts/check-app-dependencies.mjs",
|
|
36
|
+
"check:published": "node scripts/check-published-parity.mjs --self-test && node scripts/check-published-parity.mjs --offline-ok",
|
|
34
37
|
"check:engine-api": "node scripts/check-engine-api.mjs",
|
|
35
38
|
"check:engine-api:selftest": "node scripts/check-engine-api.mjs --self-test",
|
|
36
39
|
"gen:llms": "node scripts/gen-llms.mjs",
|
|
37
40
|
"check:llms": "node scripts/gen-llms.mjs --check"
|
|
38
41
|
},
|
|
39
42
|
"dependencies": {
|
|
40
|
-
"@immediately-run/mdx-plugins": "0.
|
|
41
|
-
"@immediately-run/sdk": "^0.
|
|
43
|
+
"@immediately-run/mdx-plugins": "0.7.1",
|
|
44
|
+
"@immediately-run/sdk": "^0.67.0",
|
|
42
45
|
"react": "^19.2.5",
|
|
43
46
|
"react-dom": "^19.2.5"
|
|
44
47
|
},
|
|
@@ -58,8 +61,7 @@
|
|
|
58
61
|
"typescript": "~6.0.2",
|
|
59
62
|
"typescript-eslint": "^8.58.2",
|
|
60
63
|
"vite": "^8.0.9",
|
|
61
|
-
"vitest": "^4.1.9"
|
|
62
|
-
"@immediately-run/mdx-plugins": "0.4.0"
|
|
64
|
+
"vitest": "^4.1.9"
|
|
63
65
|
},
|
|
64
66
|
"description": "The Grove viewer: a kit of React components, layouts and themes for building immediately.run wikis. Composable as a fork, a dispatch target, or a pinned library.",
|
|
65
67
|
"license": "Apache-2.0",
|
|
@@ -85,7 +87,7 @@
|
|
|
85
87
|
"llms.txt"
|
|
86
88
|
],
|
|
87
89
|
"peerDependencies": {
|
|
88
|
-
"@immediately-run/sdk": "^0.
|
|
90
|
+
"@immediately-run/sdk": "^0.67.0",
|
|
89
91
|
"react": "^19.2.5",
|
|
90
92
|
"react-dom": "^19.2.5"
|
|
91
93
|
}
|
package/src/App.tsx
CHANGED
|
@@ -24,7 +24,7 @@ import { MetadataSource } from '@immediately-run/sdk';
|
|
|
24
24
|
import { TinkerableContext } from '@immediately-run/sdk/TinkerableContext';
|
|
25
25
|
import { MDXProvider } from '@immediately-run/sdk/MDXProvider';
|
|
26
26
|
import { useOpenWikiBoot } from './hooks/useOpenWikiBoot';
|
|
27
|
-
import {
|
|
27
|
+
import { useBundleMetadata } from './hooks/useBundleMetadata';
|
|
28
28
|
import { useContentComponents } from './hooks/useContentComponents';
|
|
29
29
|
import { getContentRoot } from './lib/contentRoot';
|
|
30
30
|
import { viewedDocumentForTarget } from './lib/content';
|
|
@@ -69,7 +69,7 @@ export default function App() {
|
|
|
69
69
|
}
|
|
70
70
|
}, [boot.status, outerHref]);
|
|
71
71
|
// Only a dispatched viewer scans; a fork's index is already in the context.
|
|
72
|
-
const
|
|
72
|
+
const bundle = useBundleMetadata(boot.status === 'ready' ? getContentRoot() : null);
|
|
73
73
|
// BOTH packagings, deliberately (R3-174). A corpus's own component vocabulary must not
|
|
74
74
|
// depend on how it was composed — `PLATFORM_LAYERING_SPEC` §1.1's mode-invariance rule —
|
|
75
75
|
// so a fork reads its marker too; that is one cheap open of a file already in `/app`.
|
|
@@ -93,8 +93,8 @@ export default function App() {
|
|
|
93
93
|
// invariant): rendering into a half-composed map would flash a missing-component error
|
|
94
94
|
// for `<RoadmapBoard>` until registration landed — the very error content components
|
|
95
95
|
// exist to remove — and a nested provider patched in afterwards would do the same.
|
|
96
|
-
// Holding here costs nothing, because the gate already exists for the
|
|
97
|
-
if (boot.status === 'waiting' ||
|
|
96
|
+
// Holding here costs nothing, because the gate already exists for the bundle scan.
|
|
97
|
+
if (boot.status === 'waiting' || bundle.status === 'scanning' || contentComponents.status === 'loading') {
|
|
98
98
|
return (
|
|
99
99
|
<div className="grove-boot">
|
|
100
100
|
<p className="grove-boot__msg">Opening…</p>
|
|
@@ -116,14 +116,18 @@ export default function App() {
|
|
|
116
116
|
wiki
|
|
117
117
|
);
|
|
118
118
|
|
|
119
|
-
|
|
120
|
-
|
|
119
|
+
// R3-315/R3-310 — the declared face set mounts INSIDE GroveWiki now, keyed to
|
|
120
|
+
// the resolved theme (the catalogue looks change the reading face); nothing
|
|
121
|
+
// font-shaped waits on the scan from here.
|
|
122
|
+
|
|
123
|
+
if (bundle.status === 'ready' && bundle.metadata) {
|
|
124
|
+
// Provide the scanned bundle as the metadata SOURCE through the supported
|
|
121
125
|
// surface (R3-276), not a wholesale TinkerableContext re-provision: the
|
|
122
126
|
// platform stays free to grow its own state, and the hooks read the nearest
|
|
123
127
|
// MetadataSource — so every consumer works unchanged, and nothing re-states
|
|
124
128
|
// host fields it does not own.
|
|
125
129
|
return (
|
|
126
|
-
<MetadataSource value={
|
|
130
|
+
<MetadataSource value={bundle.metadata}>{withComponents}</MetadataSource>
|
|
127
131
|
);
|
|
128
132
|
}
|
|
129
133
|
|