| 10.1-runtime-admin-extension-point |
02 |
ui |
| vue |
| admin-spa |
| custom-elements |
| openapi-fetch |
| tailwind |
| boardwalk |
| phrasebook |
|
| phase |
provides |
| 10.1-runtime-admin-extension-point |
10.1-01 widget, toolbar and partial routes, plugin asset route, schema keys assets/toolbarActions/headerPartial and widget/action/actionLabel/fill/path, typed in schema.d.ts |
|
| phase |
provides |
| 10-admin-vue-spa |
admin SPA, typed openapi-fetch client, field registry, toast queue, hygiene and dist gates |
|
|
| admin/src/app/pluginAssets.ts (loadScript, loadStyles, activateStyles, loadControllerAssets, assetAllowed, assetPrefix, OWNER_ATTRIBUTE) |
| formContext InjectionKeys FORM_VALUES, FORM_PATCH, FORM_LOCALE, FORM_ASSETS and the summer-action / 5000 ms widget contract |
| WidgetField (type widget) and PartialField (type partial), both valueless and group-labelled, rendered on create and update |
| PartialHost with partialNodes.ts (PARTIAL_TAGS, PARTIAL_DROPPED_TAGS, partialAttrAllowed, renderPartialNodes) |
| ExtensionFailure box (UI-SPEC S5) |
| list headerPartial host with refetch after bulk delete and toolbar actions |
| ListToolbar actions/busyAction props and action event; ListView onAction posting {} to toolbar/{action} |
| partial style kit (.summer-partial, .summer-stats, .summer-stat, .summer-stat__label, .summer-stat__value) documented with the public --c-* variables in the cabana README |
| backend::lang.extension.{busy,widget_failed,partial_failed,action_failed} in en and pl |
| Vite dev proxy for {prefix}/assets |
| rebuilt modules/boardwalk/dist |
|
| 10.1-03 application widget |
| partial and toolbar proof |
| 10.1-04 unit tests and gate |
| 14 Discogs |
|
| tokens |
tasks |
commits |
| 17900 |
3 |
3 |
|
c3b76b1afb |
a5e7dac10f |
| added |
patterns |
|
|
| Plugin custom elements are created imperatively in a node Vue never renders children into; data goes in as attributes only and requests come out as a bubbling summer-action event |
| Server node trees are rebuilt with h() under a client copy of the server allowlist; no string is parsed as markup |
| Controller assets load when the controller's list or form schema arrives; stylesheet links are owned per controller and toggled on every open |
|
|
| created |
modified |
| admin/src/app/pluginAssets.ts |
| admin/src/components/form/formContext.ts |
| admin/src/components/form/fields/WidgetField.vue |
| admin/src/components/form/fields/PartialField.vue |
| admin/src/components/partial/PartialHost.vue |
| admin/src/components/partial/partialNodes.ts |
| admin/src/components/ui/ExtensionFailure.vue |
| admin/tests/fixtures/extension.form-schema.json |
| admin/tests/fixtures/extension.list-schema.json |
| admin/tests/fixtures/extension.partial.json |
| admin/tests/smoke/extension.smoke.test.ts |
|
| admin/src/api/types.ts |
| admin/src/components/form/registry.ts |
| admin/src/components/form/FormField.vue |
| admin/src/components/list/ListToolbar.vue |
| admin/src/views/FormView.vue |
| admin/src/views/ListView.vue |
| admin/src/styles/main.css |
| admin/vite.config.ts |
| admin/tests/fixtures/typed.ts |
| admin/tests/fixtures/lang.json |
| modules/phrasebook/backend/lang/en/lang.yaml |
| modules/phrasebook/backend/lang/pl/lang.yaml |
| modules/cabana/README.md |
| modules/boardwalk/dist/** |
|
|
| A widget posts only the current values of its fill keys as values, since the server passes nothing else to the action |
| loadControllerAssets resolves with the failed script URLs; a widget whose element is still undefined after a script failure shows the failure box at once instead of waiting 5000 ms |
| Stylesheet links are keyed by controller and URL, so two controllers of one plugin sharing a file each keep their own link |
| The client allowlist also drops the server's removed tags (script, style, svg and so on) with their subtree instead of unwrapping them |
| A widget or partial field without a label has no label row and no aria-labelledby; FormField renders the label as a span only when one is declared |
| Empty action messages are not toasted |
|
| Extension controls read form state through formContext injections with safe defaults, so settings forms without a provider still render |
| Smoke tests stub document.head.appendChild so plugin scripts and links never load in happy-dom |
|
|
| id |
description |
requirement |
verification |
human_judgment |
| D1 |
A type: widget field loads its controller script, mounts the custom element with attributes only, posts summer-action through the typed client once while busy, patches only returned fill keys without saving, and toasts success or failure |
ADMIN-07 |
| kind |
ref |
status |
| automated_ui |
admin/tests/smoke/extension.smoke.test.ts#widget field (D-04, D-05, D-07, D-08) |
pass |
|
|
false |
|
| id |
description |
requirement |
verification |
human_judgment |
| D2 |
Plugin assets load only from {base}/assets/, once per URL with retry after failure, and stylesheet links of other controllers are disabled |
ADMIN-07 |
| kind |
ref |
status |
| automated_ui |
admin/tests/smoke/extension.smoke.test.ts#plugin assets (D-14, D-16) |
pass |
|
| kind |
ref |
status |
| automated_ui |
admin/tests/smoke/extension.smoke.test.ts#controller stylesheets (D-14, UI-SPEC S6) |
pass |
|
|
false |
|
| id |
description |
requirement |
verification |
human_judgment |
| D3 |
Header and form partials render the server node tree through the client allowlist with skeleton, empty, failure and keep-on-refetch states; hostile nodes never reach the DOM |
ADMIN-07 |
| kind |
ref |
status |
| automated_ui |
admin/tests/smoke/extension.smoke.test.ts#list header partial (D-03, D-11, UI-SPEC S1) |
pass |
|
| kind |
ref |
status |
| automated_ui |
admin/tests/smoke/extension.smoke.test.ts#form partial (D-09, UI-SPEC S2) |
pass |
|
| kind |
ref |
status |
| automated_ui |
admin/tests/smoke/extension.smoke.test.ts#partial node allowlist (D-17) |
pass |
|
|
false |
|
| id |
description |
requirement |
verification |
human_judgment |
| D4 |
Registered toolbar actions render after delete for admins who may run them, post {} with busy state, toast, reload the list and refetch the header partial |
ADMIN-07 |
| kind |
ref |
status |
| automated_ui |
admin/tests/smoke/extension.smoke.test.ts#toolbar actions (D-12, UI-SPEC S4) |
pass |
|
| kind |
ref |
status |
| unit |
admin/tests/list/ListToolbar.test.ts (Phase 10 create/delete behaviour unchanged) |
pass |
|
|
false |
|
| id |
description |
requirement |
verification |
human_judgment |
| D5 |
Framework strings resolve in en and pl, the embedded dist matches a fresh build and the Phase 10 hygiene rules hold |
ADMIN-07 |
| kind |
ref |
status |
| unit |
modules/phrasebook/phase10_test.go#TestPhase10SPAKeysResolve |
pass |
|
| kind |
ref |
status |
| other |
scripts/check-admin-dist.sh |
pass |
|
| kind |
ref |
status |
| other |
scripts/check-phase10.sh --hygiene |
pass |
|
|
false |
|
| id |
description |
verification |
human_judgment |
rationale |
| D6 |
Partial style kit and failure box look native in light and dark mode, labels wrap at 768px with pl copy, plugin module scripts load under CSP script-src 'self' and through the Vite /assets dev proxy |
|
true |
Visual layout, real module loading and the dev proxy need a real browser; happy-dom neither lays out nor loads module scripts (plan Task 3 human-check, UI-SPEC backstop rows) |
|
|
17min |
2026-09-29 |
complete |