Floe Agent
Docs

Design workflow (brief → spec → revisions → feedback → candidate → adopt → export)

Status: this page documents two states that must not be mixed.

Quickstart — released Canvas panel (actual UI)

  1. Open a Canvas, select the node you want to design from (a text/card node, media/file node, or a built-in Markdown/HTML/SVG card), and add or import its content.
  2. Open the Canvas view menu and choose Design workflow (canvas.designWorkflow). The panel acts on the selected node and reports that node's real capabilities.
  3. Save the brief/spec (Save brief, Save spec); Apply this spec to the whole canvas writes the canvas-level spec authority in one Canvas CAS commit, and existing plus new design subdocuments inherit it.
  4. Freeze the source: Use current node content reads the node's real text, retained asset bytes, bound CAD/Office workspace document or built-in card source through the adapter guards; Import source… ingests an external file.
  5. Let the assistant/tools propose a revision, inspect it under the candidate section (Show previews), then Adopt or Reject. Assistant adoption additionally needs Authorize assistant adoption, which mints a single-use expiring grant.
  6. Export verified… exports only the recorded format and reopens the bytes with the real parser first; Restore previous revision appends a recovery revision instead of overwriting.

[Unreleased] Conversational entry: one task, three modes

Product rules this round implements in source (module-verified; UI and tool wiring still pending):

Three work modes (Core API: DesignWorkMode, DesignWorkIntent and DesignWorkScope in FloeAgent/Sources/FloeCore/DesignWorkflow.swift):

Mode Before starting Execution Preview and completion
create one natural-language goal; a short follow-up only when a material input is genuinely missing; no form create the real editable artifact through the connected service; keep materials, inputs and workspace ownership show the real artifact and continue in natural language; complete only after save/reopen and format validation
modify freeze the stated revision; map the user's location to the real page, selection, fragment or object edit inside the frozen scope; content outside the scope and the original/manual draft stay recoverable show the change and the out-of-scope check; adoption updates the explicit original target
restructure read the current state; first confirm in conversation what content, data, behavior and format must be preserved and what may change reorganize inside a separate candidate; the original is never overwritten first; a manual edit invalidates the old baseline compare and verify each preservation constraint; only the user's adoption replaces the original; variants can be saved separately

“Optimize this a bit” is not automatically a rebuild: a local reversible change is a modify, a whole-structure/behavior change is confirmed as a restructure first. Switching modes keeps the current artifact and constraints in the same task. DesignWorkIntent.validated(family:) rejects a restructure without complete preservation constraints, an empty object id, a negative page index, non-positive regions/time ranges and a format/family mismatch (DesignWorkIntentError).

[Unreleased] Restructure authority: data is not permission

[Unreleased] Capability matrix and source classification

Model / where things live

Piece Location
Workflow state machine FloeAgent/Sources/FloeCore/DesignWorkflow.swift
Work modes, preservation constraints, authority receipts [Unreleased] FloeAgent/Sources/FloeCore/DesignWorkflow.swift
Shared owner workflow (propose/adopt, authority hook) FloeAgent/Sources/FloeCore/DesignOwnerWorkflow.swift
Capability matrix + source classification [Unreleased] FloeAgent/Sources/FloeCore/DesignCapabilities.swift, DesignCanvasService.swift
DESIGN.md import/edit/export FloeAgent/Sources/FloeCore/DesignMDCodec.swift
Subdocument codec (binding + bounds) FloeAgent/Sources/FloeCore/DesignCanvasMetadata.swift
Canvas-authority service + adoption grants FloeAgent/Sources/FloeCore/DesignCanvasService.swift
Shared UI/tool transaction (decide, apply template, use current node) FloeAgent/FloeApp/Workspace/DesignWorkflowActions.swift
Agent tools (canvas.design*, design.*) FloeAgent/FloeApp/Workspace/DesignAgentTools.swift
Panel (separate view) FloeAgent/FloeApp/Workspace/DesignWorkflowPanel.swift

