# Gleam supporting APIs

Read codecs, signals, queries, children, durations, typed errors and workflow test helpers.

Supporting modules define the values that cross workflow boundaries. Use their codecs and typed errors to handle malformed input and execution failure explicitly.

## Codecs

A codec pairs JSON encode and decode functions. Decode errors carry a reason and field path. The null codec represents the canonical no-argument query document.

**aion/codec — public signatures**

```text
pub type Codec(a) {
  Codec(encode: fn(a) -> String, decode: fn(String) -> Result(a, DecodeError))
}

pub type DecodeError {
  DecodeError(reason: String, path: List(String))
}

pub fn json_codec(
  encoder: fn(a) -> json.Json,
  decoder: decode.Decoder(a),
) -> Codec(a)

pub fn null_codec() -> Codec(Nil)
```


## Signals and queries

Signal references bind a name to a payload codec. Receive waits durably; send delivers to a workflow id. Register a query handler before the first yield point that should answer it. Query callbacks return a value and must remain read-only.

**aion/signal — public signatures**

```text
pub opaque type SignalRef(payload)

pub fn new(name: String, payload_codec: Codec(payload)) -> SignalRef(payload)

pub fn name(reference: SignalRef(payload)) -> String

pub fn codec(reference: SignalRef(payload)) -> Codec(payload)

pub fn receive(
  reference: SignalRef(payload),
) -> Result(payload, error.ReceiveError)

pub fn send(
  workflow_id: String,
  reference: SignalRef(payload),
  payload: payload,
) -> Result(Nil, error.EngineError)
```


**aion/query — public signatures**

```text
pub fn handler(
  name: String,
  arguments_codec: Codec(arguments),
  value_codec: Codec(value),
  reply: fn(arguments) -> value,
) -> Result(Nil, error.QueryError)

pub fn dispatch(
  name: String,
  arguments_codec: Codec(arguments),
  arguments: arguments,
  value_codec: Codec(value),
) -> Result(value, error.QueryError)
```


## Children and durations

A child handle carries its result codecs. Await decodes success or the typed child error. Duration constructors convert explicit units to the SDK’s millisecond representation.

**aion/child — public signatures**

```text
pub opaque type ChildHandle(output, workflow_error)

pub fn spawn(
  name: String,
  workflow_fn: fn(input) -> Result(output, workflow_error),
  input: input,
  input_codec: Codec(input),
  output_codec: Codec(output),
  error_codec: Codec(workflow_error),
) -> Result(ChildHandle(output, workflow_error), error.EngineError)

pub fn await(
  handle: ChildHandle(output, workflow_error),
) -> Result(output, error.ChildError(workflow_error))

pub fn spawn_and_wait(
  name: String,
  workflow_fn: fn(input) -> Result(output, workflow_error),
  input: input,
  input_codec: Codec(input),
  output_codec: Codec(output),
  error_codec: Codec(workflow_error),
) -> Result(output, error.ChildError(workflow_error))

pub fn child_id(handle: ChildHandle(output, workflow_error)) -> String

pub fn output_codec(
  handle: ChildHandle(output, workflow_error),
) -> Codec(output)

pub fn error_codec(
  handle: ChildHandle(output, workflow_error),
) -> Codec(workflow_error)
```


**aion/duration — public signatures**

```text
pub opaque type Duration

pub fn milliseconds(value: Int) -> Duration

pub fn seconds(value: Int) -> Duration

pub fn minutes(value: Int) -> Duration

pub fn hours(value: Int) -> Duration

pub fn days(value: Int) -> Duration

pub fn to_milliseconds(duration: Duration) -> Int
```


## Agent outcomes and errors

Agent outcomes carry the harness’s text, final message, stop reason and session id. Typed errors distinguish activity, timeout, cancellation, replay mismatch, decoding, query and child failures.

**aion/agent — public signatures**

```text
pub type AgentOutcome {
  AgentOutcome(text: String, final_message: String, stop_reason: String, session_id: String)
}

pub fn outcome_codec() -> Codec(AgentOutcome)
```


**aion/error — public signatures**

