Skip to content
LogoLogo

Managed processes

Use sandbox.processes for commands you need to reconnect to, send input to, or stop later. The sandbox must be running. Use a recent SDK version that exports SandboxProcesses.

Start and follow a command

import { createClient } from "@nodeops-createos/sandbox";
 
const client = createClient();
const sandbox = await client.createSandbox({ shape: "s-1vcpu-1gb" });
try {
  await sandbox.waitUntilRunning();
  const task = await sandbox.processes.create({
    cmd: "sh",
    args: ["-c", "printf 'hello\\n'"],
  });
  for await (const event of sandbox.processes.connect(task.process_id)) {
    if (event.type === "data") console.log(event.data);
    if (event.type === "exit") console.log("exit:", event.exitCode);
    if (event.type === "error") throw new Error(event.message);
  }
} finally {
  await sandbox.destroy();
}

Disconnecting from output does not stop the managed command. Use delete() to stop its process tree, or destroy the sandbox when the workload is finished.

Methods

All methods act on the same sandbox. options supports the usual request options, including cancellation and transport timeout.

MethodReturnsUse
create(request, options?)Promise<ManagedProcess>Start a pipe process or PTY.
list(options?)Promise<{ processes: ManagedProcess[] }>List retained process records.
get(processId, options?)Promise<ManagedProcess>Read state and the retained output window.
connect(processId, options?)AsyncGenerator<ManagedProcessConnectEvent>Replay output and follow new events. after selects events with a greater sequence number.
input(processId, text, options?)Promise<{ input_seq: number }>Send UTF-8 input.
inputBytes(processId, bytes, options?)Promise<{ input_seq: number }>Send a Uint8Array.
closeStdin(processId, options?)Promise<OKResponse>Close a pipe process's stdin. PTYs reject this operation.
resize(processId, { rows, cols }, options?)Promise<OKResponse>Resize a PTY. Pipe processes reject this operation.
signal(processId, signal, options?)Promise<OKResponse>Send a supported signal, such as SIGINT or SIGTERM.
wait(processId, options?)Promise<ManagedProcess>Wait for the leader or complete process tree.
delete(processId, options?)Promise<ManagedProcess>Stop the process tree with a grace period.

Creation and PTYs

ManagedProcessCreateRequest accepts cmd, args, cwd, env, and pty. Supply cmd for a pipe process. To create an interactive default shell, use { pty: { rows: 24, cols: 80 } }. PTY output arrives on the pty stream; pipe processes retain separate stdout and stderr streams.

Output and reconnection

Data events contain { type: "data", seq, stream, data }. The SDK decodes the wire format's base64 data to UTF-8 strings. Other event types are exit (exitCode, signal), heartbeat, and error (message, optional oldestAvailableSeq).

Store the last data event's seq and pass { after: lastSeq } to reconnect. Retention is bounded to 1 MiB per process and 32 MiB per sandbox. An evicted offset returns HTTP 410; inspect the retained output window before choosing a new offset. Capture output elsewhere if you need longer retention.

Wait and stop options

For wait(), set scope: "leader" (default) or scope: "tree". waitTimeoutMs controls the server's long-poll budget, up to 30000 ms; zero or omission uses 30000. A 408 response means the wait expired: check state or wait again. timeoutMs is the separate client transport timeout.

For delete(), graceMs sets the delay between termination and force-killing remaining descendants. The default is 1000 ms; the range is 0 to 60000 ms.

See Managed Processes REST for wire fields, accepted signals, and error codes.