can1357/oh-my-pi · error · AIError.ProviderResponseError

Devin API error: response body is empty

Error message

Devin API error: response body is empty

What it means

After a successful (2xx) HTTP response, streamDevin expects a readable response body to consume the event stream. If response.body is null/undefined it throws ProviderResponseError with kind "empty-body", since a status-only response carries no stream data the provider can parse.

Source

Thrown at packages/ai/src/providers/devin.ts:220

					"connect-content-encoding": "gzip",
					"accept-encoding": "identity",
					"user-agent": "connect-go/1.18.1 (go1.26.3)",
					"connect-accept-encoding": "gzip",
					...(options?.headers ?? {}),
				},
				body: frame,
				signal: options?.signal,
			});

			if (!response.ok) {
				const text = await response.text();
				throw new AIError.DevinApiError(
					`Devin API error ${response.status} ${response.statusText}: ${text}`,
					response.status,
				);
			}
			if (!response.body) {
				throw new AIError.ProviderResponseError("Devin API error: response body is empty", {
					provider: model.provider,
					kind: "empty-body",
				});
			}
			const body = response.body;

			stream.push({ type: "start", partial: output });

			const reader = body.getReader();
			let pending = Buffer.alloc(0);

			for (;;) {
				const { done, value } = await reader.read();
				if (value && value.length > 0) {
					// Steady state drains fully per chunk; view the fresh reader chunk
					// instead of copying it through Buffer.concat (see aws-eventstream.ts).
					pending =
						pending.length === 0

View on GitHub (pinned to 9690622007)

Solutions

  1. Retry the request — likely a transient server-side anomaly.
  2. Ensure the fetch implementation passed to the provider supports streaming response bodies (no body-nulling polyfills).
  3. Check intermediaries (proxies, gateways) for body-stripping behavior on streaming responses.
  4. If persistent, capture status/headers and report to Devin support; it indicates a server-side empty response.

Example fix

null
Defensive patterns

Strategy: retry

Validate before calling

null

Type guard

null

Try / catch

try {
  await streamDevin(model, ctx, options);
} catch (err) {
  if (err instanceof AIError.ProviderResponseError && err.kind === "empty-body") {
    // transient empty 2xx: retry with backoff
    await Bun.sleep(retryDelayMs);
    return streamDevin(model, ctx, options);
  }
  throw err;
}

Prevention

When it happens

Trigger: Devin API returns 2xx but the fetch implementation provides no body — degenerate server response, an intermediary stripping the body, or a transport/polyfill that nulls bodies on certain statuses or configurations.

Common situations: Corporate proxies or gateways swallowing response bodies; custom fetch implementations that mishandle streaming responses; Devin server-side anomaly returning an empty 200.

Related errors


AI-assisted analysis of can1357/oh-my-pi@9690622007 (2026-08-31). Data as JSON: /api/errors/395db54f076daa63. Report an issue: GitHub.