Design state is a typed subdocument of the bound Canvas node (node metadata key canvas.design), persisted only through the existing FileCanvasDocumentRepository + CanvasProjectFileWriter compare-and-swap authority — so backup, sync, fork and revision-conflict handling are the Canvas ones. There is no independent design store, gallery or project identity: the node ID is the only identity, it is required, verified on decode, and a binding mismatch fails closed. Node, connections and layout stay in CanvasProject. The canvas-level project brief/spec authority lives on the CanvasProject itself (designProjectAuthority, an additive optional field; old packages decode with nil) — not a parallel store.

Lifecycle guarantees

Typed adapter capabilities (released state)

DesignCapabilityRegistry records only actually connected operations per content type; every unavailable operation carries its real reason. canvas.designCapabilities re-resolves per call. Connected today:

Type Connected operations Real path
image import, generate (when a model is configured), preview, verified export asset ingestion, media generation, CGImageSource reopen
video import, preview, verified export ingestion, AVAsset reopen (time anchors)
pdf import, preview, verified export ingestion, PDFKitGate reopen
notes import, preview, verified export markdown/plain-text bytes (md/markdown/txt), UTF-8 + format reopen
webpage/prototype import, capture (as revision), verified export browser capture bound to the exact task, locator-only snapshot; HTML/JSON and SVG reopen with a bounded XML/SVG parse
cad 2D dwg/dxf: import, preview, source export, verified export (same-engine reparse). 3D verified export is currently unavailable — glb/step/stl/obj/3mf/usdz/floecad fail explicitly rather than claiming a verified export CadDocumentCenter; engine edits stay in the CAD proposal flow
office/presentation import, preview, source export, verified export only for a node with an explicit Canvas-owned workspace binding (canvas.designBindDocument), via OfficeCommandCenter + bounded OOXML reopen (docx/xlsx/pptx) engine-command edits stay in the office proposal flow — that delegation, not "not connected", is the stated reason for unbound nodes

[Unreleased] CAD gains tool-level create and import (see the tool contract): the built-in package factory creates a legal .floecad package and reads it back; importing STEP/IGES/STL/OBJ/GLB/glTF geometry into an existing package drafts a proposal and changes nothing until preview + UI grant + apply. Imported geometry never fabricates a parametric feature tree; IGES shells/faces stay exact surface bodies (move/material/IGES re-export, no solid boolean/fillet/shell) and mesh formats stay render/mesh bodies, while the verified-export gate above is unchanged.

Built-in Canvas source nodes

The Canvas "add built-in" menu creates typed source cards (metadata.builtinPlugin) whose text IS the source and which render through dedicated views:

"Use current node" freezes the exact card bytes under the plugin's format (the adapter parser reopens them first); a proposal/adoption is written back into the same card text through the original render path, preserving node kind, builtinPlugin metadata, layout and title. Format compatibility is enforced: e.g. SVG/HTML bytes cannot be adopted into a Markdown (notes) card, and non-SVG bytes renamed .svg are rejected. An unknown/non-text builtin (e.g. panorama3D without a retained asset) fails with a precise, localized reason rather than falling back to generic card text.

Adoption always updates the real node: media/file nodes get a new verified asset reference, text nodes get the text body, layout/connections are preserved; variant creates an actual new node. Revision payloads live in the shared artifact store (DesignRevisions/<canvas>/<node>/<artifact>/<revision>), are immutable (identical re-store is a replay, different bytes a conflict), and are published before the single CAS commit so a crash never leaves a revision pointing at missing bytes. Exports use the recorded format only — no conversion is claimed — and reopen with the real parser before "verified" is reported. No screenshot/PDF is ever presented as an editable original.

Agent tools

canvas.designGetState, canvas.designCapabilities, canvas.designCreate, canvas.designUpdateBrief, canvas.designUpdateSpec, canvas.designGetProjectSpec, canvas.designSetProjectSpec, canvas.designRegisterRevision, canvas.designImportSource (payload published before one CAS commit; replay returns the recorded result, changed arguments are rejected), canvas.designUseCurrentNode, canvas.designExportRevision (recorded format only, real reopen validation), canvas.designAddFeedback, canvas.designPropose, canvas.designAdopt (replay is checked before the consumed grant; the durable decision outbox records the intent before the CAS and launch reconcile repairs crashes), canvas.designReject, canvas.designRestore (restores real node content).