```text
pub type ActivityError {
  Retryable(message: String, details: String)
  PolicyRefused(message: String)
  Terminal(message: String, details: String)
  ActivityDecodeFailed(codec.DecodeError)
  ActivityTimedOut(TimeoutError)
  ActivityCancelled(CancellationError)
  ActivityNonDeterministic(NonDeterminismError)
  ActivityEngineFailure(message: String)
}

pub type TimeoutError {
  TimedOut(message: String)
}

pub type CancellationError {
  Cancelled(reason: String)
}

pub type NonDeterminismError {
  NonDeterminismViolation(message: String)
}

pub type EngineError {
  EngineFailure(message: String)
}

pub type WorkflowError {
  WorkflowEngineFailure(message: String)
}

pub type BoundaryDecodeError {
  DecodeFailed(codec.DecodeError)
}

pub type ReceiveError {
  ReceiveDecodeFailed(codec.DecodeError)
  UnknownSignal(name: String)
  ReceiveCancelled(CancellationError)
  ReceiveNonDeterministic(NonDeterminismError)
  ReceiveEngineFailure(message: String)
}

pub type QueryError {
  QueryDecodeFailed(codec.DecodeError)
  UnknownQuery(name: String)
  QueryTimedOut(TimeoutError)
  QueryNotRunning(workflow_id: String)
  QueryHandlerFailed(message: String)
  QueryEngineFailure(message: String)
}

pub type ChildError(workflow_error) {
  ChildWorkflowFailed(workflow_error)
  ChildCancelled(reason: String)
  ChildTimedOut(timeout: String)
  ChildOutputDecodeFailed(codec.DecodeError)
  ChildErrorDecodeFailed(codec.DecodeError)
  ChildEngineFailure(message: String)
}

pub type TimeoutResultError(error) {
  TimedOutError(TimeoutError)
  InnerError(error)
  TimeoutEngineFailure(message: String)
}

pub fn retryable(message: String) -> ActivityError

pub fn retryable_with_details(
  message: String,
  details: String,
) -> ActivityError

pub fn policy_refused(message: String) -> ActivityError

pub fn terminal(message: String) -> ActivityError

pub fn terminal_with_details(
  message: String,
  details: String,
) -> ActivityError
```


## Manifests and tests

Manifest encoding serializes the supplied activity declarations. Testing creates an isolated deterministic environment with virtual time, mocked activities and children, recorded observations and replay assertions.

**aion/manifest — public signatures**

```text
pub fn to_json(declarations: List(Declaration)) -> String
```


**aion/testing — public signatures**

```text
pub opaque type TestEnv

pub fn new() -> Result(TestEnv, error.EngineError)

pub fn process_key(env: TestEnv) -> String

pub fn run(workflow: fn(TestEnv) -> value) -> Result(value, error.EngineError)

pub fn advance(
  env: TestEnv,
  by: duration.Duration,
) -> Result(TestEnv, error.EngineError)

pub fn current_time_milliseconds(
  env: TestEnv,
) -> Result(Int, error.EngineError)

pub fn mock_activity(
  env: TestEnv,
  activity_value: Activity(input, output),
  handler: fn(input) -> Result(output, error.ActivityError),
) -> Result(TestEnv, error.EngineError)

pub fn mock_child(
  env: TestEnv,
  name: String,
  input_codec: Codec(input),
  output_codec: Codec(output),
  error_codec: Codec(workflow_error),
  handler: fn(input) -> Result(output, workflow_error),
) -> Result(TestEnv, error.EngineError)

pub fn observations(_env: TestEnv) -> Result(String, error.EngineError)

pub fn recorded_observations(_env: TestEnv) -> Result(Int, error.EngineError)

pub fn clear_observations(env: TestEnv) -> Result(TestEnv, error.EngineError)

pub fn assert_replay(
  env: TestEnv,
  workflow: fn() -> Result(value, workflow_error),
) -> Result(value, replay.ReplayError(workflow_error))
```


These modules live under gleam/aion_flow/src/aion. The test helpers use the engine’s linked testing functions; run them in the Aion test environment.

On main, gleam/aion_flow/src/aion/signal.gleam:1–102, query.gleam:1–137 and child.gleam:1–204 declare the signal, query and child APIs. The remaining modules named above define their own public types and functions.
