Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions docs/app/app.config.ts
Original file line number Diff line number Diff line change
Expand Up @@ -19,9 +19,9 @@ export default defineAppConfig({
},
{
label: 'Adapters',
sections: ['adapters', 'frameworks', 'helpers'],
sections: ['adapters', 'frameworks'],
},
{ label: 'Plugins', sections: ['plugins'], link: 'section' as const },
{ label: 'Add-ons', sections: ['add-ons'], link: 'section' as const },
{ label: 'Reference', sections: ['references'], link: 'section' as const },
{ label: 'Errors', sections: ['errors'], link: 'section' as const },
// { label: 'Blog', sections: ['posts'], link: 'section' as const },
Expand Down
18 changes: 9 additions & 9 deletions docs/app/components/global/GettingStartedWizard.vue
Original file line number Diff line number Diff line change
Expand Up @@ -140,8 +140,8 @@ const DOC_CATALOG: Record<string, DocEntry> = {
'/guide/build-your-own-json-render-frontend': { title: 'Build Your Own JSON-Render Frontend', description: 'Implement the renderer contract in your own framework instead of the reference one.', icon: 'i-lucide-component' },
'/guide/build-your-own-hub-ui': { title: 'Build Your Own Hub UI', description: 'The two contracts a hub UI provider implements — node side and browser side.', icon: 'i-lucide-layout-panel-left' },
'/guide/standalone-cli': { title: 'Standalone CLI with Devframe', description: 'npx my-tool starts a dev server serving your SPA over type-safe RPC.', icon: 'i-lucide-terminal' },
'/helpers/interactive-auth': { title: 'Interactive Auth', description: 'An OTP auth layer over devframe\'s node-side primitives.', icon: 'i-lucide-key-round' },
'/helpers/utilities': { title: 'Utilities', description: 'Small, stable helpers bundled into devframe — no npm install.', icon: 'i-lucide-wrench' },
'/references/interactive-auth': { title: 'Interactive Auth', description: 'An OTP auth layer over devframe\'s node-side primitives.', icon: 'i-lucide-key-round' },
'/references/utilities': { title: 'Utilities', description: 'Small, stable helpers bundled into devframe — no npm install.', icon: 'i-lucide-wrench' },
'/adapters': { title: 'Adapters', description: 'Every path from a DevframeDefinition to a running devframe.', icon: 'i-lucide-shuffle' },
'/adapters/initiate': { title: 'The Standard Handler', description: 'initDevframe() turns a definition into a Web Standard Request → Response handler.', icon: 'i-lucide-server' },
'/adapters/cac': { title: 'CLI (cac)', description: 'A cac CLI around a DevframeDefinition with dev, build, and mcp commands.', icon: 'i-lucide-square-terminal' },
Expand All @@ -153,36 +153,36 @@ const DOC_CATALOG: Record<string, DocEntry> = {
'/frameworks/vite': { title: 'Vite', description: 'Author one devframe\'s SPA, or mount a whole hub, from a Vite plugin.', icon: 'i-simple-icons-vite' },
'/frameworks/next': { title: 'Next', description: 'Host devframes from a Next.js App Router app via a route handler.', icon: 'i-simple-icons-nextdotjs' },
'/frameworks/nuxt': { title: 'Nuxt', description: 'A Nuxt module split into authoring one devframe or mounting a hub.', icon: 'i-simple-icons-nuxtdotjs' },
'/plugins/a11y': { title: 'Accessibility Inspector', description: 'Runs axe-core against the user app and highlights violations in the page.', icon: 'i-lucide-accessibility' },
'/plugins/terminals': { title: 'Terminals', description: 'A terminal panel built on xterm.js.', icon: 'i-lucide-square-terminal' },
'/add-ons/devframes/a11y': { title: 'Accessibility Inspector', description: 'Runs axe-core against the user app and highlights violations in the page.', icon: 'i-lucide-accessibility' },
'/add-ons/devframes/terminals': { title: 'Terminals', description: 'A terminal panel built on xterm.js.', icon: 'i-lucide-square-terminal' },
}

/** Always worth reading, regardless of what's checked above. */
const BASE_DOCS = ['/guide', '/guide/devframe-definition', '/guide/tutorial-server-data-inspector']

/** `${section.key}:${item.value}` -> doc routes that answer is worth reading. */
const RECOMMENDATIONS: Record<string, string[]> = {
'dataSource:node': ['/guide/rpc', '/guide/shared-state', '/helpers/utilities'],
'dataSource:browser': ['/guide/client-context', '/guide/deep-linking', '/plugins/a11y'],
'dataSource:node': ['/guide/rpc', '/guide/shared-state', '/references/utilities'],
'dataSource:browser': ['/guide/client-context', '/guide/deep-linking', '/add-ons/devframes/a11y'],

'environments:standalone': ['/guide/standalone-cli', '/adapters/cac', '/adapters/build'],
'environments:framework': ['/adapters'],
'environments:all': ['/adapters/initiate', '/adapters', '/guide/devframe-definition'],

'availability:dev': ['/guide/rpc', '/guide/transports'],
'availability:build': ['/adapters/build', '/guide/client-assets'],
'availability:static': ['/adapters/build', '/helpers/utilities'],
'availability:static': ['/adapters/build', '/references/utilities'],
'availability:remote': ['/guide/transports', '/guide/security'],

'frontend:framework': ['/guide/client-assets', '/guide/client'],
'frontend:webcomponents': ['/guide/hub', '/guide/build-your-own-hub-ui'],
'frontend:nodeside': ['/guide/json-render', '/guide/build-your-own-json-render-frontend'],

'requirements:agent': ['/guide/agent-native', '/adapters/mcp'],
'requirements:terminal': ['/plugins/terminals'],
'requirements:terminal': ['/add-ons/devframes/terminals'],
'requirements:streaming': ['/guide/streaming'],
'requirements:deep-linking': ['/guide/deep-linking'],
'requirements:overlay': ['/guide/client-context', '/plugins/a11y'],
'requirements:overlay': ['/guide/client-context', '/add-ons/devframes/a11y'],
}

const selections = reactive<Record<string, string[]>>(
Expand Down
4 changes: 2 additions & 2 deletions docs/content/1.guide/1.tutorial-server-data-inspector.md
Original file line number Diff line number Diff line change
Expand Up @@ -245,7 +245,7 @@ export default defineConfig({
npx vite --config vite.hub.config.ts
```

Your inspector now sits in the hub's dock rail as a dock entry. Add more to `devframes: [...]` — your own or the [built-in devframes](/plugins) — and each gets its own. (The hub prints a code to authorize on first connect.)
Your inspector now sits in the hub's dock rail as a dock entry. Add more to `devframes: [...]` — your own or the [built-in devframes](/add-ons) — and each gets its own. (The hub prints a code to authorize on first connect.)

## Step 5 — Build a static version

Expand Down Expand Up @@ -317,7 +317,7 @@ node bin.mjs mcp # expose the tool to a coding agent over MCP

You can also assemble your own CLI from the adapter functions used above.

That's it for this tutorial. For a full-featured version, there's a ready-to-use [Data Inspector built-in devframe](/plugins/data-inspector) to use or read for reference.
That's it for this tutorial. For a full-featured version, there's a ready-to-use [Data Inspector built-in devframe](/add-ons/devframes/data-inspector) to use or read for reference.

## What's next

Expand Down
2 changes: 1 addition & 1 deletion docs/content/1.guide/10.standalone-cli.md
Original file line number Diff line number Diff line change
Expand Up @@ -188,7 +188,7 @@ Booleans become `--verbose` / `--no-verbose`, else `--depth <value>`; keys are c

## Common RPC functions

Recipes for opening files in the editor or OS explorer live in `devframe/recipes/common-rpc-functions` ([Common RPC Functions](/helpers/common-rpc-functions)).
Recipes for opening files in the editor or OS explorer live in `devframe/recipes/common-rpc-functions` ([Common RPC Functions](/references/common-rpc-functions)).

## Snapshot queries for static builds

Expand Down
2 changes: 1 addition & 1 deletion docs/content/1.guide/12.in-page-channel.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ navigation:
description: 'The in-page channel connects a devframe''s page script to its panels entirely in the browser — typed events, calls, and page-script-authoritative shared state, with no server involved.'
---

The in-page channel (`devframe/in-page-channel`) connects a devframe's page script to its panels entirely in the browser — typed events, calls, and page-script-authoritative shared state, with no server involved. It is how a live inspect-the-page loop (like the [a11y inspector](/plugins/a11y)'s scan/highlight cycle) works identically in dev and in a static build.
The in-page channel (`devframe/in-page-channel`) connects a devframe's page script to its panels entirely in the browser — typed events, calls, and page-script-authoritative shared state, with no server involved. It is how a live inspect-the-page loop (like the [a11y inspector](/add-ons/devframes/a11y)'s scan/highlight cycle) works identically in dev and in a static build.

## Overview

Expand Down
4 changes: 2 additions & 2 deletions docs/content/1.guide/16.hub.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ _Orchestrating multiple devtools (from [A Playground](https://github.com/devfram

## What the hub adds

`DevframeHubContext` adds four subsystems to `DevframeNodeContext`: `ctx.docks` registers dock entries and groups and [activates docks](#cross-iframe-dock-activation); `ctx.terminals` aggregates terminal sessions with streaming output ([Terminals](/plugins/terminals#hub-aggregation)); `ctx.messages` is the server-side toast/notification queue; `ctx.commands` is the hierarchical command palette with keybindings and `when` clauses. Each subsystem's API is in the [Hub API reference](/references/hub-api#hub-subsystems).
`DevframeHubContext` adds four subsystems to `DevframeNodeContext`: `ctx.docks` registers dock entries and groups and [activates docks](#cross-iframe-dock-activation); `ctx.terminals` aggregates terminal sessions with streaming output ([Terminals](/add-ons/devframes/terminals#hub-aggregation)); `ctx.messages` is the server-side toast/notification queue; `ctx.commands` is the hierarchical command palette with keybindings and `when` clauses. Each subsystem's API is in the [Hub API reference](/references/hub-api#hub-subsystems).

Data-driven UI panels are an opt-in [JSON-Render](/guide/json-render) package (a `json-render` dock type).

Expand Down Expand Up @@ -58,7 +58,7 @@ await rpc.call('hub:docks:activate', {
})
```

It mirrors into the `devframe:docks:active` shared-state slot; the [terminals dock](/plugins/terminals#focusing-a-session) reads `params.sessionId`, unknown ids no-op ([DF8107](/errors/DF8107)). Server-side: `ctx.docks.activate(dockId, params?)`.
It mirrors into the `devframe:docks:active` shared-state slot; the [terminals dock](/add-ons/devframes/terminals#focusing-a-session) reads `params.sessionId`, unknown ids no-op ([DF8107](/errors/DF8107)). Server-side: `ctx.docks.activate(dockId, params?)`.

## Process-control launchers

Expand Down
2 changes: 1 addition & 1 deletion docs/content/1.guide/17.client-context.md
Original file line number Diff line number Diff line change
Expand Up @@ -71,7 +71,7 @@ Client scripts execute in the user app's page realm (`window`); anchor shared st

### Dual boots

One bundle can serve as both a client script (default export) and, via a globally-guarded self-boot, a standalone page script ([a11y inspector](/plugins/a11y)).
One bundle can serve as both a client script (default export) and, via a globally-guarded self-boot, a standalone page script ([a11y inspector](/add-ons/devframes/a11y)).

## Iframe panels

Expand Down
10 changes: 6 additions & 4 deletions docs/content/1.guide/19.services.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,8 @@ description: 'ctx.services lets one devframe expose a typed, namespaced capabili

`ctx.services` lets one devframe expose a typed, namespaced capability visible to every devframe. Two tiers: in-process services (`provide`/`get`) share live objects between devframes; [wire services](#wire-services) also register RPC and advertise to RPC clients.

The [Services reference](/references/services) collects the host methods, the definition/descriptor fields, and the built-in services as lookup tables.

## Providing a service

Augment `DevframeServicesRegistry` with your id and type, then provide in setup:
Expand Down Expand Up @@ -113,11 +115,11 @@ A reactive UI subscribes via `rpc.services.state()`. `has()`/`get()`/`keys()` ar

### Built-in services

**`@devframes/service-open`** (`devframes:service:open`) opens files in an editor (`open-in-editor`, optional `line`/`column`) or OS explorer (`open-in-finder`), refusing paths outside the workspace root plus extra `roots` (`DS_OPEN_0002`), gating editors to `KNOWN_EDITORS`. Options `{ editor?, roots? }` (later wins; dirs union-merged).

**`@devframes/service-git`** (`devframes:service:git`) runs typed git ops — `status`, `log`, `show`, `readFile`, `diff`, `branches`, `tags`, `stage`, `unstage`, `commit` — on one repo fixed at install (`{ cwd? }`). Write ops are exposed; authorization is the host framework's boundary.
Three first-party wire services ship ready to install, each with its own page under [Add-ons › Services](/add-ons/services):

**`@devframes/service-shiki`** (`devframes:service:shiki`) renders [Shiki](https://shiki.style) highlighting on the node side via three RPC queries — `highlight` (dual-theme HTML), `code-to-hast`, `code-to-tokens` — all client-`cacheable`, LRU-cached per `(code, lang, themes)`. Options `{ themes?, langs? }` — light/dark pair (defaults `vitesse-light`/`vitesse-dark`; later wins) and preloaded languages (union-merged).
- **[`@devframes/service-open`](/add-ons/services/open)** (`devframes:service:open`) — open files in an editor or OS explorer, refusing paths outside the workspace root.
- **[`@devframes/service-git`](/add-ons/services/git)** (`devframes:service:git`) — typed read/write git operations on one repo.
- **[`@devframes/service-shiki`](/add-ons/services/shiki)** (`devframes:service:shiki`) — node-side [Shiki](https://shiki.style) highlighting, LRU-cached and dual-theme.

## Services, RPC, or shared state?

Expand Down
4 changes: 2 additions & 2 deletions docs/content/1.guide/20.deep-linking.md
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ await rpc.call('hub:docks:activate', {

The hub broadcasts the request and mirrors it into the [`devframe:docks:active`](/guide/shared-state) slot, so a dock mounting *because* of the switch converges on it. The target subscribes, filters on its `dockId`, and reads `params` — see [Cross-iframe dock activation](/guide/hub#cross-iframe-dock-activation).

Focus is one-shot: the [terminals dock](/plugins/terminals#focusing-a-session) reads `params.sessionId`, the [Data Inspector](/plugins/data-inspector#deep-linking) `params.sourceId`; a target naming something unregistered waits, then fires once. An id that never arrives is a no-op; an unknown `dockId` warns ([DF8107](/errors/DF8107)).
Focus is one-shot: the [terminals dock](/add-ons/devframes/terminals#focusing-a-session) reads `params.sessionId`, the [Data Inspector](/add-ons/devframes/data-inspector#deep-linking) `params.sourceId`; a target naming something unregistered waits, then fires once. An id that never arrives is a no-op; an unknown `dockId` warns ([DF8107](/errors/DF8107)).

## Standalone URL deep links

Expand All @@ -38,6 +38,6 @@ history.replaceState(history.state, '', `#${params.toString()}`)
window.addEventListener('hashchange', applyState)
```

The [terminals dock](/plugins/terminals#deep-linking) keys a selection as `#id=<sessionId>`; the [Data Inspector](/plugins/data-inspector#deep-linking) encodes its workbench (`#source=…&query=…` plus filter/auto-rerun flags). `replaceState` writes never fire `hashchange`, so boot read, live listener, and write-back don't loop.
The [terminals dock](/add-ons/devframes/terminals#deep-linking) keys a selection as `#id=<sessionId>`; the [Data Inspector](/add-ons/devframes/data-inspector#deep-linking) encodes its workbench (`#source=…&query=…` plus filter/auto-rerun flags). `replaceState` writes never fire `hashchange`, so boot read, live listener, and write-back don't loop.

Keep credentials out of anything shareable: a handshake token belongs in the query string, scrubbed once read (as the Data Inspector does), never in a copyable hash.
18 changes: 9 additions & 9 deletions docs/content/1.guide/23.built-with.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,18 +13,18 @@ description: 'Real-world devtools and hub UI providers built on devframe — fro

## Built-in Devframes

The [built-in devframes](/plugins) are real tools built on Devframe, each in a different UI framework:
The [built-in devframes](/add-ons) are real tools built on Devframe, each in a different UI framework:

| Devframe | UI framework | What it does |
|--------|--------------|--------------|
| [Data Inspector](/plugins/data-inspector) | Vue | Query live server-side objects with jora. |
| [Devframe Inspector](/plugins/inspect) | Vue | Browse RPC, shared state, and the agent-consumable API. |
| [Open Graph Viewer](/plugins/og) | Vue | Inspect Open Graph / Twitter metadata and card previews. |
| [Accessibility Inspector](/plugins/a11y) | Solid | Run axe-core; list WCAG violations. |
| [Git](/plugins/git) | React (Next.js) | Repository dashboard: status, graph, branches, diffs. |
| [Terminals](/plugins/terminals) | Svelte | Stream output and run interactive PTY shells. |
| [Code Server](/plugins/code-server) | Vue | Run VS Code in the browser. |
| [Assets](/plugins/assets) | Vue | Browse, preview, upload, rename, and delete files. |
| [Data Inspector](/add-ons/devframes/data-inspector) | Vue | Query live server-side objects with jora. |
| [Devframe Inspector](/add-ons/devframes/inspect) | Vue | Browse RPC, shared state, and the agent-consumable API. |
| [Open Graph Viewer](/add-ons/devframes/og) | Vue | Inspect Open Graph / Twitter metadata and card previews. |
| [Accessibility Inspector](/add-ons/devframes/a11y) | Solid | Run axe-core; list WCAG violations. |
| [Git](/add-ons/devframes/git) | React (Next.js) | Repository dashboard: status, graph, branches, diffs. |
| [Terminals](/add-ons/devframes/terminals) | Svelte | Stream output and run interactive PTY shells. |
| [Code Server](/add-ons/devframes/code-server) | Vue | Run VS Code in the browser. |
| [Assets](/add-ons/devframes/assets) | Vue | Browse, preview, upload, rename, and delete files. |

## Playable Examples

Expand Down
1 change: 0 additions & 1 deletion docs/content/4.helpers/.navigation.yml

This file was deleted.

18 changes: 0 additions & 18 deletions docs/content/4.helpers/index.md

This file was deleted.

1 change: 1 addition & 0 deletions docs/content/5.add-ons/.navigation.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
title: Add-ons
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,8 @@ await createCac(createGitDevframe({ repoRoot: process.cwd() })).parse()

Namespaced `devframes:plugin:git:*`. Reads — `status`, `log` (+ parent hashes), `branches` (ahead / behind), `diff` (unified patch) — are `query` (`snapshot: true`): live in dev, baked static, `isRepo: false` outside a repo. Write `stage` / `unstage` / `commit` are write-mode `action`s.

For a repo capability shared across devframes rather than this dashboard's own RPC, see the [`@devframes/service-git`](/add-ons/services/git) wire service.

## Source

[`plugins/git`](https://github.com/devframes/devframe/tree/main/plugins/git)
Original file line number Diff line number Diff line change
Expand Up @@ -82,12 +82,12 @@ Namespaced `devframes:plugin:assets:*`:
| `list` | `query`, `snapshot: true` | Every file: type, size, mtime. |
| `capabilities` | `query`, `snapshot: true` | Write-enabled flag; the allow-list. |
| `read-image-meta` | `query` | Width/height/orientation. |
| `read-text` | `query` | Truncated preview text; server-highlighted via [`@devframes/service-shiki`](/guide/services#built-in-services), else plain `<pre>`. |
| `read-text` | `query` | Truncated preview text; server-highlighted via [`@devframes/service-shiki`](/add-ons/services/shiki), else plain `<pre>`. |
| `upload` | `action` | Streaming upload slot; the SPA pipes bytes. |
| `rename` | `action` | Renames one (keeps extension). |
| `delete` | `action` | Deletes one or more. |
| `mkdir` | `action` | Creates a folder + parents. |
| `open-in-editor` / `reveal-in-folder` | `action` | Open/reveal via [`@devframes/service-open`](/guide/services#built-in-services); always registered. |
| `open-in-editor` / `reveal-in-folder` | `action` | Open/reveal via [`@devframes/service-open`](/add-ons/services/open); always registered. |

`upload` / `rename` / `delete` / `mkdir` register only with `write`.

Expand Down
Loading
Loading