Copy page
View as Markdown View this page as plain text

Runtime Streams

Runtime streams are an optional ThreadState capability for opening live, runtime-authorized byte streams. They let portable agent code exchange opaque bytes with an execution host without specifying what the capability means or how a runtime transports it.

1. Types

interface RuntimeStreamRequest {
  capability: string;
  metadata?: Record<string, unknown>;
  timeoutMs?: number;
}

interface RuntimeByteStream {
  readonly readable: ReadableStream<Uint8Array>;
  readonly writable: WritableStream<Uint8Array>;
  readonly closed: Promise<{ ok: boolean; error?: string }>;
  close(reason?: string): void;
}

type RuntimeStreamErrorCode =
  | 'unsupported'
  | 'unavailable'
  | 'refused'
  | 'timeout';

type RuntimeStreamResult =
  | { ok: true; stream: RuntimeByteStream }
  | { ok: false; error: string; code?: RuntimeStreamErrorCode };

interface RuntimeStreams {
  open(request: RuntimeStreamRequest): Promise<RuntimeStreamResult>;
}

interface ThreadState {
  readonly runtimeStreams?: RuntimeStreams;
}

2. Optional Capability

runtimeStreams is optional. Existing runtimes may omit it and remain conformant, so agent code must feature-detect it before opening a stream.

Capability names and metadata are opaque to this specification. Runtimes own capability authorization and may refuse any request. A runtime must not infer portable semantics from a capability name or interpret metadata in a shared layer.

3. Direction and Lifetime

  • readable carries bytes from the execution host to the runtime.
  • writable carries bytes from the runtime to the execution host.
  • Streams are live, non-durable resources. They never park and do not survive an execution-host disconnect.
  • Closing the writable side is a graceful half-close: the host may continue sending bytes through readable.
  • close(reason?) aborts the complete stream and is idempotent.
  • closed settles exactly once with the final stream outcome.

4. Neutral Example

This tool sends media bytes to a workstation-hosted transcoder and reads the encoded result. The example demonstrates feature detection, opening, writing, reading, and cleanup.

const runtimeStreams = state.runtimeStreams;
if (!runtimeStreams) {
  return { status: 'error', error: 'This runtime has no workstation streams.' };
}

const opened = await runtimeStreams.open({
  capability: 'workstation_transcoder',
  metadata: { inputFormat: 'wav', outputFormat: 'opus' },
  timeoutMs: 10_000,
});
if (!opened.ok) {
  return { status: 'error', error: opened.error, error_code: opened.code };
}

const { stream } = opened;
try {
  const writer = stream.writable.getWriter();
  try {
    await writer.write(sourceMedia);
    await writer.close();
  } finally {
    writer.releaseLock();
  }

  const reader = stream.readable.getReader();
  const chunks: Uint8Array[] = [];
  try {
    for (;;) {
      const { value, done } = await reader.read();
      if (done) break;
      chunks.push(value);
    }
  } finally {
    reader.releaseLock();
  }

  const outcome = await stream.closed;
  if (!outcome.ok) throw new Error(outcome.error ?? 'Transcoder stream failed.');
  return { status: 'success', result: `Received ${chunks.length} encoded chunks.` };
} finally {
  stream.close();
}

5. Conformance

A runtime that implements runtimeStreams must preserve byte ordering in both directions, support graceful writable half-close and complete abort, and settle closed once for every successfully opened stream. open() should report refusal without creating a stream, return unavailable when the selected execution host is absent, and return timeout when stream opening exceeds the requested or runtime-defined deadline.