FishTea
Documentation

Spec reference

Generated from packages/spec/schema/spec.schema.json at build time, so it cannot drift from what the loader actually accepts. Spec format 1.2.

Sections

A spec is one JSON object. Each top-level key is a section with its own version, and every section is content-hashed so the console and the engine can tell exactly what changed.

fishtea required

business required

fieldtypenotes
id requiredstring
name requiredstring
localestring
currencystring

entities required

Every key other than version and doc is one entity definition.

calls required

Every key other than version and doc is one call definition.

rules required

fieldtypenotes
writesobject
classifyobject
callsobject
familiarityobject
presentobjectHow answers are laid out. molecules: per entity, which field is the title, eyebrow, body, link. shapes: per shape, the ordered organisms its answer is laid out as. Anything undeclared is derived from the spec. Checked in detail by present.ts.
siteobjectThe site map a shell navigates by: home, sections (the menu, in order), parents (where up goes), actions (shapes that open over a section), and the shell's business copy. Checked against the shapes at load (site.ts).

shapes required

Every key other than version and doc is one shape definition.

personas required

Every key other than version and doc is one object definition.

envelope required

fieldtypenotes
accept requiredstring[]
greeting requiredmap of object

notifications optional

Every key other than version and doc is one object definition.

echoes optional

Every key other than version and doc is one object definition.

operator optional

fieldtypenotes
shapesmap of shape
reportsmap of object

plugins optional

Every key other than version and doc is one pluginUse definition.

Definitions

version

typeString

typeSpec

entity

fieldtypenotes
fields requiredmap of typeSpec
indexstring[]
embedstring[]
uniquestring[]
adminanyRows an operator reads and edits at /admin → Data. true takes the defaults; title: the field a row is called by; columns: the fields the list shows; order: the field it sorts by, highest first; collect: the shape of a public form that adds rows, whose link /admin offers.
seedupsert | insertupsert (default): the seed file is the truth on every start; insert: missing rows only, so /admin edits stay

call

fieldtypenotes
kind requiredquery | mutation | compute | external
in requiredmap of typeSpec
out requiredtypeSpec
impl requiredobject
transactionboolean
timeoutMsintegerThis call's own budget in milliseconds, in place of rules.calls.timeoutMs (x1 for compute, x4 otherwise). For a vendor feed or a sync that honestly takes longer, without loosening every SQL call.

step

fieldtypenotes
idstring
call requiredstring
withobject
afterstring[]

next

fieldtypenotes
labelstring
shape requiredstring
argsobject
eachstring
onobjectFire this affordance when the named form field changes, instead of on a click. It is sent as an ordinary utterance, so it is gated, planned and recorded on the trail like any other turn.

shape

fieldtypenotes
asks requiredstring
input requiredmap of typeSpec
answer requiredtypeSpec
effect requiredread | write
allow requiredstring[]
planstep[]
assembleany
phrasestring
vessellist | card | detail | compare | timeline | confirm
nextnext[]
triggersstring[]
composestring[]Sibling shapes whose answers pour alongside this one, as parts of a single composite. Each must be a read this persona may ask; a write is never composed, because a write pours confirm-write on its own and a composite must not hide one.
classifybooleanfalse keeps this shape out of the classifier's tool list: it is reached as a composite part, a chip, a greeting or a posted shape, never by classifying someone's words. For a part that would otherwise compete with its lead.
scheduleobjectoperator shapes only: when the core runs this job by itself

pluginUse

fieldtypenotes
use requiredstringwhere the plugin comes from: a bare name (builtin or plugins/<name>), a relative path, or an npm package
kindintegration | ui | auth | classifier | channel | archetype | shell
configobjectanswers to the plugin's own configuration questions
enabledboolean