What an Indicator does not do yet, and where to find the numbers. An Indicator is a sandboxed, declared computation over market data; a few things a kScript (legacy) does are deliberately out of scope today, and knowing them up front saves you from designing around a feature that is not there.
Not supported today
Numbers only in outputs. Every output is a 64-bit float and NaN is the one "nothing here" value. Text reaches the chart only through string slots and renderers under the second runtime contract; a color, a symbol string, or a free-text setting has no param form (every param is a number). Decisions are numbers too: 1 or 0 in a data-only output, turned into a look by the sheet.
No handles to drawn shapes. Boxes and segments are declared once and evaluated on every bar; there is no object to move, extend, or delete later, and no growing collection of them (16 boxes and 16 segments per sheet). A shape that should end is a when gate that turns 0, and the bars it was alive on stay drawn. A kScript that mutates drawings stays on the kScript engine (Drawing objects).
Tape is live only. The daemon's tape buffer requires min_size and serves individual prints. Historical tape and pre-bucketed order-size bands remain unavailable: history must be "0", and trade_volume_by_size still refuses by name. Side-split aggregate volume remains the scalar trades source (Data sources).
The chart ignores pins. In the browser every input reads the chart's own market and interval; symbol, exchange, and interval pins are honored on your machine only. A cross-venue or higher-timeframe package is a package for your machine, and a higher timeframe on the chart is a bucket fold inside the module (Multi-timeframe).
range() is not drawn on the chart. A declared range validates and installs, and scalar surfaces ignore it as designed, but the chart does not render it yet; shade a band with a box on every bar instead. fills exists only in hand-written sheets.
No alerts from the chart yet. Alerts armed from the chart on a published Indicator are behind a flag today. The supported path is a watch on the metric id from your machine: om watch create with a level or an edge condition on wrun/@scope/name/<output> (Alerts).
Screens and backtests refuse celled packages. A package with a volume_profile or book input runs on the chart, in watches, and under om metric get / om metric series, but om metric screen and om backtest refuse it by name: their replay and fan-out paths carry no cell blocks yet.
No history array. state() sees one bar. There is no close[1]; the previous value is a variable you kept, and a window is a ring buffer you fill. This is also why an Indicator cannot look ahead by accident (Execution model).
No persistence across runs. Module state lives for one evaluation and is restored by reset() for the forming bar. Nothing survives a reload or carries from one run to the next; anything you need next time is recomputed from the loaded history.
No cross-Indicator communication on the chart. Two overlays on the same chart do not share state. On your machine a hand-written sheet can compose an installed package's output as an input (a metric source); the chart does not compose.
No execution from the file. The module has no filesystem, no network, and no order capability. A watch on the metric can carry an execute action; that authorization lives on the watch and never in the Indicator.
Named refusals
Each gap that a surface can hit at runtime is a typed refusal, so the message names the way out:
wrun_cells_unavailable a celled input reads a class this data plane does not serve
wrun_celled_metric_unsupported a backtest or screen was asked to evaluate a celled package
wrun_cell_block_too_large a bar's block exceeds the input's max_cells (never truncated)
wrun_preview_displacement_unsupported chart preview of an output with displacement_bars
wrun_source_set_generated a sheet edit on a code-first workspace (edit the declaration)
wrun_render_result_too_large the expanded render selection passed 2 MiB in one runCommon errors lists each one with its cause and fix.
Sandbox limits
Every Indicator runs under fixed ceilings so one module cannot exhaust the chart or the daemon: 16 boxes and 16 segments per sheet, 32 renderers, 64 drawings, 64 polyline points, 64 string slots of at most 4096 bytes each, 64 KiB of strings per row and 8 MiB per run, bar offsets within -500..500, a 4 MiB default memory ceiling, and the max_cells contract on every celled input. The full table, with the exact refusal for each, is in the Limits reference.
Build and runtime errors
For the messages you hit while writing an Indicator (a coordinate passed as a string instead of a handle, a param option that does not exist, a missing cast, a sheet field out of range, the four-export contract), see Common errors. Each one is listed by its exact text with a cause and a fix.