You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Copy file name to clipboardExpand all lines: packages/opencode/specs/tui-plugins.md
+22-3Lines changed: 22 additions & 3 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -10,6 +10,7 @@ Technical reference for the current TUI plugin system.
10
10
- Package plugins can be installed from CLI or TUI.
11
11
- v1 plugin modules are target-exclusive: a module can export `server` or `tui`, never both.
12
12
- Server runtime keeps v0 legacy fallback (function exports / enumerated exports) after v1 parsing.
13
+
- npm packages can be TUI theme-only via `package.json["oc-themes"]` without a `./tui` entrypoint.
13
14
14
15
## TUI config
15
16
@@ -88,7 +89,8 @@ export default plugin
88
89
- If package `exports` exists, loader only resolves `./tui` or `./server`; it never falls back to `exports["."]`.
89
90
- For npm package specs, TUI does not use `package.json``main` as a fallback entry.
90
91
-`package.json``main` is only used for server plugin entrypoint resolution.
91
-
- If a configured plugin has no target-specific entrypoint, it is skipped with a warning (not a load failure).
92
+
- If a configured TUI package has no `./tui` entrypoint and no valid `oc-themes`, it is skipped with a warning (not a load failure).
93
+
- If a configured TUI package has no `./tui` entrypoint but has valid `oc-themes`, runtime creates a no-op module record and still loads it for theme sync and plugin state.
92
94
- If a package supports both server and TUI, use separate files and package `exports` (`./server` and `./tui`) so each target resolves to a target-only module.
93
95
- File/path plugins must export a non-empty `id`.
94
96
- npm plugins may omit `id`; package `name` is used.
@@ -101,10 +103,18 @@ export default plugin
101
103
102
104
## Package manifest and install
103
105
104
-
Install target detection is inferred from `package.json` entrypoints:
106
+
Install target detection is inferred from `package.json` entrypoints and theme metadata:
105
107
106
108
-`server` target when `exports["./server"]` exists or `main` is set.
107
109
-`tui` target when `exports["./tui"]` exists.
110
+
-`tui` target when `oc-themes` exists and resolves to a non-empty set of valid package-relative theme paths.
111
+
112
+
`oc-themes` rules:
113
+
114
+
-`oc-themes` is an array of relative paths.
115
+
- Absolute paths and `file://` paths are rejected.
116
+
- Resolved theme paths must stay inside the package directory.
117
+
- Invalid `oc-themes` causes manifest read failure for install.
108
118
109
119
Example:
110
120
@@ -289,9 +299,12 @@ Theme install behavior:
289
299
290
300
- Relative theme paths are resolved from the plugin root.
291
301
- Theme name is the JSON basename.
302
+
-`api.theme.install(...)` and `oc-themes` auto-sync share the same installer path.
303
+
- Theme copy/write runs under cross-process lock key `tui-theme:<dest>`.
292
304
- First install writes only when the destination file is missing.
293
305
- If the theme name already exists, install is skipped unless plugin metadata state is `updated`.
294
-
- On `updated`, host only rewrites themes previously tracked for that plugin and only when source `mtime`/`size` changed.
306
+
- On `updated`, host skips rewrite when tracked `mtime`/`size` is unchanged.
307
+
- When a theme already exists and state is not `updated`, host can still persist theme metadata when destination already exists.
295
308
- Local plugins persist installed themes under the local `.opencode/themes` area near the plugin config source.
296
309
- Global plugins persist installed themes under the global `themes` dir.
297
310
- Invalid or unreadable theme files are ignored.
@@ -328,6 +341,7 @@ Slot notes:
328
341
-`api.plugins.add(spec)` treats the input as the runtime plugin spec and loads it without re-reading `tui.json`.
329
342
-`api.plugins.add(spec)` no-ops when that resolved spec (or resolved plugin id) is already loaded.
330
343
-`api.plugins.add(spec)` assumes enabled and always attempts initialization (it does not consult config/KV enable state).
344
+
-`api.plugins.add(spec)` can load theme-only packages (`oc-themes` with no `./tui`) as runtime entries.
331
345
-`api.plugins.install(spec, { global? })` runs install -> manifest read -> config patch using the same helper flow as CLI install.
332
346
-`api.plugins.install(...)` returns either `{ ok: false, message, missing? }` or `{ ok: true, dir, tui }`.
333
347
-`api.plugins.install(...)` does not load plugins into the current session. Call `api.plugins.add(spec)` to load after install.
@@ -357,7 +371,11 @@ Metadata is persisted by plugin id.
357
371
- External TUI plugins load from `tuiConfig.plugin`.
0 commit comments