Nodes that start external work and then wait for a signal use the declarative park contract:
local result, err = n:park({
wait_for_signal = true,
signal_id = stable_signal_id,
arm = {
ref = "component.namespace:arm_function",
args = { correlation_id = stable_signal_id },
},
})park persists the node yield before the orchestrator invokes arm.ref. The arm runs
in an isolated function process under the workflow's recovered actor and scope; arguments
are snapshotted as bounded plain data (scalars and tables with string or positive-integer
keys) before the durable commit. Cycles, runtime values, excessive nesting, and oversized
payloads fail with PARK_ARM_INVALID; metatables and later caller mutations cannot cross
the boundary. Arguments cannot select authority. Arm functions must be idempotent: after a crash
between external success and acknowledgement, restart recovery replays the persisted
declaration when the node reattaches. Persist stable correlation in the arguments rather
than returning an opaque handle. A failed arm returns the structured PARK_ARM_FAILED
error and abandons the tracked wait so a later signal cannot revive it.
Existing n:yield behavior is unchanged.