FacetDocs

Commands

Every command, with its arguments. Each runs against a file with facet --doc FILE COMMAND (add --headless for a host of your own, without the app), or against the open window without --doc. facet guide TOOL prints the same for one command.

The table names each argument as facet call TOOL '{json}' takes it; the flag beside it is the command-line form.

build

Create a whole tree in one call: frames with auto layout, text, images, vectors, instances with variants and overrides, component sets and variable references. Returns every node id by layer name.

facet build @screen.json [--sync] [--replace] [--parent ID] [--component] [--preview out.png]
ArgumentFlagTypeAbout
schemaNODErequiredthe tree to build (see the grammar below); a bare node also works
parentId--parentidbuild inside this frame instead of on the page
position{x, y}page position of the root (default: right of existing content)
convertToComponent--componentboolmake the root a main component
replace--replaceboolreplace the top-level node of the same name: the new one takes its place, its instances move to the new components with the same names, and the old one is deleted (one undo step)
sync--syncboolchange the top-level node of the same name in place to match: layers that still match keep their ids, instances and comments; the rest are added or deleted (one undo step)
preview--previewpathwrite a PNG of the result (the written node, or the page)
facet build '{"name": "Card", "width": 320, "padding": 16, "gap": 8, "fill": "#FFFFFF", "cornerRadius": 12, "column": [{"text": "Hello", "font": "Inter 20 700"}, "Plain text"]}'

source

A layer written in the build language, shortest form first: what you would write to build it, ready to edit and send back with build --sync.

facet source NODE [--depth N]
ArgumentFlagTypeAbout
nodeIdid / name / selectorrequiredthe layer
depth--depthnumberlevels of children to include (all by default)
facet source Card

kit

The document's kit: its font, colors, type presets and parts, as you would write it.

facet kit

pages

The document's pages; "add" makes a page and shows it, "show" shows one by name or id. Builds go to the page showing.

facet call pages
facet call pages '{"add": "Flows"}'
facet call pages '{"show": "Flows"}'
ArgumentFlagTypeAbout
addnameadd a page with this name and show it
showname / idshow this page

modify

Change an existing node with the same keys as build; edit named descendants with "$nodes", an instance's layers with "$override" and its variant with "$variant".

facet modify NODE @props.json [--preview out.png]
ArgumentFlagTypeAbout
nodeIdid / name / selectorrequiredthe node to change: its id, or a layer name or selector that matches exactly one node
schemapropsrequiredkeys to set, e.g. {"fill": "#000", "$nodes": {"Title": {"text": "Hi"}}}
preview--previewpathwrite a PNG of the result (the written node, or the page)
facet modify 12 '{"$nodes":{"Title":{"text":"Welcome back"}},"fill":"#F8FAFC"}'

tree

The page structure: ids, names, types, positions and sizes, nested.

facet tree [NODE] [--depth N] [--full]
ArgumentFlagTypeAbout
nodeIdidstart here instead of the page
depth--depthnumberlevels to expand (default 4)
detail--full"full"every node with all its properties, as inspect shows them
facet tree --depth 2

inspect

Everything about one node in grammar keys: position, size, sizing, layout, look, text, component facts, children.

facet inspect NODE
ArgumentFlagTypeAbout
nodeIdidrequiredthe node
facet inspect 12

find

Nodes matching a selector: Name, "[name^=Card]", "[type=text]", "#12", "Card Title" (descendant), "Card > Title" (child), "A, B". Names may contain spaces ("Card Coil > Photo"); [name="..."] matches one name exactly.

facet find SELECTOR [--in NODE]
ArgumentFlagTypeAbout
selectorstringrequiredwhat to match
scopeidsearch inside this node only
facet find '[type=text]' --in 12

components

Component sets (with their variant properties and values in order, first is the default) and main components.

facet components

variables

Create a variable collection with any number of modes, in the document's variables (saved with the file, shown in the Variables window); a value may be {"alias": "Collection/name"}. Reference variables in builds as "@Collection/name|fallback": fills, strokes, gradient stop colors and positions, radius, stroke width, size, gap, padding, opacity (percent), font size, letter spacing, text and visibility stay bound, and set_mode switches a subtree's mode.

