different-ai/openwork · error · DiagnosticFailure

The Den container could not complete the outbound connection

Error message

The Den container could not complete the outbound connection.

What it means

sendRequest in egress-diagnostics.ts issues the synthetic outbound diagnostic request from the Den container via fetchImpl. If fetch throws (connection refused/reset, DNS failure, TLS error, timeout), networkFailure maps the underlying cause code (ENOTFOUND, CERT/SSL, ABORT_ERR, ETIMEDOUT, etc.) to a DiagnosticFailure; the generic fallback message 'The Den container could not complete the outbound connection.' is used when no known cause code is found. This is a connectivity-category failure owned by the network administrator.

Source

Thrown at ee/apps/den-api/src/egress-diagnostics.ts:287

  category: EgressDiagnosticCategory
  evidence: StepEvidence
  expectedStatuses: readonly number[]
  fetchImpl: DiagnosticFetch
  init?: RequestInit
  runId: string
  step: string
  timeoutMs: number
  url: string
}): Promise<Response> {
  let response: Response
  try {
    response = await input.fetchImpl(input.url, {
      ...input.init,
      headers: requestHeaders(input.runId, input.step, input.init?.headers),
      signal: input.init?.signal ?? AbortSignal.timeout(input.timeoutMs),
    })
  } catch (error) {
    throw networkFailure(error)
  }
  input.evidence.httpStatuses.push(response.status)
  const diagnosticId = response.headers.get(EGRESS_DIAGNOSTIC_ID_HEADER) ?? ""
  if (diagnosticIdPattern.test(diagnosticId)) input.evidence.diagnosticIds.push(diagnosticId)
  if (!input.expectedStatuses.includes(response.status)) throw httpFailure(response.status, input.category)
  if (!diagnosticIdPattern.test(diagnosticId)) {
    throw new DiagnosticFailure({
      action: "Ask the network administrator to inspect whether a proxy, gateway, or service mesh replaced the response or removed x-openwork-diagnostic-id.",
      category: input.category,
      code: "diagnostic_reference_missing",
      message: "A response arrived, but it did not contain proof that it came from the Diagnostics application.",
      owner: "network-administrator",
    })
  }
  return response
}

function protocolFailure(category: EgressDiagnosticCategory, code: string, message: string): DiagnosticFailure {

View on GitHub (pinned to 2b7df46e8a)

Solutions

  1. Ask the network administrator to inspect Den container egress rules, proxy configuration, service-mesh policy, and connection resets (per the error's action).
  2. Verify the diagnostic endpoint hostname/URL configured for the egress diagnostic is correct.
  3. Check proxy env vars (HTTP_PROXY/HTTPS_PROXY/NO_PROXY) are set correctly for the Den runtime.
  4. Retry the diagnostic — transient resets may pass; persistent failure indicates a real network block.
  5. Run the specific typed diagnostics (DNS/TLS variants) to narrow whether it is name resolution, TLS, or routing.
Defensive patterns

Strategy: retry

Validate before calling

// preflight: resolve and TCP-connect before running the diagnostic
const addr = await dns.promises.lookup(diagnosticHost).catch(() => null)
if (!addr) throw new Error('diagnostic hostname unresolvable from Den container')

Type guard

function isEgressDiagnosticFailure(e: unknown): e is { category: 'connectivity'; code: string } {
  return typeof e === 'object' && e !== null && (e as { category?: string }).category === 'connectivity'
}

Try / catch

try {
  result = await sendRequest(input)
} catch (error) {
  if (isEgressDiagnosticFailure(error)) {
    const code = error.code // fetch_failed | ENOTFOUND | ABORT_ERR | CERT_* ...
    if (code === 'ABORT_ERR' || code === 'ETIMEDOUT') retryWithBackoff()
    else escalateToNetworkAdmin(code)
  } else throw error
}

Prevention

When it happens

Trigger: Running an egress diagnostic (runEgressDiagnostic and its first/second/protectedResponse/tasks variants) when the outbound fetch itself throws before an HTTP status is received — connection refused, reset, TLS handshake failure, timeout, or unresolvable hostname with no recognized cause code.

Common situations: Den container with no egress route; NetworkPolicy or service mesh blocking outbound traffic; misconfigured proxy env vars; connection reset by an inspection firewall that doesn't map to a standard errno; wrong diagnostic endpoint URL.

Related errors


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