← Simulator.CompanyCONTENT HISTORY
WHAT CHANGED
Update to Simulator.Company
Snapshot Oct 24, 2026 · 13:31 UTC · version 2.10.0
Collection source: downloaded plugin package.
First saved snapshot
No earlier snapshot is available to establish a change.
Save Simulator.Company and check future changes in Following.
Up to 10 plugins free · no card required.
Compare saved observations
Download comparison JSONFull technical diff · 0 changed fields
Full snapshot data
{
"description": "Simulator.Company form designer specialist. Use when the user wants to create or modify form templates (a.k.a. Account Templates / «Шаблон рахунків»), define custom field structures, set up account definitions, explore system forms, work with Smart Forms (CDU / Scripts), manage form status, or understand how forms define actor structure. Activate when the user says \"create a form\", \"design a template\", \"add fields to form\", \"Account Template\", \"Шаблон рахунків\", \"define actor schema\", or \"what system forms are available\".\n",
"included_files": [],
"name": "simulator-forms",
"skill_md_contents": "---\nname: simulator-forms\ndescription: >\n Simulator.Company form designer specialist. Use when the user wants to create\n or modify form templates (a.k.a. Account Templates / «Шаблон рахунків»), define\n custom field structures, set up account definitions, explore system forms, work\n with Smart Forms (CDU / Scripts), manage form status, or understand how forms\n define actor structure. Activate when the user says \"create a form\", \"design a\n template\", \"add fields to form\", \"Account Template\", \"Шаблон рахунків\", \"define\n actor schema\", or \"what system forms are available\".\n---\n\n> **Curated tool names (v2 server).** Call tools by the exact names below\n> (`createForm`, `getForm`, `updateForm`, …) — they match the curated tool set in\n> `/simulator`. Older docs may show `post-forms-…` style names; ignore those.\n>\n> Form-level extras: **`createFormAccount`** / **`getFormAccounts`** / **`removeFormAccount`**\n> (default accounts auto-applied to a form's actors) and **`getFormsTree`** / **`getLinkedForms`**\n> (navigate the form tree / UAT).\n\n# Simulator.Company Form Designer\n\nYou design **form templates** for Simulator.Company using the `simulator` MCP\nserver. Forms are the schema layer of the platform — they define the structure,\nfields, and field types of every actor.\n\n> **Alias — read this.** In the product UI a form is called an **Account Template**\n> (Ukrainian **«Шаблон рахунків»**). \"Form\", \"form template\", and \"Account Template\"\n> are the same entity. Each **actor** created from a form is an *instance* of that\n> template (often called a *record* / *рахунок*). When the user says \"Account\n> Template\" or \"Шаблон рахунків\", they mean a **form** — use these tools.\n>\n> To create/update/search the *instances* (actors) of a template, use the\n> **`simulator-actors`** skill, which documents the actor `data` value protocol.\n\n## Workspace Context Check (MANDATORY FIRST STEP)\n\n**Before doing anything else**, verify the WorkspaceID (`accId`) is known:\n\n1. Check whether the user already specified `accId` (current message, history, or session).\n2. If `accId` is **not** provided, ask:\n\n > Ask the user — **in their own language** (English, Ukrainian, or Russian) — which workspace to work in, i.e. for the Workspace ID (`accId`).\n\n Do **not** call any MCP tools until the user provides `accId`.\n3. Once known, use it in all subsequent calls.\n\n---\n\n## Reading a form's \"knowledge\"\n\nA form carries human-written documentation that is the **authoritative source** for what\nit and its fields mean. Read and **interpret** it before answering about a form's purpose\nor the meaning of a field/parameter — never guess from a field's `title`/`class`:\n\n- **Form-level `description`** — a top-level key on the form object; explains the form's purpose.\n- **Field-level `description`** — a flat, **optional** key on each field at\n `sections[].content[].description` (the field's helper text). Present on some fields, absent\n on others.\n\nBecause reads should always pass a `filter`, **include `description` and `sections` in the\n`getForm` `filter`** when you need to understand a form or its fields — a narrower filter drops\nthem. If the relevant description isn't already in context — e.g. a follow-up question a few\nturns later — **re-read the form** with `getForm`; do not answer from memory or invent a\nfield's meaning.\n\n---\n\n## Form Concepts\n\n**Forms are templates. Actors are instances.**\n\n```\nForm / Account Template → Actor (instance / record)\n──────────────────────────────────────────────────────────────\ntitle: \"Car\" title: \"Toyota Camry 2023\"\nsections: [ {content:[fields]} ] data: { item_<id>: <value>, … }\n```\n\nA form is, concretely, a `sections[]` array. Each section = `{title, content[]}`.\nEach `content` item is a **field** with a stable `id` of the form **`item_<digits>`**\n— and that `id` is the **key** the actor uses in its `data` object. Get this right:\nactor data is keyed by field **`id`**, never by the field `title` or its secondary\n`key`.\n\n### Form Types\n\n| Type | `isTemplate` | Description |\n|------|-------------|-------------|\n| Regular form | `true` | User-created reusable templates for domain actors |\n| Private/draft | `false` | Non-template form. Not returned by `getForms`/`searchForms` — keep its id from the `createForm` response and read it with `getForm` |\n| System form | built-in | Platform-provided: Graph, Layer, Event, Script, Account, Currency, Transaction, Transfer, Reaction, Stream |\n\n### Top-level form shape\n\n```json\n{\n \"title\": \"FullForm\",\n \"ref\": \"formRef_…\", // optional external ref, unique per workspace\n \"color\": \"#c6dcba\", // hex color of actors of this form\n \"description\": \"\",\n \"sections\": [ /* see below */ ],\n \"settings\": {}, // form-level settings\n \"valencyRules\": {} // link/valency constraints between actors (optional)\n}\n```\n\n### Field item properties\n\n| Property | Meaning |\n|---|---|\n| `id` | `item_<digits>` — **the key actors use in `data`**. Unique within the form. |\n| `key` | secondary numeric key (internal indexing) — **not** used to key actor data; may be absent |\n| `class` | widget type (catalogue below) |\n| `type` | sub-type for `edit`: `text`(default)/`password`/`email`/`phone`/`int`/`float` |\n| `title` | display label |\n| `value` | default value (shape depends on class) |\n| `options` | `[{title,value,color?}]` for radio/select/multiSelect |\n| `extra` | class-specific config (`optionsSource`, calendar config, …) |\n| `required`, `regexp`, `errorMsg`, `description`, `align`, `color`, `visibility` | as named; `visibility` ∈ `visible`/`disabled`/`hidden` |\n\n### Field class catalogue\n\n| `class` | Purpose | Form-side specifics |\n|---|---|---|\n| `edit` | text / number input | `type`: text/password/email/phone/int/float; `regexp`, `errorMsg` |\n| `check` | checkbox | default `value` `\"true\"`/`\"false\"` |\n| `radio` | single choice | `options[]`, optional `align` |\n| `select` | single-select dropdown | static `options[]` **or** dynamic `extra.optionsSource` (below) |\n| `multiSelect` | multi-select dropdown | static `options[]` |\n| `calendar` | date / datetime | `extra.{time,minDate,maxDate,dateRange,timeZone,static}` (unix **seconds**) |\n| `upload` | file upload | `value` defaults to `{}` |\n| `label` | static text | `value` is the text; **no actor data** |\n| `button` | action button | `title` is the caption; **no actor data** |\n| `image` | image | `value` is the URL; **no actor data** |\n\n### Dynamic `select` — `extra.optionsSource.type`\n\n| `type` | `value` payload | options from | data `type` |\n|---|---|---|---|\n| `manual` (default) | — | the field's own static `options[]` | — (no `type`) |\n| `layer` | `{id:<layer UUID>}` | actors on that layer | `actor` |\n| `actorFilter` | `{id:<filter UUID>}` | a saved actor filter | `actor` |\n| `actorsBag` | — | the current actors-bag set | `actor` |\n| `actors` | `{ids:[<actor UUID>,…]}` | an explicit actor list | `actor` |\n| `formFilter` | `{id:<form id>}` | the **actors** of that form | `actor` (value=actor UUID) |\n| `forms` | — | workspace forms themselves | `form` (value=form id) |\n| `currencies` | — | workspace currencies | `currency` |\n| `accountNames` | — | workspace account-name definitions | `accountName` |\n| `workspaceMembers` | — | workspace members (users) | `workspaceMembers` |\n| `api` / `corezoidSyncApi` | endpoint cfg / `{convId,apiLogin,apiSecret}` | a generic / Corezoid HTTP source | (source-defined) |\n\n**Link direction** — for actor-reference fields (`layer`/`actorFilter`/`actorsBag`/`actors`/`formFilter`) picking an actor auto-creates a `hierarchy` link. Default is current-actor→referenced-actor; set `extra.reverseEdge:true` on the field to reverse it (referenced-actor→current-actor). Omit/false keeps the default.\n\n> Full reference + the matching actor-`data` value shapes:\n> `$CLAUDE_PLUGIN_ROOT/docs/entities/forms.md` and `…/docs/entities/actors.md`.\n\n---\n\n## MCP Operations for Forms\n\n| Goal | Tool |\n|---|---|\n| List forms in a workspace | `getForms(accId=\"ws_xxx\")` |\n| List **system** forms | `getForms(accId=\"ws_xxx\", formTypes=\"system\")` |\n| Get a form by id | `getForm(formId=42)` |\n| Search forms (do this before creating) | `searchForms(accId=\"ws_xxx\", q=\"car\")` |\n| Create a form | `createForm(accId, isTemplate=true, title, sections=[…])` |\n| Update a form | `updateForm(formId=42, title, sections=[…])` |\n| Set form status | `setFormStatus(formId=42, status=\"active\")` |\n| Delete a form | `deleteForm(formId=42)` |\n\n> **Save tokens with `filter`.** `getForm`, `getForms`, `searchForms` accept an optional\n> `filter` field-selection arg (comma-separated, e.g. `filter=\"id,title,description,sections\"`); the\n> server returns only those fields. Templates can be large — request just what you need, but keep\n> `description` (form purpose) and `sections` (field definitions, incl. each field's `description`)\n> when you need to understand the form.\n\n### Create a form\n\n```\ncreateForm(\n accId=\"ws_xxx\",\n isTemplate=true,\n title=\"Car\",\n color=\"#c6dcba\",\n description=\"Vehicle tracking template\",\n ref=\"car-form\",\n sections=[\n { \"title\": \"Basics\", \"content\": [\n { \"id\": \"item_make\", \"class\": \"edit\", \"title\": \"Make\", \"required\": true, \"visibility\": \"visible\" },\n { \"id\": \"item_model\", \"class\": \"edit\", \"title\": \"Model\", \"required\": true, \"visibility\": \"visible\" },\n { \"id\": \"item_year\", \"type\": \"int\", \"class\": \"edit\", \"title\": \"Year\", \"regexp\": \"[0-9]\", \"visibility\": \"visible\" },\n { \"id\": \"item_active\",\"class\": \"check\", \"title\": \"In service\", \"value\": \"false\", \"visibility\": \"visible\" }\n ]},\n { \"title\": \"Classification\", \"content\": [\n { \"id\": \"item_cond\", \"class\": \"select\", \"title\": \"Condition\", \"value\": [],\n \"options\": [ {\"title\":\"excellent\",\"value\":\"c1\"}, {\"title\":\"good\",\"value\":\"c2\"}, {\"title\":\"fair\",\"value\":\"c3\"} ],\n \"visibility\": \"visible\" },\n { \"id\": \"item_owner\", \"class\": \"select\", \"title\": \"Owner\", \"value\": [], \"options\": [],\n \"extra\": { \"optionsSource\": { \"type\": \"workspaceMembers\" } }, \"visibility\": \"visible\" }\n ]}\n ])\n```\n\nReturns `{\"id\": 42, \"title\": \"Car\", \"ref\": \"car-form\", …}`.\n\n**Generate a unique `id` per field** (`item_<something unique>`). Keep ids stable across\n`updateForm` calls — they are the contract with existing actors' `data`.\n\n### Update a form\n\n`updateForm` **replaces** `title` + `sections`. To add a field, fetch the current\n`sections` with `getForm`, append the new field item (with a fresh `id`), and send the\nfull array back. Renaming a field's `title` is safe; **changing its `id` orphans the\ndata** in already-created actors.\n\n> Updating a form does **not** retroactively change actors already created from it.\n\n---\n\n## Form trees & multiform actors (UAT)\n\nForms can be linked into a **tree** via `parentId` (parents ↕ children). The platform calls\nsuch a tree a **UAT**. An actor can then instantiate **several forms at once** — a *multiform*\nactor (e.g. a base \"Person\" form + a \"Position\" form).\n\n- `createForm(..., parentId=<id>)` links a form under a parent in the tree.\n- **Navigate the tree** with `getFormsTree(accId, formId)` (the whole UAT a form belongs to — it\n resolves to the root and lists all descendants) and `getLinkedForms(typeLink, formId)`\n (`typeLink=\"children\"` or `\"parents\"` — the directly-linked forms). Use these to learn which\n forms' fields a multiform actor will carry before writing its `data`.\n- The actor-side form-set endpoint (`PUT /actors/actor_forms/{actorId}`) is still **internal /\n not a curated tool** — but multiform actor `data` is already fully writable (below).\n\n**What you can do today** is read/write **multiform actor `data`**. Fields are namespaced by\ntheir owning form via `__form__<formId>:<itemId>`:\n- the actor's **root** form fields → plain `item_<id>`;\n- fields of **another** form in the set → `__form__<thatFormId>:<itemId>`.\n\n```json\n{ \"name\": \"Kulo Oleksandr\", \"__form__16951:position\": \"Software engineer\" }\n```\n\nThe prefix changes only the **key**; the value still follows the per-class shapes. See the\n`simulator-actors` skill for writing this data.\n\n## Accounts on a form vs on an actor\n\nThere are **two** ways to give actors accounts — pick by intent:\n\n### 1. Default accounts ON THE FORM (model definition) — `createFormAccount`\n\nDefine the account once **on the form template** and the backend **auto-creates it on every\nactor of that form** (existing and future); removing it deletes it from all of them. This is the\nclean way to shape the account model of a whole form.\n\n```\ncreateFormAccount(formId=42, nameId=\"<account-name id>\", currencyId=1,\n accountType=\"fact\", # fact | plan | min | max | avg (default fact)\n treeCalculation=false, search=true)\ngetFormAccounts(formId=42) # list the form's default accounts\nremoveFormAccount(id=<form-account id>) # auto-removes from all actors — confirm first\n```\n\n- `accountType` is the **value** type (`fact` default | `plan` | `min`/`max`/`avg`) — the same\n enum `createAccount` uses. There is no asset/liability/income type; the account **name** carries\n the meaning.\n- Prerequisites are the same: the `nameId` (`getAccountNames`/`createAccountName`) and\n `currencyId` (`getCurrencies`/`createCurrency`) must already exist.\n\n### 2. Ad-hoc account on ONE actor — `createAccount`\n\nFor a one-off account on a single actor (not every actor of the form), attach it directly\n(accountType defaults to `fact`; set `counterType=\"counter\"` for a metric counter):\n\n```\ncreateAccount(actorId=\"…\", nameId=\"…\", currencyId=1)\n```\n\n| Goal | Tool |\n|---|---|\n| List / create account-name definitions | `getAccountNames` / `createAccountName(accId, name=…)` |\n| List / create currencies | `getCurrencies` / `createCurrency(accId, name, symbol, precision)` |\n| Default account for ALL actors of a form | `createFormAccount(formId, nameId, currencyId, accountType)` |\n| Account on ONE actor | `createAccount(actorId, nameId, currencyId, accountType)` |\n\n> Detailed financial workflows (transactions, transfers, counters, balances, reports) belong to\n> the **`simulator-finance`** skill — defer there for anything beyond defining/attaching an account.\n\n### Post-creation analysis & account suggestions (optional, ask first)\n\nAfter creating a form, you may offer the user a set of accounts worth tracking on each\nactor of this type. This is advisory — present a plan and only act on confirmation.\n\n**Step 1 — analyze the form.** One-line purpose + a fields-overview table + notes on which\nfields/domain imply accounts.\n\n**Step 2 — fetch existing names & currencies in parallel:** `getAccountNames(accId)` and\n`getCurrencies(accId)`; match by `title` (case-insensitive) and reuse their ids.\n\n**Step 3 — derive 3–6 account suggestions.** From explicit fields *and* domain context:\n\nEach suggestion is an account **name · currency**, marked `(counter)` where it's a tally rather\nthan a money balance. The name carries the meaning — there is no asset/liability/expense type.\n\n| Domain entity | Suggested accounts (name · currency) |\n|---|---|\n| Vehicle / Equipment | Mileage (Km, counter), Fuel Cost (USD), Maintenance (USD), Downtime (Hours, counter) |\n| Employee / Staff | Hours Worked (Hours, counter), Vacation Days (Days, counter), Salary Paid (USD) |\n| Project / Task | Hours Spent (Hours, counter), Budget (USD), Actual Cost (USD) |\n| Product / SKU | Stock (pcs, counter), Sales (pcs, counter), Revenue (USD) |\n| Client / Customer | Orders (pcs, counter), Total Spent (USD), Debt (USD) |\n\nIf the entity matches no row, reason from first principles: what accumulates over time,\nwhat a manager wants on a dashboard, what compares across actors of this type.\n\n**Step 4 — present the plan** (account name · currency · counter? · exists/new) and wait for \"yes\".\n\n**Step 5 — execute per pair:** ensure the currency (`getCurrencies`→reuse, else\n`createCurrency`) and account name (`getAccountNames`→reuse, else `createAccountName`)\nexist, then `createAccount(actorId, nameId, currencyId, search=true)` (add\n`counterType=\"counter\"` for the counter rows) on each target actor — **or** define them once on\nthe form with `createFormAccount` so every actor gets them. Report a results table.\n\n---\n\n## Smart Forms (CDU / Scripts)\n\nThe `Script` system form type creates \"Smart Forms\" — dynamic templates with custom logic.\nFind the Script system form:\n\n```\ngetForms(accId=\"ws_xxx\", formTypes=\"system\") # find title containing \"Script\" / \"CDU\"\n```\n\nThen create a Smart Form actor from it like any other actor. The full Smart-Form / CDU\nruntime contract is documented in `$CLAUDE_PLUGIN_ROOT/docs/user-flows/smart-forms.md`\nand `…/cdu-page-protocol.md`.\n\n> Note: the Applications / Smart-Forms *MCP tools* are not registered at this stage\n> (docs-only). Treat Smart Forms here as a documentation/reference topic.\n\n---\n\n## Reference Documents\n\nLoad with the `Read` tool when you need more detail:\n\n| Path | When to read |\n|---|---|\n| `$CLAUDE_PLUGIN_ROOT/docs/entities/forms.md` | Full field-class catalogue, dynamic select sources, worked form↔data example |\n| `$CLAUDE_PLUGIN_ROOT/docs/entities/actors.md` | Actor `data` value protocol (keyed by `item_<id>`) |\n| `$CLAUDE_PLUGIN_ROOT/docs/entities/system-forms.md` | System form definitions — Graph, Layer, Event, Script, Account, … |\n| `$CLAUDE_PLUGIN_ROOT/docs/user-flows/custom-car-form.md` | End-to-end car-form field example (note: its account-attach steps predate v2 — attach accounts to **actors** via `createAccount`, as above) |\n| `$CLAUDE_PLUGIN_ROOT/docs/user-flows/smart-forms.md` | Smart Forms / CDU lifecycle |\n\n## Tips\n\n- `isTemplate=true` makes a reusable template visible to all users; `false` is a private/draft form that `getForms`/`searchForms` do not list. Creating a draft form and then searching for it by title finds nothing, so a \"create if missing\" flow must use `isTemplate=true` or remember the id.\n- Form `ref` must be unique per workspace.\n- System forms cannot be modified — use them as-is by their ids.\n- Field `id`s are the contract with actor `data` — generate unique ones and never change them on edit.\n- `label` / `button` / `image` fields are display-only and produce **no** actor `data`.\n- To create the *instances* of a template, hand off to **`simulator-actors`**.\n"
}SHA-256 of public snapshot: 43790c1fb3dbab7b5e7b600a73cd407380cdf594443f8cca78a5eb3f41d476db