facet call variables @tokens.json
ArgumentFlagTypeAbout
collectionNamestringrequirede.g. Theme
modes[string]e.g. ["Light", "Dark"] (default one mode)
variables[{name, type, value / values}]requiredtype: color, number, string, boolean; values: {Mode: value or {"alias": "Collection/name"}}
facet call variables '{"collectionName":"Theme","modes":["Light","Dark"],"variables":[{"name":"surface","type":"color","values":{"Light":"#FFFFFF","Dark":"#0F172A"}}]}'

set_mode

Show a subtree in another mode of a collection: every property bound to that collection's variables takes the mode's value.

facet call set_mode '{"nodeId":ID,"collectionName":C,"modeName":M}'
ArgumentFlagTypeAbout
nodeIdidrequiredsubtree root
collectionNamestringrequiredthe collection
modeNamestringrequiredthe mode
facet call set_mode '{"nodeId":"12","collectionName":"Theme","modeName":"Dark"}'

design_system

Variables with their modes, components, and the colors and text styles in use.

facet call design_system

package

Save the design and write it with what it needs into one folder (default: "<name> package" beside it): the .facet document, the project's DESIGN.md, the system it follows at that version, fonts.json naming every family, and a README. Never overwrites a folder.

facet --doc F call package '{"out":"/abs/folder"}'
ArgumentFlagTypeAbout
outstringthe package folder (absolute)

systems

Design systems in the library (~/.facet/systems): each one's name, version, and absolute paths to its tokens.json (DTCG), DESIGN.md (rules) and folder. They are plain files; read and edit them directly.

facet call systems

system

