Skip to main content
Connectors are the dots on a node. Inputs on the left, outputs on the right, and the lines you draw between them are how data moves through a workflow. You declare them in interface.yaml, and Canvas draws one dot per entry.
interface.yaml
That node has one input dot and two output dots.

Sending something to an output

Declaring an output only creates the dot. api/events.yaml is what puts a value on it. One row per output connector, in the same order interface.yaml declares them. Read that one file and you know everything the node ever emits.
api/events.yaml
emit names the connector. value shapes what lands on it, as an expression over the reply. An output with no row is a dot that never carries anything, and lint warns about it.

Emitting once, or many times

This is where the node’s kind shows up. A PromiseNode settles. One call, one reply, and each row fires once over that reply. The rows above are a settling node. A CallbackNode emits. The reply arrives as a stream of events, so a row says which event it fires on, and it fires every time that event arrives.
api/events.yaml
from: complete fires once at the end, over everything already emitted. That is how a streaming node also produces a single settled value for downstream nodes to use. The other from values cover the cases where something leaves the node that was never in the reply at all: tool for the result of a tool call, and narrator for a status line written alongside the main work.

Reading what arrives

A downstream node reads an upstream output by name:
quote1 is the id Canvas gives the node on the canvas, and quote is the output connector. So signal.quote1.quote is the quote text. Give outputs names worth reading. They become the reference someone types into a template later, and a good name is the difference between signal.crm1.contact and signal.crm1.output.

Types

type also decides how a wired field is written. A string field takes a Handlebars template, an object or array field takes a return expression. Config Schema covers both.

Required, and what waiting means

required: true means the node waits for that connector before it runs.
A node that never runs is usually a required connector with nothing wired to it. Nothing reports an error, because waiting is a legitimate state for a node to be in.

Looping over a list

A node does not loop itself. You loop in the workflow, with the Loop nodes, and your node runs once per item like any other step. That keeps a node simple: it takes what it is given, does one job, and emits.

Service connectors are different

The dots covered here carry data through a workflow. A node can also offer a capability that other nodes call directly, which uses a service edge instead. That is Service Connectors.

When it goes wrong


Next: Discoverability