All take explicit canvasID + nodeID (+ expectedRevision and an operationID for mutations); they read/write only through the Canvas authority. adopt additionally requires a grantID from a single-use, expiring user grant minted by the panel (DesignAdoptionGrantStore) — the agent cannot self-adopt. adopt/restore are side-effecting and approval-gated. Input data cannot grant permissions.

[Unreleased] cad.document adds create and import actions; the design.*/canvas.design* names and parameters are unchanged. Passing work modes and restructure authority through the model-facing arguments, and wiring Canvas actions to pass an optional work intent, are owned by the integration lane; no raw string/boolean “authorization” argument may be added.

Templates

Built-in templates ship with the app; user templates are stored in Application Support/FloeAgent/DesignTemplates with immutable version directories and atomic pointer swaps (rollback restores the real previous bytes). Templates delivered by the signed content-update service (kind templates) are materialized read-only into the same library with hash verification; install/update/rollback stay in Content Update settings. Template UI lives in the design panel (Creative), not Skills.

Tests

Released engine suites: Tests/FloeCoreTests/DesignWorkflowTests.swift: freezing, candidate-not-applied-until-adopt, no-op proposal rejection, variant branching, anchor staleness/relocation, resolution requiring a real change, revision conflicts, restore, DESIGN.md round-trip and spec hashing, canvas-subdocument binding/malformed/newer-schema safety, operation-ID dedup and capability honesty. Beyond the engine suites: whole-project adoption (real node content in one CAS, layout preserved, replay skips content work), project-spec authority (three nodes inherited in one commit, repeated different payloads, changed operation payload rejected, stale revision conflict, unrelated node edit, frozen run preserved, new-node inheritance, reopen), the decision outbox (full fingerprint dedupe across relaunch, legacy-envelope backfill, first write/reopen, corrupt/newer-schema read-only with observable errors, pending never pruned, hard cap), the payload store (traversal/symlink/overwrite/cross-canvas), template persistence and signed-package digest authority, the retained-image evidence policy (real PNG/JPEG/WebP/GIF bytes, MIME spoof, over-limit pre-decode rejection, duplicate/two-result attribution, Chat/Responses/Anthropic serialization), and FloeAppTests integration (image end-to-end import→adopt→export with delivery-failure reconcile, missing-origin fail-closed, project-spec tools across three nodes, use-current-node text + precise localized unavailable reasons, built-in Markdown/HTML/SVG cards source→propose→adopt→restore→verified-export and precise unsupported states, cross-task capture fail-closed).

Module evidence for the unreleased source (2026-10-13, branch codex/design-workflows-20261013, Xcode 27.0/Swift 6, focused SwiftPM harness): FloeCore ran 495 tests including 20 new intent/classification tests; the authority follow-up ran 141 focused tests including 8 new authority tests (forged matching source+digest denied with zero staged bytes, genuine bound claim accepted, stale/wrong-owner/digest/operation refused, idempotent replay does not claim twice). Runtime/log-repair evidence is listed in the tool contract. This is module-level evidence; the 2026-10-14 continuation added the full App compile, 15 changed App suites (78 Swift Testing + 53 XCTest cases), 26 native-CAD App tests, the conversational-entry UI test and one live-model design loop, and the real PPTX artifact passed independent python-pptx/openpyxl readback. Fine-grained GUI and on-device acceptance remain with the coordinator.

Open gates

Engine-command edits for office/presentation stay delegated to the office proposal flow even though a bound workspace document supports import/verified export; 3D CAD verified export (exchange/mesh formats and .floecad packages) has no connected single-payload reader yet and must not be claimed as verified; real-provider generation loops need configured credentials. [Unreleased] the conversational UI, the mode/authority tool wiring and the capability live probes are not integrated yet, so none of them may be presented as accepted or installable; visual acceptance and physical-device checks remain pending and are never implied by a passing unit test or a green build.

Search documentation

    Results open the matching section.