a9script

Docs / Agents: CLI, MCP, skill

Parameter structures — saying what a caller must send

A parameter structure is an entity of kind parameter_structure. It names the shape of a JSON value once, and everything that needs to say a shape says the name instead: a config function’s parameter, a main script’s input and output, and — through those — the input schema an assistant is offered for a tool.

It is optional. A script or a function that declares nothing is byte-identical to what it was, so add one when something outside the environment has to get the shape right without asking a person.

The file

{
  "kind": "parameter_structure",
  "name": "Customer",
  "config": {
    "description": "A person we sell to.",
    "fields": [
      { "name": "email", "kind": "string", "required": true, "description": "Their address." },
      { "name": "name", "kind": "string", "description": "Display name." }
    ]
  }
}

A field has name, kind, and optionally required, description, array and structure. Nothing else — the field object is strict, so a minLength or a pattern is refused where you type it rather than ignored.

The kinds are string, number, boolean, object and structure.

Nesting is a name

A field of kind structure must carry structure, naming the one it holds. There is no inline shape.

{
  "kind": "parameter_structure",
  "name": "PurchaseOrder",
  "config": {
    "fields": [
      { "name": "reference", "kind": "string", "required": true },
      { "name": "customer", "kind": "structure", "structure": "Customer", "required": true },
      { "name": "lines", "kind": "structure", "structure": "OrderLine", "array": true }
    ]
  }
}

array is a flag beside the kind, not an item type — so an array of arrays cannot be written at all. Where a shape is somebody else’s and changes on their schedule, use kind: "object" and say so honestly.

Two rules the folder relies on:

  • Order does not matter. A reference is a NAME, resolved nowhere at write time, so PurchaseOrder.json may name Customer before that file is applied. apply sends the folder; a name nothing declares is reported where it runs, and as a changeset warning when you lint.
  • A cycle IS refused, at Activate, naming the reference that closed it.

Attaching one

On a config function’s parameter, and on a main script’s input and output:

{
  "kind": "config_function",
  "name": "createOrder",
  "config": {
    "type": "http",
    "connectionName": "crm",
    "method": "POST",
    "path": "/orders",
    "params": [{ "name": "order", "structure": "PurchaseOrder" }],
    "bodyKind": "json",
    "body": "{{order}}"
  }
}
{
  "kind": "script_main",
  "name": "take-order",
  "codeFile": "take-order.js",
  "config": { "inputStructure": "PurchaseOrder", "outputStructure": "OrderReceipt" }
}

The structures must be in the same folder, or already in the environment. apply orders the kinds for you.

Where it is checked, and where it is not

Checked at the API door and at an MCP tools/call, after the caller’s credential and before any run starts; and on a config function’s own Test or probe, before the call leaves. A webhook only REPORTS — one warning line in the run’s log, and the run happens.

Never inside a script. A script calling a configured function is not checked against that function’s structures, so do not expect a refusal there and do not use a structure as an assertion. A structure describes what crosses INTO the environment.

Three properties to write against:

  • No coercion. "5" for a number field is refused, not converted.
  • An undeclared field passes. A structure is not a closed contract.
  • null reads as absent — so required refuses it.

Reading what is there

entity list parameter_structure and entity get parameter_structure <name> answer as they do for any kind. A structure has no secret, so nothing is masked. When you lint a folder, apply --dry-run reports a reference that names nothing as a warning rather than a refusal — read the warnings.

Rendered from docs/skills/a9script-authoring/reference/parameter-structures.md in the product's own repository, at build time. Found a problem on this page? Write to the address in the footer.