One system (default: the one this file's project follows, named in the header of the DESIGN.md beside it): version, file paths, rules, published versions.

facet call system '{"name":"Acme"}'
ArgumentFlagTypeAbout
namestringsystem name

system_create

Make a system from this file: its tokens as tokens.json, the project's DESIGN.md (or a starter) as the system's rules, version 1.0.0; the project then follows it.

facet call system_create '{"name":"Acme","description":"..."}'
ArgumentFlagTypeAbout
namestringrequiredsystem name
descriptionstringone line about it
facet call system_create '{"name":"Acme"}'

system_use

Bring a system's tokens into this file (collections, modes, aliases, text, paint and shadow styles; existing ones update) and make the project follow it. Run it again after editing the system's files to take the changes.

facet call system_use '{"name":"Acme","version":"1.2.0"}'
ArgumentFlagTypeAbout
namestringsystem (default: the one followed)
versionstringa published version (default: the files as they are)
facet call system_use '{"name":"Acme"}'

system_save

Write this file's tokens to its system's tokens.json (unpublished until system_publish).

facet call system_save
ArgumentFlagTypeAbout
namestringsystem (default: the one followed)

system_publish

Record the system's files as a new version (major, minor, patch or an explicit 1.2.0) under versions/; a project that follows it moves to that version.

facet call system_publish '{"bump":"minor"}'
ArgumentFlagTypeAbout
namestringsystem (default: the one followed)
bumpstringmajor, minor (default), patch or a version
facet call system_publish '{"bump":"patch"}'

lint

Check the page against the design rules in DESIGN.md beside the file (colors, radii and spacing from tokens, text styles, fonts): the rules file's path, its rules and every layer that breaks one (main components and instance overrides; what instances show unchanged is not reported twice). Run it after edits.

facet call lint

duplicate

Copy nodes; a copy sits right of its source. Optional "name" and "mode": {collectionName, modeName} for a themed copy.

facet call duplicate '{"nodeIds":[ID],"name":"Copy"}'
ArgumentFlagTypeAbout
nodeIds[id]requirednodes to copy
namestringname of the copy
mode{collectionName, modeName}show the copy in this mode
previewpathwrite a PNG of the result (the written node, or the page)
facet call duplicate '{"nodeIds":["12"],"name":"Login Dark","mode":{"collectionName":"Theme","modeName":"Dark"}}'

delete

Delete nodes and their children.

facet call delete '{"nodeIds":[ID]}'
ArgumentFlagTypeAbout
nodeIds[id]requirednodes to delete
facet call delete '{"nodeIds":["14"]}'

move

Move layers into another frame (or onto the page with "parentId": null) at a child index (default: last, on top). Layers keep their place on the canvas unless the new parent's auto layout places them; absolute layers stay absolute.

facet call move '{"nodeIds":[ID],"parentId":FRAME,"index":0}'
ArgumentFlagTypeAbout
nodeIds[id]requiredlayers to move, in order
parentIdid / nullthe new parent frame (default and null: the page)
indexnumberchild index in the new parent (0 is the bottom of the stack and the start of a flow)
facet call move '{"nodeIds":["14"],"parentId":"12","index":0}'

script

Run JavaScript (the body of an async function) over the same tools, as ONE call: canvas.build({...}), canvas.find({selector}), canvas.call(TOOL, args) and plugin-style nodes (facet.currentPage.findOne(...), node.fills = [...], facet.createFrame()). If it throws, everything it did is rolled back; otherwise it is one undo step. --read-only always rolls back. No file, network or clock access; timers run instantly in order. facet guide script lists the API.

facet script @file.js [--read-only] [--input JSON] [--timeout-ms N]
ArgumentFlagTypeAbout
scriptstringrequiredthe code; return gives the result, await works
readOnly--read-onlyboolroll back every change at the end (inspections and measurements)
input--inputany JSONa value the script reads as canvas.input
timeoutMs--timeout-msnumbertime limit (default 30000, at most 120000)
facet script 'const card = facet.currentPage.findOne(n => n.name === "Card"); card.resize(320, card.height); return card.width;'

paint_styles

Create paint styles: each one solid color, bound to a color variable when given as "@Collection/name|#fallback". Apply with "$fillStyle" or "$strokeStyle". A name that exists is kept ("reused": true); "update": true gives it the new color instead.

facet call paint_styles '{"styles":[{"name":"Brand/Accent","fill":"@Brand/accent|#2563EB"}]}'
ArgumentFlagTypeAbout
styleslistrequired[{"name", "fill"}]
updateboolredefine styles that exist (layers using them update)
facet call paint_styles '{"styles":[{"name":"Brand/Accent","fill":"#2563EB"}]}'

effect_styles

Create effect styles from "effects" lists (drop-shadow, inner-shadow, blur, background-blur, as in build). Apply with "$effectStyle". A name that exists is kept; "update": true redefines it and every layer following it updates.

facet call effect_styles '{"styles":[{"name":"Elevation/Card","effects":[...]}]}'
ArgumentFlagTypeAbout
styleslistrequired[{"name", "effects"}]
updateboolredefine styles that exist (layers using them update)
facet call effect_styles '{"styles":[{"name":"Elevation/Card","effects":[{"type":"drop-shadow","y":4,"blur":12,"color":"#0000001A"}]}]}'

text_styles

Create text styles from text keys (fontFamily, fontWeight or fontStyle, fontSize, lineHeight, letterSpacing). Apply with "$textStyle". A name that exists is kept; "update": true redefines it and every text following it updates.

facet call text_styles '{"styles":[{"name":"Body/Strong","fontFamily":"Inter","fontWeight":600,"fontSize":14}]}'
ArgumentFlagTypeAbout
styleslistrequired[{"name", "fontFamily", "fontWeight", "fontSize", ...}]
updateboolredefine styles that exist (texts following them update)

photos

Search openly licensed photos (Wikimedia Commons, then Openverse): title, web-sized thumbnail URL, size, license, author and page. Place one with "$image": URL, or the best match directly with "$image": "photo:masala chai". Results and photos are cached.

facet call photos '{"query":"masala chai","limit":6}'
ArgumentFlagTypeAbout
querystringrequiredwhat the photo shows
limitnumberresults (default 6, at most 20)
facet call photos '{"query":"masala chai","limit":3}'

fonts

Every font family a document can name: those installed here and every Google Fonts family (styles, weights, italics, variable axes, subsets, license, whether it renders here now). Name any of them as fontFamily: one not installed is downloaded and cached before the write measures (FONT_INSTALLED); text in it shows a metric-close stand-in only while it loads. Runs without a host too.

facet fonts list|search QUERY|info FAMILY [--json]
ArgumentFlagTypeAbout
actionlist / search / infodefault: info with family, search with query, else list
querystringsearch: part of a family name
familystringinfo: the family
categorystringlist: sans-serif, serif, display, handwriting or monospace
installedboollist: only families that render here now
googleboollist: only Google Fonts families
limitnumberfamilies returned (list 200, search 20)
facet fonts search 'playfair' && facet fonts info 'Playfair Display'

refresh_images

Re-read and decode every image under a node (or the page) from the document: how many were refreshed, and which layers miss their image.

facet call refresh_images '{"nodeId":ID}'
ArgumentFlagTypeAbout
nodeIdidsubtree (default: the page)
facet call refresh_images '{"nodeId":"12"}'

project

Create a project (a folder beside the served document), or reuse the one with that name ("reused": true).

facet call project '{"name":"Checkout"}'
ArgumentFlagTypeAbout
namestringrequiredproject name

file

Create an empty document in a project (or reuse it); the reply gives its path. Work on it with facet --doc PATH.

facet call file '{"projectId":"Checkout","title":"Cart"}'
ArgumentFlagTypeAbout
projectIdstringrequiredproject name
titlestringrequiredfile name (without .facet)

projects

Projects beside the served document, with their files.

facet call projects

undo

Revert the latest write call as a whole (however many engine steps it took). If the document changed since, revert one step.

facet undo

redo

Replay the call undo reverted.

facet redo

audit

Layout findings: content a fixed frame clips (LAYOUT_OVERFLOW) and content an edge-pinned bar covers (LAYOUT_OCCLUDED). Every write runs it on what it wrote.

facet audit [NODE]
ArgumentFlagTypeAbout
nodeIdidaudit this subtree (default: the page)
facet audit 12

shot

Render nodes (or the page) to PNG, text included. LOOK at it after every write.

facet shot [NODE...] -o out.png [--scale 2] [--padding 0] [--background #FFFFFF]
ArgumentFlagTypeAbout
nodeIds[id]nodes to frame (default: the page)
outputpathrequiredPNG file to write
scale--scalenumberpixels per unit (default 1)
padding--paddingnumbermargin in units (default 0)
background--backgroundcolorcolor under the content (default transparent)
facet shot 12 -o card.png --scale 2

spec

Handoff: what a node is, its structure, every string, colors, typography, spacing, radii, shadows, instances, images, bound variables and component states.

facet spec NODE
ArgumentFlagTypeAbout
nodeIdidrequiredthe node
facet spec 12

measure

Handoff: layout as data (redlines): sizes, sizing modes, padding, gaps, insets and the space between siblings.

facet measure NODE [--depth N]
ArgumentFlagTypeAbout
nodeIdidrequiredthe node
depth--depthnumberlevels of children (default 1)
facet measure 12 --depth 2

tokens

Handoff: variables, or (when there are none) the colors, spacing, radii, shadows and text styles in use, as CSS custom properties, a TypeScript module or JSON.

facet tokens export --format css|ts|json|dtcg [--mode M] [--node ID] [-o FILE]
ArgumentFlagTypeAbout
format--formatcss / ts / jsonrequiredoutput format
mode--modestringone mode of each collection
nodeId--nodeidinfer from this subtree only
facet tokens export --format css -o tokens.css

assets

Handoff: image files, vectors as SVG and the font families in use, with a manifest.json.

facet assets export [NODE] --out DIR
ArgumentFlagTypeAbout
output--outdirrequiredfolder to write
nodeIdidexport from this subtree only
facet assets export 12 --out assets/

guide

This page. Topics: tools, grammar, results, or a tool name.

facet guide [TOPIC]
ArgumentFlagTypeAbout
topicstringtools, grammar, results or a tool name
facet guide build

Everything else

Files, hosts, the app window and behavior charts, as facet --help prints them:

facet: design by command, and drive the visible app

Agents: read `facet guide` first (generated from the tool catalog).

  facet --doc FILE build @screen.json [--preview s.png]   one call builds a whole tree
  facet --doc FILE modify NODE @props.json                change a node (and named layers)
  facet --doc FILE tree | inspect NODE | find SELECTOR | components | audit [NODE]
  facet --doc FILE spec NODE | measure NODE | shot [NODE] -o x.png
  facet --doc FILE tokens export --format css|ts|json|dtcg | assets export [NODE] --out DIR
  facet --doc FILE undo | redo                            whole calls
  facet --doc FILE call lint                              layers breaking the rules in DESIGN.md beside FILE
  facet --doc FILE call package ['{"out":DIR}']         FILE with its DESIGN.md, system and fonts in one folder
  facet [--doc FILE] call systems | system | system_create | system_use | system_save | system_publish
                                                           design systems: plain files in ~/.facet/systems/NAME
                                                           (tokens.json as DTCG, DESIGN.md); see `facet guide`
  facet [--doc FILE] history [list|version NAME|restore REF|diff FROM [TO]]   operation log and versions
  facet --doc FILE chart import @chart.json | chart FEATURE [--explore] | chart bind|design FEATURE @f.json
  facet --doc FILE states COMPONENT | states apply NODE VIEW | plays list|run | replay FEATURE PLAY --at MS
  facet --doc FILE lattice FEATURE matrix|flow|designs|replay [--scenario k=v]
  facet --doc FILE shot NODE --state VIEW [--scenario k=v] [--design k=v] -o x.png
  facet --doc FILE call TOOL '{json}'                     any tool (variables, set_mode, duplicate, delete, ...)
  facet close --doc FILE                                  save and stop the document's host
  facet --doc FILE --headless COMMAND                     own headless host even when the app has FILE open
  facet serve FILE [--socket PATH] [--font FILE]          run a headless host in the foreground
  facet [--doc FILE] mcp                                  the tools as an MCP server on stdio (facet mcp --help)

Open files (registry ~/.facet/docs, app socket ~/.facet/app.sock; --doc FILE uses the app's host when the app has FILE open):
  facet files [--json] [--no-ping]   every open file: path, kind app|headless, pid, build, socket, lock holder, ping health (ms)
  facet app restart [--bundle PATH]  save every file, restart the app on the new build (default: its own bundle), reopen
                                      every tab and headless host on the same sockets with the same view; prints both builds
  facet open FILE [--socket PATH] [--focus] [--new-window | --no-window]
                                               open FILE in the running app (a tab in the current window, own socket; --new-window: own window; --no-window: headless host), or start the app
  facet focus FILE             select FILE's tab and bring its app window to the front
  facet close FILE [--no-save] close FILE's app window (saves unless --no-save) or stop its headless host

Without --doc (or CANVAS_DOC) commands drive the running app over its control socket:
  facet capabilities [--json] | schema [OP] | demo list|open CASE|step|reset|close
  facet tour [CASE] [--delay-ms N] | whats-new [--json] | try [FEATURE] [--json]
  facet inspect | select ID | drag HANDLE DX DY | zoom FACTOR | pan DX DY
  facet duplicate | undo | redo | fit | save | reopen
  facet front                  bring the window to the front (no other command does)
  facet send '{"op":"mask","enabled":true,"mode":"outline"}'
  facet export --out DIR [--frames] [--settings JSON] [--wait]   background job; export status|cancel [JOB]
  facet variables [--json] | tokens [--mode NAME] [-o OUT.json] | tokens import FILE.json [--json]
  facet bench [--samples N] [--json]
  facet renderer exact|tiles   draw every frame exactly, or compose in tiles
  facet smoothness [--reset] [--frames] [--json]   presented frame rate, dropped frames, input latency, drawn jerk, flicker
  facet smoothness --oracle arm [--stride N] [--max-frames N] | stop | clear
  facet smoothness --oracle [--evidence DIR] [--threshold T] [--headless] [--json]   compare captured frames with references at rest

Without any host:
  facet render DOC -o OUT.png [--view content|saved] [--node ID] [--zoom Z] [--scale S] [--padding P] [--background #RRGGBB[AA]]
  facet export DOC --out DIR [--page P] [--node ID]... [--frames] [--format png|jpg|svg|pdf] [--size 2x|512w|512h] [--suffix S] [--text outlines|text]
  facet export DOC --pdf OUT.pdf [--page P]
  facet tokens DOC [--mode NAME] [-o OUT.json]
  facet chart CHART.json|DIR [--explore] [--json]       a chart file's report (scr-kit interchange)
  facet guide [TOPIC] [--json]
  facet fonts list|search QUERY|info FAMILY|fetch FAMILY...|refresh [--json]   installed and Google Fonts families

Global: --doc FILE, --socket PATH, --headless, --json; every command takes --help. Agent results print on stdout,
`facet: warning:` and `facet: note:` lines on stderr. Exit 0 = completed, 2 = invalid input or
unavailable, 3 = failed or unknown outcome (nothing changed for agent tools). No automatic retries.
Coordinates for drag, pan and pointer commands are canvas-local logical screen pixels; drag handles:
south_east, east, north_west, north, north_east, south, south_west, west, rotate.