heygen-com/hyperframes · error

Model did not return output '${outputName}'

Error message

Model did not return output '${outputName}'

What it means

Thrown per-frame by the session.process closure when session.run returns an outputs map that has no key matching outputName (the first entry from session.outputNames). This means the model executed but produced a different output tensor set than expected — the binding name captured at session creation no longer matches what run() returns. Indicates a model/ONNX-runtime version skew or a model whose output names are non-deterministic across runs (rare). Fires during active rendering, not at session setup.

Source

Thrown at packages/cli/src/background-removal/inference.ts:118

  const inputName = session.inputNames[0];
  const outputName = session.outputNames[0];
  if (!inputName || !outputName) {
    throw new Error("ONNX session is missing input or output bindings");
  }

  // Reused across calls; sized lazily on first frame. Saves ~9 MB/frame at 1080p.
  const inputData = new Float32Array(3 * INPUT_PLANE);
  const maskBuf = Buffer.allocUnsafe(INPUT_PLANE);
  let rgbaBuf: Buffer | null = null;
  let rgbaBgBuf: Buffer | null = null;

  return {
    provider: providerUsed,
    async process(rgb, width, height, withBackground = false) {
      const tensor = await preprocess(sharp, ort, rgb, width, height, inputData);
      const outputs = await session.run({ [inputName]: tensor });
      const output = outputs[outputName];
      if (!output) throw new Error(`Model did not return output '${outputName}'`);
      const expectedBytes = width * height * 4;
      if (!rgbaBuf || rgbaBuf.length !== expectedBytes) {
        rgbaBuf = Buffer.allocUnsafe(expectedBytes);
      }
      if (withBackground) {
        if (!rgbaBgBuf || rgbaBgBuf.length !== expectedBytes) {
          rgbaBgBuf = Buffer.allocUnsafe(expectedBytes);
        }
      }
      return await postprocess(
        sharp,
        output,
        rgb,
        width,
        height,
        maskBuf,
        rgbaBuf,
        withBackground ? rgbaBgBuf : null,

View on GitHub (pinned to c2996c8626)

Solutions

  1. Re-create the session (the outputNames are re-read fresh); avoid reusing a session across an onnxruntime reload.
  2. Pin the onnxruntime-node version to the one the package was tested with.
  3. If using a custom model, confirm its output tensor name is stable; log Object.keys(outputs) vs outputName.
  4. Re-download the canonical u2net_human_seg model to rule out a swapped model.

Example fix

// before
const session = await createSession({});
// ... many frames, onnxruntime reloads ...
session.process(frame); // throws: output not returned

// after
const session = await createSession({});
// use within a single process lifetime; recreate if onnxruntime reloads
Defensive patterns

Strategy: try-catch

Try / catch

try {
  await session.process(frame, w, h);
} catch (err) {
  if (err instanceof Error && err.message.includes('Model did not return output')) {
    await session.close();
    session = await createSession(); // recreate, re-read outputNames
    await session.process(frame, w, h);
  } else throw err;
}

Prevention

When it happens

Trigger: session.run({ [inputName]: tensor }) resolves with an outputs object whose keys don't include the outputName captured from session.outputNames[0] at creation. Seen when the ONNX runtime version changes between session creation and run, or with a model that dynamically renames outputs.

Common situations: An onnxruntime-node upgrade changed output-key semantics; a custom model whose output name varies; memory corruption producing a malformed output map; rendering resumed on a warm process after an onnxruntime hot-reload.

Related errors


AI-assisted analysis of heygen-com/hyperframes@c2996c8626 (2026-08-12). Data as JSON: /api/errors/84c0a68c6cf30314. Report an issue: GitHub.