different-ai/openwork · error · ApiError

agent_diagnostics_request_too_large

agent_diagnostics_request_too_large

Error message

Agent diagnostics request body is too large

What it means

The agent diagnostics endpoint enforces AGENT_DIAGNOSTICS_MAX_REQUEST_BYTES and rejects early via the Content-Length header before reading the stream. If the declared body size exceeds the cap, `tooLarge()` throws ApiError with code `agent_diagnostics_request_too_large` without consuming the body. This guards memory and prevents oversized diagnostic payloads from being processed at all.

Source

Thrown at apps/server/src/server.ts:3759

  const tooLarge = () => new ApiError(
    413,
    "agent_diagnostics_request_too_large",
    "Agent diagnostics request body is too large",
  );
  const timedOut = () => new ApiError(
    408,
    "agent_diagnostics_request_timeout",
    "Agent diagnostics request body timed out",
  );
  const configuredDeadlineMs = Number(process.env.OPENWORK_AGENT_DIAGNOSTICS_BODY_TIMEOUT_MS);
  const deadlineMs = Number.isFinite(configuredDeadlineMs) && configuredDeadlineMs >= 50
    ? Math.min(configuredDeadlineMs, 10_000)
    : AGENT_DIAGNOSTICS_DEFAULT_BODY_DEADLINE_MS;
  const declaredLength = request.headers.get("content-length");
  if (declaredLength !== null) {
    const declaredBytes = Number(declaredLength);
    if (Number.isFinite(declaredBytes) && declaredBytes > AGENT_DIAGNOSTICS_MAX_REQUEST_BYTES) {
      throw tooLarge();
    }
  }

  const reader = request.body?.getReader();
  if (!reader) {
    throw new ApiError(400, "invalid_json", "Invalid JSON body");
  }
  const chunks: Uint8Array[] = [];
  let size = 0;
  let deadlineExpired = false;
  let activeRead: ReturnType<typeof reader.read> | undefined;
  let deadlineTimer: ReturnType<typeof setTimeout> | undefined;
  const deadline = new Promise<never>((_resolve, reject) => {
    deadlineTimer = setTimeout(() => {
      deadlineExpired = true;
      reject(timedOut());
    }, deadlineMs);
  });

View on GitHub (pinned to 2b7df46e8a)

Solutions

  1. Shrink the client payload: trim diagnostic fields, drop transcripts/screenshots, or raise the server limit if legitimately needed
  2. Split the diagnostics into multiple requests each under AGENT_DIAGNOSTICS_MAX_REQUEST_BYTES
  3. Send with Transfer-Encoding: chunked only if the streamed size is actually under the cap — the streaming reader enforces the same limit
  4. Compress the payload (gzip) and decompress server-side if the endpoint supports it

Example fix

// before
fetch(url, { method: "POST", body: JSON.stringify(allDiagnostics) }) // Content-Length > cap
// after
const body = JSON.stringify(essentialDiagnostics);
if (new Blob([body]).size <= AGENT_DIAGNOSTICS_MAX_REQUEST_BYTES) {
  fetch(url, { method: "POST", body });
} else {
  await uploadInChunks(essentialDiagnostics);
}
Defensive patterns

Strategy: validation

Validate before calling

const bytes = new Blob([JSON.stringify(diagnostics)]).size;
if (bytes > AGENT_DIAGNOSTICS_MAX_REQUEST_BYTES) {
  throw new Error(`payload ${bytes}B exceeds limit ${AGENT_DIAGNOSTICS_MAX_REQUEST_BYTES}B`);
}

Type guard

null

Try / catch

try {
  await submitDiagnostics(diagnostics);
} catch (e) {
  if (e instanceof ApiError && e.code === "agent_diagnostics_request_too_large") {
    await submitDiagnostics(truncateDiagnostics(diagnostics));
  } else throw e;
}

Prevention

When it happens

Trigger: Client POSTs (or PUTs) to the agent diagnostics endpoint with a Content-Length header whose numeric value exceeds AGENT_DIAGNOSTICS_MAX_REQUEST_BYTES.

Common situations: Diagnostics collector accidentally embedding full session transcripts or base64 screenshots; batch tooling uploading aggregated diagnostics in one request; misconfigured client chunking that sends everything in a single call.

Related errors


AI-assisted analysis of different-ai/openwork@2b7df46e8a (2026-09-01). Data as JSON: /api/errors/0eeba6a0e7158be6. Report an issue: GitHub.