# Where scripts run

CoCoCo runs a script in one of two ways.

**Evaluated.** The whole script runs, and the value it returns with `return` is the
result. Its data arrives in the global `input`, or as the script's arguments, which
you read at the top with `local input = ...`.

**Dispatched.** The script runs once to set itself up, putting functions on the
global `exports` table, and then CoCoCo calls one of them. A `return` at the top
level is ignored. Keep the top level to constants and function definitions: it runs
before every call and counts against the same limits.

The table shows how each kind of script is run, how its data arrives and what
CoCoCo does with the result. The next chapters take them in turn, with a complete
script for each: *Workflows, webhooks and apps* for Normal scripts, *Integrations*,
and *Pure scripts*.

| Where | Profile | Data | Result |
|---|---|---|---|
| Playground and stored scripts | Normal | `local input = ...` | The chunk's return value is the run's output. |
| Workflow script nodes | Normal | `local input = ...` | The chunk's return value is the node's output. |
| Custom workflow actions | Normal | `local input, config = ...` | The chunk's return value is the node's output. |
| Incoming webhooks | Normal | called as `exports.handler(request)` | The handler's return value is the HTTP response. |
| Custom app server functions | Normal | called as `exports.<method>(…)` | The function's return value is sent back to the app. |
| Workspace handlers | Normal | called as `exports.<handler>(input)` | The handler's return value is its declared output. |
| MCP tools | Normal | called as `exports.handler(input)` | The handler returns the tool's JSON result. |
| Archive jobs | Normal | `input`: `last_checkpoint` holds the checkpoint of the last successful run, or nil on the first | `exports.schema()` describes the columns; `exports.next_chunk()` returns rows until nil. |
| Quote price tuning | Normal | `local input = ...` | The chunk returns a list of line adjustments. |
| Integration lifecycle hooks | Integration | called as `exports.init / shutdown / on_timer / on_event(…, config)` | The return value is ignored. |
| Integration handler scripts | Integration | `local …, config = ...`: the timer name, event or command input, then config | A command's return value is its result; other handlers' are ignored. |
| Integration server functions | Integration | called as `exports.<method>(…)` | The function's return value is sent back to the caller. |
| Integration workflow actions | Integration | `local input, config = ...` | The chunk's return value is the node's output. |
| Integration upgrade scripts | Integration | `local oldVersion, newVersion, oldConfig = ...` | A returned table becomes the new config; anything else keeps the old one. |
| Data pipeline stages | Pure | `input`: the row | The chunk returns the transformed row, or nil to drop it. |
| Report preparation scripts | Pure | `input`: the report's parameters, context and datasets | The chunk returns `input` with its datasets changed; the parameters stay as they were passed. |
| Scheduler penalty functions | Pure | called as `exports.calculatePenalty(schedule)` | The function returns the schedule's penalty as a number. |
| Product template resolvers | Pure | `input`: the template's configuration, components and finishing flags | The chunk returns a patch to the components and finishing, or nil for no change. |
| JDF and JMF templates | Pure | none | The chunk returns the template, usually a table of functions, to the script that loaded it. |

## Playground input

The playground passes the JSON in its Input box to the script as its argument, not
as a global variable or `ctx.input`, so bind it at the top with `local input = ...`.
When the box is empty the script receives no arguments and `input` is `nil`, so give
it a default. The next chapter opens with a complete playground script.

Calling the `executeLuaScript` mutation directly works the same way: supply its
`input.input` as a JSON-encoded string, for example `"{\"operationId\":\"example\"}"`.