feat: preview task canvases with workspace data (#3887)
This commit is contained in:
@@ -7,6 +7,8 @@
|
||||
|
||||
The initial-grant rule is amended by
|
||||
[owner-authorized canvas creation](2026-09-10-canvas-creation-authority.md).
|
||||
Task placement and data scope are separated for owner-authorized canvases by
|
||||
[task canvas workspace data](2026-09-23-task-canvas-workspace-data.md).
|
||||
The bounded startup acknowledgement is specified in the
|
||||
[runtime design](../specs/plugins/system-design/isolated-web-app-contributions.md#runtime-startup-protocol);
|
||||
it adds no privileged host API.
|
||||
|
||||
@@ -4,6 +4,10 @@
|
||||
**Date:** 2026-09-10
|
||||
**Area:** backend, protocol, security
|
||||
|
||||
The task-data initial grant ceiling below is amended by
|
||||
[task canvas workspace data](2026-09-23-task-canvas-workspace-data.md).
|
||||
It remains the historical rule for version-1 authority.
|
||||
|
||||
## Context
|
||||
|
||||
A user asks their task agent to create a canvas, then must approve its first
|
||||
|
||||
@@ -0,0 +1,72 @@
|
||||
# ADR-2026-09-23-task-canvas-workspace-data: Separate canvas placement from data scope
|
||||
|
||||
**Status:** accepted
|
||||
**Date:** 2026-09-23
|
||||
**Area:** backend, frontend, protocol, security
|
||||
|
||||
## Context
|
||||
|
||||
Users create canvases from tasks and review their behavior before promotion.
|
||||
The original canvas contract binds task placement and data scope together. A
|
||||
task coordinator that calls the supported canvas task-list endpoint therefore
|
||||
receives only its creating task, even when the package declares task reads and
|
||||
the workspace has many tasks. Granting every capability would not remove that
|
||||
scope filter.
|
||||
|
||||
The [owner-authorized creation decision](2026-09-10-canvas-creation-authority.md)
|
||||
already treats the user's request as authority for the first release's exact
|
||||
declared grants. The [same-origin decision](2026-09-19-trusted-same-origin-canvases.md)
|
||||
also establishes that locally run canvas code has the viewer's ordinary browser
|
||||
authority. The relative canvas API should provide a coherent supported path
|
||||
without relying on direct first-party API calls.
|
||||
|
||||
## Decision
|
||||
|
||||
A task canvas has separate placement and data scopes. For a newly
|
||||
owner-authorized local canvas, the first valid release receives only its
|
||||
declared supported capabilities, with data scope limited to its current
|
||||
workspace. It remains placed in the creating task until the user promotes it.
|
||||
The task-list API can show every task in that workspace before promotion;
|
||||
current user authorization still applies. Promotion governs placement and
|
||||
sharing, and still requires human confirmation.
|
||||
|
||||
The data scope is server-owned, persisted, included in runtime bindings, and
|
||||
checked alongside grants on every canvas-protocol request. Agent or manifest
|
||||
input cannot choose a different workspace. Existing task-only releases retain
|
||||
their scope until a workspace owner reviews their exact declared permissions
|
||||
and explicitly enables workspace data access. Later permission increases and
|
||||
imported packages continue through their existing review paths.
|
||||
|
||||
This amends the task-scoped first-grant ceiling in the 2026-09-10 decision and
|
||||
the coupling of task canvas and task data scope in the 2026-08-26 decision. It
|
||||
does not change the same-origin trust decision or grant undeclared capabilities.
|
||||
|
||||
## Consequences
|
||||
|
||||
- An owner-created canvas can be evaluated with representative live workspace
|
||||
data and supported actions before it appears in workspace navigation.
|
||||
- Permission review remains tied to the exact capabilities a release uses;
|
||||
there is no blanket read, write, network, secret, or backend permission.
|
||||
- The runtime, persistence, review projection, and authoring guidance must
|
||||
carry placement and data scopes independently.
|
||||
- Existing task canvases require an explicit access upgrade or promotion to
|
||||
show workspace data. No retained release is silently broadened on upgrade.
|
||||
- The upgrade path must check current ownership and a versioned review
|
||||
snapshot atomically, then invalidate older runtime tokens.
|
||||
|
||||
## Alternatives Considered
|
||||
|
||||
- **Grant all possible permissions by default:** Does not remove the task-list
|
||||
scope filter and gives unused writes and network access to generated code.
|
||||
- **Require promotion before representative preview:** Leaves the user unable
|
||||
to judge the app before placing it in workspace navigation.
|
||||
- **Call ordinary Kandev APIs from canvas code:** Works only with browser user
|
||||
authority and bypasses the supported capability contract; capability-only
|
||||
hosts would still show one task.
|
||||
- **Silently widen all existing task canvases:** Changes retained release
|
||||
authority without a review of the code and exact declared capabilities.
|
||||
|
||||
## Related contracts
|
||||
|
||||
- [Workspace preview requirements](../specs/canvases/requirements/task-canvas-workspace-preview.md)
|
||||
- [Workspace preview design](../specs/canvases/system-design/task-canvas-workspace-preview.md)
|
||||
@@ -0,0 +1,152 @@
|
||||
---
|
||||
created: 2026-09-23
|
||||
status: complete
|
||||
requirements:
|
||||
- REQ-CANVASES-WORKSPACE-PREVIEW-001
|
||||
- REQ-CANVASES-LOCAL-CREATION-001
|
||||
- REQ-CANVASES-AGENT-WEB-APPS-003
|
||||
system_design:
|
||||
- ../../specs/canvases/system-design/task-canvas-workspace-preview.md
|
||||
- ../../specs/canvases/system-design/local-creation-authority.md
|
||||
- ../../specs/canvases/system-design/agent-authored-web-apps.md
|
||||
- ../../specs/plugins/system-design/canvas-workspace-data-scope.md
|
||||
legacy_specs: []
|
||||
---
|
||||
|
||||
# Implementation Plan: Task canvas workspace data preview
|
||||
|
||||
## Overview
|
||||
|
||||
Let an owner-created canvas use its declared capabilities across the current
|
||||
workspace while it remains in the creating task. First add the server-owned
|
||||
data-scope and review transaction, then expose the scope and legacy upgrade
|
||||
in the host, authoring guidance, and browser tests. Promotion continues to
|
||||
control workspace placement.
|
||||
|
||||
## Scope
|
||||
|
||||
### In scope
|
||||
|
||||
- Workspace task lists and all currently supported declared canvas data,
|
||||
write, event, state, and network capabilities before promotion.
|
||||
- A separate server-owned data scope on plugin instances and runtime bindings.
|
||||
- An explicit, reviewed workspace-data upgrade for existing task canvases.
|
||||
- Desktop and phone host scope presentation, localized copy, authoring and
|
||||
public documentation, and focused browser coverage.
|
||||
|
||||
### Out of scope
|
||||
|
||||
- Cross-workspace and installation-wide data access.
|
||||
- Blanket grants for undeclared capabilities, new capability kinds, or
|
||||
managed agent-generated backend code.
|
||||
- Silent widening of retained releases.
|
||||
|
||||
## Technical approach
|
||||
|
||||
1. Add nullable `data_scope_kind` to plugin instance persistence with null
|
||||
fallback to the existing placement `scope_kind`. Create version-2 local
|
||||
canvas authority with workspace data scope and exact workspace-ceiling
|
||||
declared grants. Keep other instances and historical authority unchanged.
|
||||
2. Carry data scope through `webapp.CapabilityBinding`, grant validation, and
|
||||
the relative browser protocol. Use it for tasks, workflows, writes,
|
||||
messages, dependency projection, and events. Bind every operation to the
|
||||
trusted workspace and current user authorization. Follow the
|
||||
[plugin runtime design](../../specs/plugins/system-design/canvas-workspace-data-scope.md).
|
||||
3. Add an owner-reviewed workspace-data upgrade for retained task canvases
|
||||
using the active release ID, permission digest, and grant generation as
|
||||
conditional transaction inputs. Keep placement and package unchanged.
|
||||
4. Project placement and data scope separately in canvas context and host
|
||||
review. Update authoring instructions and public canvas/API docs. Use the
|
||||
existing desktop action menu and phone action drawer for legacy upgrade.
|
||||
|
||||
Likely backend files include `internal/plugins/instances/store.go`,
|
||||
`internal/plugins/webapp/tokens.go`, `internal/plugins/webapp_protocol*.go`,
|
||||
`internal/canvas/authoring.go`, `internal/canvas/service.go`, and the canvas
|
||||
HTTP handler/controller. Existing E2E fixture expectations for one task must
|
||||
change to a multi-task workspace fixture.
|
||||
|
||||
## ASCII UI preview
|
||||
|
||||
`UI-01: Task canvas host, new release (desktop)`. Entry: task canvas panel.
|
||||
The host header stays fixed; the application owns its existing scroll region.
|
||||
The badge reports data scope, while Promote controls placement. Labels are
|
||||
illustrative; the distinction is required by
|
||||
`AC-CANVASES-WORKSPACE-PREVIEW-001.3-.4`.
|
||||
|
||||
```text
|
||||
Task coordinator [Workspace data] [Releases and permissions] [Promote canvas]
|
||||
--------------------------------------------------------------------------
|
||||
Existing tasks [Refresh]
|
||||
Available 3 Active 2 Completed 1
|
||||
Task A Task B Task C
|
||||
```
|
||||
|
||||
`UI-02: Existing task-only canvas (desktop)`. Entry: the same task panel.
|
||||
The upgrade dialog uses the current permission-review layout and keeps
|
||||
Cancel and Enable actions visible. It does not promote the canvas.
|
||||
|
||||
```text
|
||||
Task coordinator [Task data] [Enable workspace data] [Promote canvas]
|
||||
|
|
||||
Enable workspace data for this canvas?
|
||||
Release: Task coordinator 1.0.0
|
||||
Reads: tasks in this workspace
|
||||
Writes/events/network: exact declared permissions
|
||||
[Cancel] [Enable workspace data]
|
||||
```
|
||||
|
||||
`UI-03: Existing task-only canvas (phone)`. Entry: focused task canvas route.
|
||||
The existing Actions drawer exposes the upgrade; the review opens as a
|
||||
full-height view with one scrolling permission region and safe-area actions.
|
||||
|
||||
```text
|
||||
< Task Task coordinator [Actions]
|
||||
Task data
|
||||
| Actions drawer: Enable workspace data
|
||||
v
|
||||
Enable workspace data
|
||||
Release and declared permissions [scrolls]
|
||||
-------------------------------------------
|
||||
[Cancel] [Enable workspace data] [fixed, safe area]
|
||||
```
|
||||
|
||||
## Tests
|
||||
|
||||
| Criteria | Evidence |
|
||||
| --- | --- |
|
||||
| `.1`, `.2`, `.8` | Plugin instance and web-app protocol tests for exact grants, all workspace pages, foreign denial, writes, workflows, messages, events, and dependencies. |
|
||||
| `.3`, `.4` | Canvas service promotion and projection tests. |
|
||||
| `.5`, `.6` | Conditional legacy-upgrade transaction and stale/owner/revocation tests. |
|
||||
| `.7` | Canvas host component tests and desktop/mobile E2E. |
|
||||
|
||||
## E2E tests
|
||||
|
||||
- `apps/web/e2e/tests/canvas/plugin-canvas.spec.ts` (`chromium`): owner-created
|
||||
task canvas sees two or more workspace tasks and refreshes before promotion;
|
||||
promotion leaves the list intact. Covers `.1`, `.3`, `.4`.
|
||||
- `apps/web/e2e/tests/canvas/mobile-plugin-canvas.spec.ts`
|
||||
(`mobile-chrome`): same data before promotion plus task-only legacy upgrade
|
||||
from the phone action drawer. Covers `.5`, `.7`.
|
||||
|
||||
## Work orders
|
||||
|
||||
- [x] [Task 01: Workspace data scope and legacy upgrade](task-01-workspace-data-scope.md)
|
||||
- [x] [Task 02: Host scope review and browser proof](task-02-host-scope-review.md)
|
||||
|
||||
Task 02 depends on Task 01. Both run in the primary session unless the user
|
||||
later explicitly authorizes another arrangement.
|
||||
|
||||
## Verification results
|
||||
|
||||
Passed: backend canvas/plugin tests, focused frontend Vitest coverage, web
|
||||
typecheck, i18n validation, desktop and mobile canvas Playwright suites, spec
|
||||
index validation, specification lint, and public documentation validation.
|
||||
|
||||
## Risks
|
||||
|
||||
- Grant checks currently equate instance scope with data scope. Missing a
|
||||
validation or event path could leak data or leave preview inconsistent.
|
||||
- Existing task releases must retain their one-task behavior until reviewed;
|
||||
a broad migration would silently change authority.
|
||||
- Same-origin canvas code can call ordinary user APIs already; the supported
|
||||
relative protocol must remain internally coherent in capability-only hosts.
|
||||
@@ -0,0 +1,112 @@
|
||||
---
|
||||
id: "01-workspace-data-scope"
|
||||
title: "Workspace data scope and legacy upgrade"
|
||||
status: complete
|
||||
wave: 1
|
||||
depends_on: []
|
||||
plan: "plan.md"
|
||||
requirements:
|
||||
- REQ-CANVASES-WORKSPACE-PREVIEW-001
|
||||
- REQ-CANVASES-LOCAL-CREATION-001
|
||||
- REQ-CANVASES-AGENT-WEB-APPS-003
|
||||
acceptance_criteria:
|
||||
- AC-CANVASES-WORKSPACE-PREVIEW-001.1
|
||||
- AC-CANVASES-WORKSPACE-PREVIEW-001.2
|
||||
- AC-CANVASES-WORKSPACE-PREVIEW-001.3
|
||||
- AC-CANVASES-WORKSPACE-PREVIEW-001.5
|
||||
- AC-CANVASES-WORKSPACE-PREVIEW-001.6
|
||||
- AC-CANVASES-WORKSPACE-PREVIEW-001.8
|
||||
- AC-CANVASES-LOCAL-CREATION-001.2
|
||||
- AC-CANVASES-AGENT-WEB-APPS-003.2
|
||||
system_design:
|
||||
- ../../specs/canvases/system-design/task-canvas-workspace-preview.md
|
||||
- ../../specs/canvases/system-design/local-creation-authority.md
|
||||
- ../../specs/canvases/system-design/agent-authored-web-apps.md
|
||||
- ../../specs/plugins/system-design/canvas-workspace-data-scope.md
|
||||
---
|
||||
|
||||
# Task 01: Workspace data scope and legacy upgrade
|
||||
|
||||
## Summary
|
||||
|
||||
Persist a separate data scope for canvas instances and honor it throughout the
|
||||
relative web-app protocol. New owner-authorized task canvases get exact
|
||||
declared workspace grants on first publication; existing task-only canvases
|
||||
can obtain them only through a conditional owner-reviewed upgrade.
|
||||
|
||||
## In scope
|
||||
|
||||
- SQLite/PostgreSQL instance mapping and null fallback; version-2 creation
|
||||
authority and first-publication transaction.
|
||||
- Runtime binding, grant checks, task/workflow/write/message/event/dependency
|
||||
enforcement, and additive context projection.
|
||||
- Bounded expvar counters for first publication, reviewed upgrades, and
|
||||
promotion data-scope results, without per-canvas metric labels.
|
||||
- Workspace-data preview and confirmation endpoints for retained task canvases.
|
||||
- Promotion behavior with an already workspace-data task canvas and tests for
|
||||
foreign workspaces, stale reviews, owner drift, and revoked grants.
|
||||
|
||||
## Out of scope
|
||||
|
||||
- Host action, dialog, translations, browser tests, and public docs.
|
||||
|
||||
## Acceptance
|
||||
|
||||
1. A new task-placed local canvas can list and operate on all authorized tasks
|
||||
in its own workspace through declared capabilities before promotion; no
|
||||
foreign workspace or undeclared capability is admitted.
|
||||
2. Existing task-only instances keep their current behavior until an owner
|
||||
confirms an exact, current release review; confirmation changes grants and
|
||||
data scope atomically without changing placement or release.
|
||||
3. Promotion preserves workspace data access when it already exists, while
|
||||
stale or invalid runtime bindings and reviews fail closed.
|
||||
|
||||
## Verification
|
||||
|
||||
Run from the repository root:
|
||||
|
||||
```bash
|
||||
(cd apps/backend && go test ./internal/canvas ./internal/plugins/instances ./internal/plugins ./internal/plugins/webapp ./internal/backendapp)
|
||||
python3 scripts/list-docs.py validate
|
||||
```
|
||||
|
||||
## Files likely touched
|
||||
|
||||
- `apps/backend/internal/plugins/instances/store.go`
|
||||
- `apps/backend/internal/plugins/webapp/tokens.go`
|
||||
- `apps/backend/internal/plugins/webapp_protocol.go`
|
||||
- `apps/backend/internal/plugins/webapp_protocol_data.go`
|
||||
- `apps/backend/internal/plugins/webapp_events.go`
|
||||
- `apps/backend/internal/plugins/webapp_protocol_json.go`
|
||||
- `apps/backend/internal/canvas/authoring.go`
|
||||
- `apps/backend/internal/canvas/service.go`
|
||||
- `apps/backend/internal/canvas/types.go`
|
||||
- `apps/backend/internal/backendapp/` canvas HTTP handlers and tests
|
||||
- Adjacent `*_test.go` files
|
||||
|
||||
## Dependencies
|
||||
|
||||
None.
|
||||
|
||||
## Risks
|
||||
|
||||
Every route that uses placement scope today must be classified by whether it
|
||||
filters data, determines discovery, or checks grant validity. Missing a route
|
||||
could make the preview inconsistent or broaden an unintended path.
|
||||
|
||||
## Parallelism
|
||||
|
||||
`sequential`
|
||||
|
||||
## Inputs
|
||||
|
||||
- [Workspace preview requirements](../../specs/canvases/requirements/task-canvas-workspace-preview.md)
|
||||
- [Workspace preview design](../../specs/canvases/system-design/task-canvas-workspace-preview.md)
|
||||
- [Scope decision](../../decisions/2026-09-23-task-canvas-workspace-data.md)
|
||||
|
||||
## Results
|
||||
|
||||
Passed: `go test ./internal/canvas ./internal/plugins/instances
|
||||
./internal/plugins ./internal/plugins/webapp ./internal/backendapp` and
|
||||
`python3 scripts/list-docs.py validate`. The canvas tests verify fixed-label
|
||||
counter increments for initial publication, reviewed upgrade, and promotion.
|
||||
@@ -0,0 +1,141 @@
|
||||
---
|
||||
id: "02-host-scope-review"
|
||||
title: "Host scope review and browser proof"
|
||||
status: complete
|
||||
wave: 2
|
||||
depends_on:
|
||||
- "01-workspace-data-scope"
|
||||
plan: "plan.md"
|
||||
requirements:
|
||||
- REQ-CANVASES-WORKSPACE-PREVIEW-001
|
||||
- REQ-CANVASES-AGENT-WEB-APPS-003
|
||||
acceptance_criteria:
|
||||
- AC-CANVASES-WORKSPACE-PREVIEW-001.1
|
||||
- AC-CANVASES-WORKSPACE-PREVIEW-001.4
|
||||
- AC-CANVASES-WORKSPACE-PREVIEW-001.5
|
||||
- AC-CANVASES-WORKSPACE-PREVIEW-001.7
|
||||
- AC-CANVASES-AGENT-WEB-APPS-003.1
|
||||
system_design:
|
||||
- ../../specs/canvases/system-design/task-canvas-workspace-preview.md
|
||||
- ../../specs/canvases/system-design/agent-authored-web-apps.md
|
||||
---
|
||||
|
||||
# Task 02: Host scope review and browser proof
|
||||
|
||||
## Summary
|
||||
|
||||
Show task placement and workspace data access separately in the host and
|
||||
promotion review. Give older task-only canvases an owner-reviewed access
|
||||
action on desktop and phone, update author guidance, and prove live workspace
|
||||
task refresh before promotion in browser tests.
|
||||
|
||||
## In scope
|
||||
|
||||
- Canvas API client/projections, existing host actions and review component,
|
||||
localized copy in six catalogs, and phone action drawer.
|
||||
- Versioned bundled authoring reference, public canvas and plugin API docs,
|
||||
and concise scoped `AGENTS.md` updates if implementation changes their
|
||||
current statements.
|
||||
- Component and desktop/mobile Playwright tests using multiple tasks in one
|
||||
workspace and a foreign-workspace negative case.
|
||||
|
||||
## Out of scope
|
||||
|
||||
- New canvas-authored UI template, broad UI redesign, installation-wide task
|
||||
listing, and silent legacy grant migration.
|
||||
|
||||
## Acceptance
|
||||
|
||||
1. Desktop and phone hosts label the data scope accurately and offer the
|
||||
upgrade review only for eligible task-only canvases; the action does not
|
||||
promote or republish.
|
||||
2. Promotion review distinguishes placement from data access and keeps exact
|
||||
declared permission details visible on both viewports.
|
||||
3. Browser tests show a new task canvas refreshing at least two workspace
|
||||
tasks before promotion and an existing one expanding access after review.
|
||||
|
||||
## ASCII UI preview
|
||||
|
||||
`UI-01: Task canvas host, new release (desktop)` and
|
||||
`UI-02: Existing task-only canvas (desktop)` use the same header shown in
|
||||
[the full plan](plan.md#ascii-ui-preview):
|
||||
|
||||
```text
|
||||
New: Task coordinator [Workspace data] [Releases] [Promote canvas]
|
||||
Existing: Task coordinator [Task data] [Enable workspace data] [Promote canvas]
|
||||
```
|
||||
|
||||
`UI-03: Existing task-only canvas (phone)` uses the existing focused route
|
||||
and Actions drawer. Its review is full-height with one scroll region and
|
||||
fixed safe-area actions:
|
||||
|
||||
```text
|
||||
< Task Task coordinator [Actions]
|
||||
Task data
|
||||
Actions > Enable workspace data
|
||||
Review declared permissions [scrolls]
|
||||
[Cancel] [Enable workspace data] [fixed, safe area]
|
||||
```
|
||||
|
||||
The scope label and action availability are required by
|
||||
`AC-CANVASES-WORKSPACE-PREVIEW-001.4-.5` and `.7`; text spacing is
|
||||
illustrative. Reuse the shipped canvas host and phone drawer.
|
||||
|
||||
## Verification
|
||||
|
||||
Run from the repository root:
|
||||
|
||||
```bash
|
||||
(cd apps/web && pnpm exec vitest run components/settings/canvas-lifecycle-dialogs.test.tsx components/settings/canvas-host-components.test.tsx lib/api/domains/canvas-api.test.ts)
|
||||
(cd apps/web && pnpm run typecheck)
|
||||
(cd apps/web && pnpm run i18n:check)
|
||||
(cd apps/web && pnpm e2e:run --host --project chromium tests/canvas/plugin-canvas.spec.ts)
|
||||
(cd apps/web && pnpm e2e:run --host --project mobile-chrome tests/canvas/mobile-plugin-canvas.spec.ts)
|
||||
python3 scripts/list-docs.py validate
|
||||
python3 scripts/lint-spec-files.py --all
|
||||
node scripts/validate-public-docs.mjs
|
||||
```
|
||||
|
||||
## Files likely touched
|
||||
|
||||
- `apps/web/lib/api/domains/canvas-api.ts`
|
||||
- `apps/web/components/settings/canvas-host-actions.tsx`
|
||||
- `apps/web/components/settings/canvas-lifecycle-dialogs.tsx`
|
||||
- `apps/web/components/settings/canvas-host-route*.tsx`
|
||||
- `apps/web/src/locales/*/canvases.json`
|
||||
- `apps/web/e2e/tests/canvas/plugin-canvas.spec.ts`
|
||||
- `apps/web/e2e/tests/canvas/mobile-plugin-canvas.spec.ts`
|
||||
- `apps/backend/internal/mcp/canvasskill/files/references/browser-api.md`
|
||||
- `apps/backend/config/prompts/create-canvas.md`
|
||||
- `docs/public/canvases.md`
|
||||
- `docs/public/plugins-authoring.md`
|
||||
- Adjacent component tests and `AGENTS.md` files when needed
|
||||
|
||||
## Dependencies
|
||||
|
||||
Task 01 supplies the data-scope projection and conditional access endpoint.
|
||||
|
||||
## Risks
|
||||
|
||||
The current canvas fixture expects one task. The browser proof must create a
|
||||
second task in the same workspace and retain a foreign-workspace negative case
|
||||
without changing unrelated fixture behavior.
|
||||
|
||||
## Parallelism
|
||||
|
||||
`sequential`
|
||||
|
||||
## Inputs
|
||||
|
||||
- [Workspace preview requirements](../../specs/canvases/requirements/task-canvas-workspace-preview.md)
|
||||
- [Workspace preview design](../../specs/canvases/system-design/task-canvas-workspace-preview.md)
|
||||
- [Full UI preview](plan.md#ascii-ui-preview)
|
||||
|
||||
## Results
|
||||
|
||||
Passed: focused Vitest suite (41 tests), web typecheck, i18n checks, desktop
|
||||
canvas Playwright suite, mobile canvas Playwright suite (5 tests), spec index
|
||||
validation, specification lint, and public documentation validation. The phone
|
||||
browser test verifies both scope labels and the legacy review flow; it uses a
|
||||
test-only legacy API response, while backend service/store tests verify the
|
||||
transactional grant upgrade.
|
||||
+20
-5
@@ -53,7 +53,18 @@ Kandev validates the package before it stores or runs the release. An invalid dr
|
||||
|
||||
## Use a canvas
|
||||
|
||||
A task canvas belongs to one task. A workspace canvas appears in workspace navigation and uses workspace scope. Promotion changes the same canvas from task scope to workspace scope. It does not copy the canvas.
|
||||
A task canvas stays in its creating task until promotion. After the first valid
|
||||
release, a new owner-authorized task canvas can use its declared supported
|
||||
permissions across the current workspace. This lets the app preview the full
|
||||
workspace task list before it appears in workspace navigation. Imported and
|
||||
older task canvases keep their existing data scope until an authorized review
|
||||
widens it.
|
||||
|
||||
A workspace canvas appears in workspace navigation. Promotion changes the
|
||||
canvas placement and keeps its identity, active release, state, and release
|
||||
history. For a new canvas that already has workspace data access, promotion
|
||||
changes placement only. The host review identifies whether it changes data
|
||||
access for a legacy canvas.
|
||||
|
||||
The app uses relative requests such as `./_kandev/v1/data/tasks` and `./_kandev/v1/state`. Kandev remains the source of truth for task, workflow, and message data. Canvas state stores app-specific shared state. It does not replace Kandev domain data.
|
||||
|
||||
@@ -115,7 +126,7 @@ and **Releases and permissions** outside the failed frame. Retry creates a new
|
||||
runtime binding and startup attempt. This check confirms document and context
|
||||
startup; it does not certify application business health.
|
||||
|
||||
Kandev calculates effective access from the package declaration, instance grant, trusted task or workspace scope, and current caller authorization. A release receives only the intersection of those permissions. See [Security and trust](security.md#isolated-web-applications) for the security boundary.
|
||||
Kandev calculates effective access from the package declaration, instance grant, trusted data scope, and current caller authorization. A release receives only the intersection of those permissions. See [Security and trust](security.md#isolated-web-applications) for the security boundary.
|
||||
|
||||
### Return to a task after publication
|
||||
|
||||
@@ -136,13 +147,17 @@ Only a user can promote a task canvas. An agent cannot promote, demote, grant pe
|
||||
1. Open the task canvas and choose its promotion action.
|
||||
2. Read the review dialog before you continue.
|
||||
3. Review every Kandev data read and write, event subscription, shared-state permission, and exact external HTTPS origin.
|
||||
4. Confirm the task-to-workspace scope change and workspace placement.
|
||||
4. Confirm the placement change to workspace navigation.
|
||||
|
||||
The confirmation includes the active release ID, permission declaration
|
||||
digest, and grant generation that you reviewed. If any of these changes before
|
||||
confirmation, Kandev rejects the request as stale and requires a new review.
|
||||
|
||||
The promotion keeps the canvas identity, active release, state, and release history. A workspace canvas then appears in workspace navigation. Canceling the review leaves the task canvas unchanged.
|
||||
The promotion keeps the canvas identity, active release, state, and release
|
||||
history. A workspace canvas then appears in workspace navigation. A new
|
||||
owner-authorized task canvas already has workspace data access, so promotion
|
||||
changes placement only. A legacy task canvas uses the permission review shown
|
||||
by its host. Canceling the review leaves the task canvas unchanged.
|
||||
|
||||
If promotion adds a permission, Kandev keeps the current active release until a user approves the new grant. The new release stays pending permission until that review finishes.
|
||||
|
||||
@@ -193,7 +208,7 @@ Use these recovery actions:
|
||||
- Roll back to the retained prior release after a failed publish.
|
||||
- Restore the database and matching artifact directory after a storage loss. See [Canvas artifacts and recovery](operations.md#canvas-artifacts-and-recovery).
|
||||
- Archive a canvas to hide it from normal discovery. Restore it from the canvas controls.
|
||||
- Remove a task canvas to remove its task-scoped data. Removing a task does not remove a canvas already promoted to a workspace.
|
||||
- Remove a task canvas to remove the canvas and its data. Removing a task does not remove a canvas already promoted to a workspace.
|
||||
- Remove a workspace canvas to remove its grants, state, tokens, releases, and artifacts after cleanup completes.
|
||||
|
||||
Kandev records artifact cleanup before it removes release ownership. A worker completes cleanup after the database transaction and retries it after a restart.
|
||||
|
||||
@@ -121,11 +121,12 @@ does not need a Go backend or an injected Kandev JavaScript API.
|
||||
the app needs.
|
||||
5. Package the manifest and static files as a gzip-compressed tar archive.
|
||||
|
||||
For a new owner-created task canvas, the first valid release can receive the
|
||||
declared supported task-scoped permissions through its initial permission
|
||||
policy. Imported packages and later permission increases need human approval.
|
||||
Keep `network_origins` as exact HTTPS origins. Do not use wildcards, paths,
|
||||
credentials, query strings, or fragments.
|
||||
For a new owner-authorized task canvas, the first valid release can receive
|
||||
only its declared supported permissions through the initial permission policy.
|
||||
Kandev data access is limited to the current workspace while the canvas stays
|
||||
placed in its creating task. Imported packages and later permission increases
|
||||
need human approval. Keep `network_origins` as exact HTTPS origins. Do not use
|
||||
wildcards, paths, credentials, query strings, or fragments.
|
||||
|
||||
For example, a page can read task data with the browser Fetch API:
|
||||
|
||||
@@ -137,9 +138,12 @@ if (!response.ok) {
|
||||
const tasks = await response.json();
|
||||
```
|
||||
|
||||
Use `./_kandev/v1/events` for the event stream. Keep all protocol paths
|
||||
relative so the same package works in task and workspace scope. Do not copy a
|
||||
capability URL from the host into the app.
|
||||
Use `./_kandev/v1/events` for the event stream. Read both `scope_kind` and
|
||||
`data_scope_kind` from `./_kandev/v1/context`: the first describes placement,
|
||||
and the second describes the Kandev data boundary. Keep all protocol paths
|
||||
relative so the same package works in task and workspace placement. For task
|
||||
lists, follow `page_info.next_cursor` to load every page. Do not set
|
||||
`workspace_id` to another workspace or copy a capability URL from the host.
|
||||
|
||||
For recorded workflow movement, the browser can GET
|
||||
`./_kandev/v1/data/tasks/{task_id}/step-transitions` with
|
||||
|
||||
@@ -10,8 +10,8 @@ last_updated: 2026-09-10
|
||||
# Canvases
|
||||
|
||||
Canvases own agent-authored task applications and their promotion to workspace
|
||||
applications. The system owns canvas scope, source lineage, release selection,
|
||||
editing sessions, discovery, and portable canvas distribution.
|
||||
applications. The system owns canvas placement and data scope, source lineage,
|
||||
release selection, editing sessions, discovery, and portable canvas distribution.
|
||||
|
||||
The Plugins system owns the web-application runtime, permissions,
|
||||
Kandev data access, state, events, and package validation. The task system
|
||||
@@ -20,18 +20,21 @@ remains authoritative for task data and permissions.
|
||||
## Requirements
|
||||
|
||||
- [Agent-authored web-app canvases](requirements/agent-authored-web-apps.md)
|
||||
- [Task canvas workspace data preview](requirements/task-canvas-workspace-preview.md)
|
||||
- [Canvas marketplace and sharing](requirements/marketplace-sharing.md)
|
||||
- [Deprecated collaborative canvases](requirements/collaborative-canvases.md)
|
||||
|
||||
## System design
|
||||
|
||||
- [Agent-authored web-app canvases](system-design/agent-authored-web-apps.md)
|
||||
- [Task canvas workspace data preview](system-design/task-canvas-workspace-preview.md)
|
||||
- [Canvas marketplace and sharing](system-design/marketplace-sharing.md)
|
||||
- [Superseded collaborative canvases](system-design/collaborative-canvases.md)
|
||||
|
||||
## Related context
|
||||
|
||||
- [Runtime and permission fix plan](../../plans/canvas-runtime-permission-fixes/plan.md)
|
||||
- [Task canvas workspace data preview plan](../../plans/task-canvas-workspace-preview/plan.md)
|
||||
- [Agent MCP discovery guidance](../agents/system-design/mcp-tool-discovery-guidance.md)
|
||||
- [MCP discovery and canvas prompt plan](../../plans/mcp-discovery-canvas-prompts/plan.md)
|
||||
- [GitHub Copilot App Canvas reference](../../copilot-canvas-reference.md)
|
||||
|
||||
@@ -6,7 +6,7 @@ system: canvases
|
||||
owners:
|
||||
- canvases
|
||||
created: 2026-08-26
|
||||
last_updated: 2026-09-21
|
||||
last_updated: 2026-09-23
|
||||
---
|
||||
|
||||
# Agent-authored web-app canvases Requirements
|
||||
@@ -15,7 +15,8 @@ last_updated: 2026-09-21
|
||||
|
||||
A canvas is a custom web application that an agent creates for one task. A
|
||||
user can promote a useful task canvas to its workspace. A workspace canvas
|
||||
appears in workspace navigation and can use workspace-scoped data.
|
||||
appears in workspace navigation. An owner-authorized task canvas can already
|
||||
use its workspace's data while the user reviews it in the originating task.
|
||||
|
||||
The Canvases system owns the canvas scope, source lineage, release selection,
|
||||
promotion, editing flow, and discovery. The Plugins system owns the web-application
|
||||
@@ -24,13 +25,13 @@ runtime and its data contract.
|
||||
## Terminology
|
||||
|
||||
- **Task canvas:** A canvas that belongs to one task and appears only in that
|
||||
task.
|
||||
task. Its placement does not determine its approved data scope.
|
||||
- **Workspace canvas:** A canvas that belongs to one workspace and appears in
|
||||
workspace navigation. Agent-authored canvases reach this scope by promotion;
|
||||
[distribution](marketplace-sharing.md) also defines reviewed package installs.
|
||||
- **Draft:** Editable canvas source in an authorized agent workspace.
|
||||
- **Release:** An immutable package that passed validation.
|
||||
- **Promotion:** A user action that changes a task canvas to workspace scope.
|
||||
- **Promotion:** A user action that changes a task canvas to workspace placement.
|
||||
|
||||
## Requirements
|
||||
|
||||
@@ -120,8 +121,8 @@ browser session end.
|
||||
|
||||
### REQ-CANVASES-AGENT-WEB-APPS-003: User-controlled promotion
|
||||
|
||||
**Intent:** A useful task canvas becomes a workspace application only after a
|
||||
user reviews its scope and permissions.
|
||||
**Intent:** A useful task canvas becomes available in workspace navigation only
|
||||
after a user reviews its placement and permissions.
|
||||
|
||||
**User story:** As a user, I want to promote a useful task canvas, so that I
|
||||
can open it from the workspace sidebar.
|
||||
@@ -132,7 +133,8 @@ can open it from the workspace sidebar.
|
||||
system shall show the requested data, write, event, state, and network
|
||||
permissions before confirmation.
|
||||
- **AC-CANVASES-AGENT-WEB-APPS-003.2:** When the user confirms promotion, the
|
||||
same canvas identity and active release shall change to workspace scope.
|
||||
same canvas identity and active release shall change to workspace placement.
|
||||
A release that already has workspace data access shall keep that access.
|
||||
- **AC-CANVASES-AGENT-WEB-APPS-003.3:** When promotion completes, the canvas
|
||||
shall appear in navigation for that workspace only.
|
||||
- **AC-CANVASES-AGENT-WEB-APPS-003.4:** An agent shall not promote, demote, or
|
||||
@@ -342,6 +344,7 @@ including missing references, lookup failures, and passthrough exclusions.
|
||||
|
||||
- [Canvas runtime and task-entry recovery](../../../plans/canvas-runtime-entry-recovery/plan.md)
|
||||
- [Direct canvas creation and saved prompt](../../../plans/canvas-direct-creation/plan.md)
|
||||
- [Task canvas workspace data preview](../../../plans/task-canvas-workspace-preview/plan.md)
|
||||
|
||||
## Out of scope
|
||||
|
||||
|
||||
@@ -6,7 +6,7 @@ system: canvases
|
||||
owners:
|
||||
- canvases
|
||||
created: 2026-09-10
|
||||
last_updated: 2026-09-10
|
||||
last_updated: 2026-09-23
|
||||
---
|
||||
|
||||
# Owner-authorized canvas creation
|
||||
@@ -39,10 +39,11 @@ imported code and later changes cannot claim that creation authority.
|
||||
- **AC-CANVASES-LOCAL-CREATION-001.1:** The first valid release of an
|
||||
owner-authorized task canvas shall activate without a separate permission
|
||||
approval. Its grants shall contain only its declared, supported permissions.
|
||||
- **AC-CANVASES-LOCAL-CREATION-001.2:** Initial grants shall remain within the
|
||||
task scope and current owner access. They can cover supported data reads,
|
||||
writes, events, instance state, and exact HTTPS external origins. They shall
|
||||
not enable remote scripts, managed backend execution, or workspace access.
|
||||
- **AC-CANVASES-LOCAL-CREATION-001.2:** Initial grants shall contain only the
|
||||
declared supported data reads, writes, events, instance state, and exact HTTPS
|
||||
external origins. For a new owner-authorized canvas, those grants shall cover
|
||||
the current workspace while the canvas remains in its task. They shall not
|
||||
enable another workspace, remote scripts, or managed backend execution.
|
||||
- **AC-CANVASES-LOCAL-CREATION-001.3:** Agent fields, package metadata, display
|
||||
titles, and ownership of an imported package shall not establish local
|
||||
creation authority. Missing or mismatched trusted identity shall deny it.
|
||||
@@ -71,3 +72,4 @@ a marketplace, import UI, collaborator role, or ongoing blanket approval.
|
||||
## Implementation plans
|
||||
|
||||
- [Canvas runtime and permission fixes](../../../plans/canvas-runtime-permission-fixes/plan.md)
|
||||
- [Task canvas workspace data preview](../../../plans/task-canvas-workspace-preview/plan.md)
|
||||
|
||||
@@ -0,0 +1,88 @@
|
||||
---
|
||||
id: canvases-task-canvas-workspace-preview
|
||||
title: Task canvas workspace data preview
|
||||
status: draft
|
||||
system: canvases
|
||||
owners:
|
||||
- canvases
|
||||
created: 2026-09-23
|
||||
last_updated: 2026-09-23
|
||||
---
|
||||
|
||||
# Task canvas workspace data preview Requirements
|
||||
|
||||
## Overview
|
||||
|
||||
A user creates a canvas from a task and reviews the live application there
|
||||
before deciding whether to add it to workspace navigation. Its task placement
|
||||
must not reduce the data available to an owner-authorized first release.
|
||||
Canvases owns the creation and promotion lifecycle; the Plugins system owns the
|
||||
runtime data contract and grant enforcement.
|
||||
|
||||
## Terminology
|
||||
|
||||
- **Placement scope:** Where Kandev presents a canvas and which task owns its
|
||||
unpromoted lifecycle.
|
||||
- **Data scope:** The largest Kandev data boundary admitted by a release's
|
||||
declared and granted capabilities. Data scope never overrides the viewing
|
||||
user's current authorization.
|
||||
|
||||
## Requirements
|
||||
|
||||
### REQ-CANVASES-WORKSPACE-PREVIEW-001: Representative task canvas preview
|
||||
|
||||
**Intent:** A locally requested canvas works with the current workspace's live
|
||||
data before the user chooses to promote it.
|
||||
|
||||
**User story:** As a user creating a canvas from a task, I want to see all tasks
|
||||
in my current workspace, so that I can judge the canvas before promotion.
|
||||
|
||||
#### Acceptance criteria
|
||||
|
||||
- **AC-CANVASES-WORKSPACE-PREVIEW-001.1:** After the first valid release of an
|
||||
owner-authorized task canvas activates, its declared task read capability
|
||||
shall list and read all currently authorized tasks in the canvas's workspace,
|
||||
including tasks added after publication. Refresh and pagination shall reach
|
||||
the full result set. A task in another workspace shall remain unavailable.
|
||||
- **AC-CANVASES-WORKSPACE-PREVIEW-001.2:** Before promotion, every supported
|
||||
capability declared by that first release shall operate across the same
|
||||
workspace where the capability has a workspace data meaning. Undeclared or
|
||||
unsupported capabilities shall remain unavailable, and every operation shall
|
||||
obey current user authorization.
|
||||
- **AC-CANVASES-WORKSPACE-PREVIEW-001.3:** The canvas shall remain discoverable
|
||||
only in its originating task until a user promotes it. Task removal shall
|
||||
retain its existing cleanup behavior. Promotion shall still require user
|
||||
confirmation, but it shall not be required to preview workspace data.
|
||||
- **AC-CANVASES-WORKSPACE-PREVIEW-001.4:** The canvas context and host review
|
||||
shall distinguish task placement from workspace data access. Promotion review
|
||||
shall identify whether it changes data access or only placement.
|
||||
- **AC-CANVASES-WORKSPACE-PREVIEW-001.5:** An existing task canvas with
|
||||
task-only data access shall keep that access after upgrade until a current
|
||||
workspace owner explicitly enables workspace data access. The review shall
|
||||
name the active release and its declared permissions. Confirmation shall
|
||||
widen only those declared grants without promoting or republishing the
|
||||
canvas; cancellation shall change nothing.
|
||||
- **AC-CANVASES-WORKSPACE-PREVIEW-001.6:** A stale review, changed owner,
|
||||
revoked grant, missing task or workspace, or failed permission check shall
|
||||
deny the access change without widening data exposure. A new release that
|
||||
adds a capability after first publication shall still await permission
|
||||
review.
|
||||
- **AC-CANVASES-WORKSPACE-PREVIEW-001.7:** Desktop and phone users shall be
|
||||
able to inspect the data scope and complete the existing-canvas access review
|
||||
from the task canvas host. The phone flow shall remain usable with one
|
||||
vertical scroll region, safe-area clearance, and touch controls.
|
||||
- **AC-CANVASES-WORKSPACE-PREVIEW-001.8:** A canvas built under this contract
|
||||
shall receive only workspace data authorized for its own workspace. Its
|
||||
runtime token, manifest, or agent input shall not select a different
|
||||
workspace or expand its capabilities.
|
||||
|
||||
## Out of scope
|
||||
|
||||
- Data from other workspaces or installation-wide grants.
|
||||
- Blanket grants for capabilities a release does not declare.
|
||||
- New canvas plugin capability types or arbitrary backend execution.
|
||||
- Automatic widening of existing published releases.
|
||||
|
||||
## Implementation plans
|
||||
|
||||
- [Task canvas workspace data preview](../../../plans/task-canvas-workspace-preview/plan.md)
|
||||
@@ -6,7 +6,7 @@ system: canvases
|
||||
owners:
|
||||
- canvases
|
||||
created: 2026-08-26
|
||||
last_updated: 2026-09-21
|
||||
last_updated: 2026-09-23
|
||||
requirements:
|
||||
- REQ-CANVASES-AGENT-WEB-APPS-001
|
||||
- REQ-CANVASES-AGENT-WEB-APPS-002
|
||||
@@ -110,9 +110,11 @@ Use a small lifecycle record instead of declarative canvas blocks.
|
||||
- nullable `archived_at`
|
||||
- `created_at` and `updated_at`
|
||||
|
||||
The plugin instance owns `scope_kind`, active release, status, and grants. The
|
||||
canvas service is the only service that changes the task or workspace scope of
|
||||
a canvas instance.
|
||||
The plugin instance owns placement `scope_kind`, effective data scope, active
|
||||
release, status, and grants. The canvas service is the only service that
|
||||
changes task or workspace placement or authorizes a canvas data-scope change.
|
||||
The [workspace preview design](task-canvas-workspace-preview.md) separates
|
||||
these scopes for locally requested task canvases.
|
||||
|
||||
The canvas and plugin instance have a one-to-one relationship. Canvas removal
|
||||
removes the plugin instance, runtime tokens, grants, state, pending releases,
|
||||
@@ -366,13 +368,14 @@ The promotion dialog shows:
|
||||
- each event subject
|
||||
- shared state access
|
||||
- each exact external network origin
|
||||
- the change from task scope to workspace scope
|
||||
- the change from task placement to workspace placement, with any data-scope
|
||||
difference identified separately
|
||||
- the new workspace navigation placement
|
||||
|
||||
The user can cancel without a state change. Confirmation creates the approved
|
||||
workspace grants and changes the plugin instance scope in one transaction. The
|
||||
canvas keeps its ID, plugin instance, active release, state, and release
|
||||
history.
|
||||
The user can cancel without a state change. Confirmation creates any needed
|
||||
workspace grants and changes the plugin instance placement scope in one
|
||||
transaction. The canvas keeps its ID, plugin instance, active release, state,
|
||||
and release history.
|
||||
|
||||
Promotion publishes one lifecycle event after commit. The task and workspace
|
||||
navigation projections then refresh.
|
||||
@@ -641,8 +644,10 @@ connection. An edit Quick Chat session also verifies its trusted target canvas
|
||||
metadata.
|
||||
|
||||
Task canvases cannot appear in another task. Workspace canvases can serve task
|
||||
surfaces only inside their workspace. Promotion does not grant access to tasks,
|
||||
repositories, sessions, or external services by itself.
|
||||
surfaces only inside their workspace. A task canvas can use approved workspace
|
||||
data before promotion under the [workspace preview contract](task-canvas-workspace-preview.md).
|
||||
Promotion does not grant undeclared access to tasks, repositories, sessions,
|
||||
or external services.
|
||||
|
||||
The plugin runtime repeats resource authorization for each request. Canvas
|
||||
authorization does not replace task or workspace authorization.
|
||||
|
||||
@@ -152,7 +152,8 @@ The definition in `config/prompts/create-canvas.md` contains this guidance:
|
||||
> Call `publish_canvas_kandev` and address any validation errors.
|
||||
> Report the canvas identity and whether its release is active, awaits permission review, or was unsuccessful.
|
||||
> If publication is unsuccessful, report the failure and do not claim that the canvas is published.
|
||||
> If workspace access requires promotion, explain the user action that is still required.
|
||||
> A new owner-authorized task canvas can use its declared supported permissions across the current workspace before promotion.
|
||||
> Promotion adds workspace navigation. Do not claim that promotion is required to preview workspace task data.
|
||||
> A local build alone does not publish a canvas inside Kandev.
|
||||
> If the tools remain unavailable, report the limitation instead of claiming that workspace files are a Kandev canvas.
|
||||
|
||||
|
||||
@@ -6,7 +6,7 @@ system: canvases
|
||||
owners:
|
||||
- canvases
|
||||
created: 2026-09-10
|
||||
last_updated: 2026-09-10
|
||||
last_updated: 2026-09-23
|
||||
requirements:
|
||||
- REQ-CANVASES-LOCAL-CREATION-001
|
||||
---
|
||||
@@ -20,7 +20,8 @@ owns grant storage, release activation, and runtime enforcement. This design
|
||||
implements `REQ-CANVASES-LOCAL-CREATION-001`; the authority, transaction, and
|
||||
compatibility sections map to criteria .1-.3, .4-.5, and .6-.7 respectively.
|
||||
|
||||
See [the creation authority decision](../../../decisions/2026-09-10-canvas-creation-authority.md)
|
||||
See [the creation authority decision](../../../decisions/2026-09-10-canvas-creation-authority.md),
|
||||
[its workspace-data amendment](../../../decisions/2026-09-23-task-canvas-workspace-data.md),
|
||||
and [plugin grants](../../plugins/system-design/isolated-web-app-contributions.md#instance-grants).
|
||||
|
||||
## Trusted creation authority
|
||||
@@ -40,7 +41,7 @@ Add a canvas-owned `canvas_creation_authority` table through
|
||||
| `canvas_id` | Primary key, references the canvas lifecycle identity |
|
||||
| `owner_user_id` | Trusted workspace owner at creation |
|
||||
| `creating_session_id` | Trusted source session |
|
||||
| `policy_version` | Integer 1 for the initial-publication policy |
|
||||
| `policy_version` | Integer 1 for historical task-data grants; version 2 for new workspace-data grants |
|
||||
| `consumed_at` | Empty until the first release transaction consumes it |
|
||||
|
||||
Create the row in the canvas/instance creation transaction. No agent-facing
|
||||
@@ -52,7 +53,9 @@ Existing databases acquire the empty table; do not backfill authority.
|
||||
At publication require every predicate: a nonzero captured `PublishAuthority`,
|
||||
local-canvas instance source, task scope, matching task and workspace, matching
|
||||
creating session, unchanged current owner, pending instance, no active or
|
||||
persisted release, no previous grant changes, and unconsumed policy version 1.
|
||||
persisted release, no previous grant changes, and an unconsumed supported
|
||||
policy version. New authority uses version 2; historical version-1 authority
|
||||
keeps its task data ceiling and is never upgraded by publication alone.
|
||||
Check the full instance snapshot again inside the transaction. Re-read the
|
||||
current task/workspace ownership through the same transaction and serialize
|
||||
against ownership changes; the adapter's earlier lookup alone is insufficient.
|
||||
@@ -64,10 +67,12 @@ The trusted adapter supplies the freshly resolved owner; caller-controlled
|
||||
## Grant derivation and transaction
|
||||
|
||||
Derive grants from `ManifestPermissions` and the existing static web-app
|
||||
capability vocabulary. Restrict Kandev resource access to the recorded task,
|
||||
using normal runtime authorization. Normalize each declared external origin
|
||||
through `NormalizeNetworkOrigins`; initial external grants count as delegated
|
||||
owner approval, with that owner as `ApprovedBy`. This is deliberate: a locally
|
||||
capability vocabulary. Version-2 authority binds the approved data scope to
|
||||
the recorded workspace while the canvas remains task-placed. Historical
|
||||
version-1 authority retains task data scope. See the
|
||||
[workspace preview design](task-canvas-workspace-preview.md). Normalize each
|
||||
declared external origin through `NormalizeNetworkOrigins`; initial external
|
||||
grants count as delegated owner approval, with that owner as `ApprovedBy`. A locally
|
||||
requested app can contact its declared HTTPS service on its first run.
|
||||
Unsupported capabilities and backend/native contributions cannot gain access
|
||||
through this path. Do not add a generic manifest-controlled auto-approve flag.
|
||||
@@ -96,8 +101,9 @@ schema replay and backup enumeration must include this table.
|
||||
## API and compatibility
|
||||
|
||||
Return an additive `initial_permission_policy` field in the create response:
|
||||
version 1, eligibility, scope `task`, supported permission kinds, and the exact
|
||||
HTTPS-origin constraint. This is descriptive output, never a publish input.
|
||||
the policy version, eligibility, placement `task`, data scope, supported
|
||||
permission kinds, and exact HTTPS-origin constraint. This is descriptive
|
||||
output, never a publish input.
|
||||
It must not claim a permission ceiling that the backend does not enforce.
|
||||
Keep the existing `activated` and `permission_required` publish result fields.
|
||||
|
||||
|
||||
@@ -0,0 +1,168 @@
|
||||
---
|
||||
id: canvases-task-canvas-workspace-preview-design
|
||||
title: Task canvas workspace data preview design
|
||||
status: draft
|
||||
system: canvases
|
||||
owners:
|
||||
- canvases
|
||||
created: 2026-09-23
|
||||
last_updated: 2026-09-23
|
||||
requirements:
|
||||
- REQ-CANVASES-WORKSPACE-PREVIEW-001
|
||||
---
|
||||
|
||||
# Task canvas workspace data preview System Design
|
||||
|
||||
## Boundary and mapping
|
||||
|
||||
Canvases owns when a locally requested task canvas gains workspace data scope,
|
||||
how an older canvas can opt in, and when promotion changes placement. Plugins
|
||||
persists the instance's effective data scope and enforces it through the shared
|
||||
web-app runtime. Task services remain authoritative for data and current user
|
||||
access. This design implements `REQ-CANVASES-WORKSPACE-PREVIEW-001`.
|
||||
|
||||
| Criteria | Design sections |
|
||||
| --- | --- |
|
||||
| `AC-CANVASES-WORKSPACE-PREVIEW-001.1`, `.2`, `.8` | Data scope and runtime enforcement |
|
||||
| `AC-CANVASES-WORKSPACE-PREVIEW-001.3`, `.4` | Lifecycle and presentation |
|
||||
| `AC-CANVASES-WORKSPACE-PREVIEW-001.5`, `.6`, `.7` | Existing canvas upgrade and host flow |
|
||||
|
||||
See [the workspace preview decision](../../../decisions/2026-09-23-task-canvas-workspace-data.md)
|
||||
and [the existing creation authority](local-creation-authority.md).
|
||||
|
||||
## Data scope and persistence
|
||||
|
||||
Keep `plugin_instances.scope_kind` as the placement/lifecycle scope. Add a
|
||||
nullable `data_scope_kind` to `plugin_instances`; null means the existing
|
||||
`scope_kind` so older rows and non-canvas plugins retain their behavior. A
|
||||
non-null value is valid only when it equals the placement scope, or when a
|
||||
`local_canvas` task instance uses `workspace` data scope with its existing
|
||||
trusted `workspace_id` and `task_id`. Reject `instance` and foreign workspace
|
||||
data scope for canvases. Do not accept the field from agent, manifest, or
|
||||
browser input. Store it through SQLite and PostgreSQL schema paths, backup,
|
||||
snapshot, and instance row mapping.
|
||||
|
||||
At trusted canvas creation, record workspace data scope only for a new task
|
||||
canvas with owner-authorized creation provenance. The task remains the canvas
|
||||
owner and the plugin instance's placement scope. The first valid release
|
||||
derives grants from exactly its declared supported capabilities with a
|
||||
`workspace` ceiling, then consumes creation authority and activates in the
|
||||
existing transaction. Raise `CreationAuthorityPolicyVersion` for newly issued
|
||||
authority; consumed version-1 rows remain historical evidence and are never
|
||||
reissued. If provenance or current owner checks fail, publication follows the
|
||||
normal permission-review path and cannot infer a workspace grant.
|
||||
|
||||
All grant-fit, release activation, and runtime-binding validation for a web
|
||||
app use its effective data scope. A grant ceiling cannot be interpreted as
|
||||
covering a wider data scope merely because it covers the placement scope. A
|
||||
later declaration increase still creates a pending release. Revocation bumps
|
||||
the existing grant generation and invalidates runtime tokens.
|
||||
|
||||
## Runtime enforcement
|
||||
|
||||
`webapp.CapabilityBinding` carries both placement `ScopeKind` and effective
|
||||
`DataScopeKind`. Issue both from the persisted instance, and compare both with
|
||||
the current instance on every token validation. Existing bindings with an
|
||||
empty data scope resolve to placement scope. The relative
|
||||
`./_kandev/v1/context` response retains `scope_kind` for placement and adds
|
||||
`data_scope_kind` for authors to label the available data accurately.
|
||||
|
||||
Use the effective data scope for the web-app task list, single-task read,
|
||||
task update, message dispatch, workflow list and steps, task dependency edge
|
||||
projection, and subscribed task events. A workspace data scope binds all
|
||||
queries and mutations to the instance's trusted `workspace_id`, including
|
||||
explicit `workspace_id` filters. It does not derive workspace IDs from the
|
||||
request or allow `ScopeInstance`. The task-list route uses its existing
|
||||
pagination path instead of the bound-task shortcut. Each operation still
|
||||
checks the declared capability, effective grant, and current user/domain
|
||||
authorization. Other plugin instances continue to use their existing scope
|
||||
rules.
|
||||
|
||||
Never use the ordinary authenticated Kandev HTTP API as an implicit escape
|
||||
from the canvas protocol. The [same-origin trust decision](../../../decisions/2026-09-19-trusted-same-origin-canvases.md)
|
||||
acknowledges that browser code can call those APIs, but the documented canvas
|
||||
contract and capability-only runtime must remain coherent.
|
||||
|
||||
## Lifecycle and presentation
|
||||
|
||||
`canvas_lifecycle_metadata.task_id` and the instance's placement scope retain
|
||||
task discovery and deletion semantics. Workspace data scope does not add the
|
||||
canvas to workspace navigation. Promotion remains a reviewed human action:
|
||||
it changes placement to workspace, clears task placement, preserves the active
|
||||
release, and leaves workspace data scope intact. The review states that data
|
||||
access is already workspace-wide when that is true. A task-only legacy canvas
|
||||
still has its existing promotion behavior, including grant expansion.
|
||||
|
||||
Project `data_scope_kind` alongside `scope_kind` in the canvas and runtime
|
||||
responses. The task host exposes a compact data-scope label in its existing
|
||||
header/action surface. Releases and permissions and promotion review explain
|
||||
placement separately from data access. The bundled authoring guidance and
|
||||
public canvas documentation tell authors to read both context fields and to
|
||||
declare only capabilities they use. Revise the saved `create-canvas` prompt's
|
||||
promotion guidance so it describes workspace navigation rather than saying
|
||||
that workspace data always requires promotion. No generated package rewrite
|
||||
is needed.
|
||||
|
||||
## Existing canvas upgrade
|
||||
|
||||
Do not silently widen a retained release. An active task canvas with task-only
|
||||
data scope offers **Enable workspace data** in the existing host action menu.
|
||||
The backend returns a review snapshot of the active release, permission
|
||||
digest, grant generation, current/target data scope, and exact declared
|
||||
permissions. Only a currently authorized workspace owner may confirm it.
|
||||
|
||||
Confirmation rechecks the canvas's task and workspace identity, owner, active
|
||||
release, permission digest, and grant generation inside one transaction. It
|
||||
upserts workspace-ceiling grants only for that release's declared permissions,
|
||||
sets `data_scope_kind=workspace`, increments grant generation, and publishes a
|
||||
single lifecycle refresh after commit. It neither promotes the canvas nor
|
||||
republishes the artifact. On stale review or any failed check it changes
|
||||
nothing. A canceled review has no write. Imported or legacy packages receive
|
||||
no automatic exemption.
|
||||
|
||||
Use the existing canvas HTTP controller's preview/confirm pattern with
|
||||
`GET /api/v1/canvases/{id}/workspace-data-preview` and
|
||||
`POST /api/v1/canvases/{id}/workspace-data`. The request carries the same
|
||||
release ID, permission digest, and grant generation preconditions as promotion.
|
||||
Return an updated canvas projection after success. Keep the action unavailable
|
||||
for pending, archived, removed, already workspace-data, or foreign canvases.
|
||||
|
||||
## Desktop and phone host flow
|
||||
|
||||
Desktop keeps the current canvas panel and action toolbar. The data-scope
|
||||
label sits with existing host metadata, and a legacy canvas exposes the upgrade
|
||||
action from its current actions. Phone keeps the focused canvas route and
|
||||
secondary-action drawer; the same upgrade opens the existing full-height
|
||||
review surface. The header and actions remain fixed while one body region
|
||||
scrolls, with safe-area clearance and touch targets. Both presentations share
|
||||
one review state and backend snapshot; neither relies on canvas-authored UI.
|
||||
|
||||
## Failure and observability
|
||||
|
||||
Denied or stale access review returns the existing safe error style and leaves
|
||||
the active release and old scope usable. A missing task or workspace makes
|
||||
its runtime binding stale. Scope or grant changes invalidate old tokens; the
|
||||
host reloads the runtime through its existing recovery path. Record bounded
|
||||
scope-transition result counters and IDs already allowed for canvas lifecycle
|
||||
logging. Do not log package source, permission bodies, tokens, or task data.
|
||||
|
||||
## Verification strategy
|
||||
|
||||
- Instance-store tests cover null fallback, invalid combinations, transaction
|
||||
rollback, snapshot/backup mapping, and grant-generation invalidation.
|
||||
- Canvas service tests cover version-2 owner authority, exact declarations,
|
||||
legacy review, stale snapshots, owner drift, and promotion without data
|
||||
expansion.
|
||||
- Web-app protocol tests cover list pagination, task read/write, workflow,
|
||||
message, event, dependency projection, foreign-workspace denial, and old
|
||||
task-scoped behavior.
|
||||
- Desktop and mobile Playwright exercise an owner-created task canvas with at
|
||||
least two tasks, refresh before promotion, and an older canvas's explicit
|
||||
access upgrade. The mobile route and review remain touch-usable.
|
||||
|
||||
## Related designs
|
||||
|
||||
- [Canvas lifecycle and promotion](agent-authored-web-apps.md)
|
||||
- [Owner-authorized first publication](local-creation-authority.md)
|
||||
- [Plugin web-app runtime](../../plugins/system-design/isolated-web-app-contributions.md)
|
||||
- [Plugin canvas data-scope runtime](../../plugins/system-design/canvas-workspace-data-scope.md)
|
||||
@@ -0,0 +1,72 @@
|
||||
---
|
||||
id: plugins-canvas-workspace-data-scope-design
|
||||
title: Canvas placement and data scope in the web-app runtime
|
||||
status: draft
|
||||
system: plugins
|
||||
owners:
|
||||
- kandev
|
||||
created: 2026-09-23
|
||||
last_updated: 2026-09-23
|
||||
requirements: []
|
||||
---
|
||||
|
||||
# Canvas placement and data scope in the web-app runtime
|
||||
|
||||
## Boundary
|
||||
|
||||
This is the Plugins runtime implementation contract for the
|
||||
[Canvas workspace preview requirement](../../canvases/requirements/task-canvas-workspace-preview.md).
|
||||
Canvases decides when an owner-authorized local app may use workspace data.
|
||||
Plugins persists and enforces that decision; it does not infer authority from
|
||||
the manifest or browser request. The existing
|
||||
[isolated web-app design](isolated-web-app-contributions.md) remains the general
|
||||
runtime contract.
|
||||
|
||||
## Instance model and grants
|
||||
|
||||
Add nullable `plugin_instances.data_scope_kind`. A null value resolves to
|
||||
`scope_kind` for retained rows and non-canvas instances. A non-null workspace
|
||||
data scope is valid only for a `local_canvas` instance placed in a task or
|
||||
workspace with a trusted `workspace_id`. Reject any attempt to use an
|
||||
installation-wide data scope for a canvas. Creation, reviewed upgrade, and
|
||||
promotion update the field and grants through transactions owned by the
|
||||
canvas lifecycle service.
|
||||
|
||||
Grant fit, release activation, and runtime validation compare each declared
|
||||
permission with the effective data scope. An exact task grant cannot cover
|
||||
workspace data. A workspace grant authorizes only the bound workspace and is
|
||||
still intersected with current user and resource access. Revocation and scope
|
||||
changes increment the existing grant generation.
|
||||
|
||||
## Runtime binding and protocol
|
||||
|
||||
Add effective `DataScopeKind` to `webapp.CapabilityBinding`, sourced from the
|
||||
persisted instance and checked against it on every request. Keep `ScopeKind`
|
||||
for placement and task lifecycle. The relative context response exposes both
|
||||
`scope_kind` and `data_scope_kind`; empty historical data scope resolves to
|
||||
placement scope.
|
||||
|
||||
Task lists, single-task reads, task writes, messages, workflow reads, task
|
||||
dependency projections, and events use data scope. Workspace-data task
|
||||
canvases use the paginated workspace path, bounded by the trusted workspace
|
||||
ID, rather than the task-only shortcut. Explicit foreign `workspace_id`
|
||||
filters fail. Non-canvas instances retain current behavior.
|
||||
|
||||
## Compatibility and failure
|
||||
|
||||
The schema migration does not widen old rows. Historical runtime bindings
|
||||
and grants remain task-scoped until a reviewed update changes them. A stale
|
||||
binding, missing workspace/task, revoked grant, or mismatched data scope fails
|
||||
closed through existing safe errors. Current plugin manifests and immutable
|
||||
canvas packages need no rewrite.
|
||||
|
||||
## Verification
|
||||
|
||||
Test SQLite and PostgreSQL mapping, legacy null fallback, invalid scope
|
||||
combinations, runtime token invalidation, exact grants, all workspace task
|
||||
pages, task read/write and message paths, workflow and event scope, dependency
|
||||
redaction, and foreign-workspace denial.
|
||||
|
||||
## Related decision
|
||||
|
||||
- [Task canvas workspace data](../../../decisions/2026-09-23-task-canvas-workspace-data.md)
|
||||
Reference in New Issue
Block a user