Merged
Size
M
Change Breakdown
Bug Fix75%
Refactor20%
Performance5%
#28233fix(HTTP Request Node): Fix multipart/form-data file upload with binary streams

File uploads fixed in HTTP Request node

Multipart form-data file uploads should now complete successfully in production n8n deployments, where binary streams previously caused content-length calculation failures.

When n8n's HTTP Request node attempted to upload binary files via multipart form-data, the requests could fail silently or timeout in production — even though the same workflow worked fine in local development. This frustrating inconsistency had two root causes, both addressed in this fix.

First, the code used instanceof FormData to identify form data objects. In production npm installations, different packages can resolve separate copies of the form-data module, causing instanceof to return false even when the object is legitimately a FormData instance. When this check failed, the code would destroy the FormData by spreading it as a plain object and recreating it — losing all the stream data in the process. A new duck-type checking function now validates FormData instances by looking for the required getHeaders and append methods, with instanceof as a fast path for environments where it works.

Second, when appending binary streams to FormData, the file size wasn't being provided. The form-data package couldn't measure stream length on its own, causing content-length header calculation to fail silently. Servers that require this header would then reject or timeout the request. The fix retrieves file metadata to obtain the size and passes it as knownLength when appending streams.

These changes touch the core execution engine in packages/core and the HTTP Request node implementation in packages/nodes-base, ensuring consistent behavior across different installation methods.

View Original GitHub Description

Summary

Fixes multipart/form-data file uploads failing when binary data is stored in filesystem mode (the default for production n8n). Two root causes:

  1. instanceof FormData fails across packages — When packages/core and packages/nodes-base resolve separate copies of the form-data module (common with npm/npx installs), instanceof returns false. The code then destroys the FormData by spreading it as a plain object and re-creating it, losing all stream data. Fixed by adding isFormDataInstance() — a duck-type check with an instanceof fast path. This is the root cause for the differing behavior between npx n8n and a local dev build: pnpm deduplicates to a single shared copy of form-data, so instanceof succeeds locally.

  2. Missing knownLength for binary streamsgetBinaryStream() returns a Readable stream whose length the form-data package cannot measure, causing content-length calculation to fail silently. Servers that require content-length then reject or time out the request. Fixed by calling getBinaryMetadata() to obtain the file size and passing it as knownLength when appending streams to FormData.

How to test

  1. Create an empty folder and initialise it with npm init -y
  2. Install n8n: npm install --save n8n and add a run script "n8n": "n8n" to package.json
  3. Start n8n: npm run n8n (reproduces the same dependency layout as npx n8n)
  4. Create a workflow: Manual Trigger → Read Binary File → HTTP Request (POST, body type Form-Data, with an n8n Binary File parameter)
  5. Verify the upload completes without "Unable to calculate form data length" errors and that content-length is set correctly — use RequestBin or a similar tool to inspect the incoming request headers and boundary values

Related Linear tickets, GitHub issues, and community forum posts

Review / Merge checklist

  • PR title and summary are descriptive. (conventions)
  • Docs updated or follow-up ticket created.
  • Tests included.
  • PR Labeled with release/backport (if the PR is an urgent fix that needs to be backported)
© 2026 · via Gitpulse