How curl handles chunked transfer encoding uploads

This article explains how the curl command-line tool manages chunked transfer encoding during data uploads. It covers when curl automatically applies chunked encoding, how the underlying data transfer mechanism works, and how to force or disable this behavior during HTTP requests.

When curl Uses Chunked Transfer Encoding

By default, when you upload a file using curl with the -T (or --upload-file) option, curl attempts to determine the file size beforehand. If it can determine the size, it sends a standard Content-Length header. However, curl automatically switches to chunked transfer encoding under the following conditions:

How the Data is Transmitted

When chunked transfer encoding is active, curl does not send the entire payload as a single continuous block. Instead, it breaks the upload stream into a series of chunks.

Each chunk is formatted with: 1. The size of the chunk represented in hexadecimal format. 2. A carriage return and line feed (CRLF). 3. The actual chunk data. 4. Another CRLF.

Once the entire stream has been read and sent, curl transmits a final chunk of size zero (0 followed by CRLF) to signal to the receiving server that the upload is complete.

Forcing or Disabling Chunked Uploads

If you are uploading a static file but want to force chunked encoding—often done to test how a receiving server handles chunked requests—you can manually add the header to your command:

curl -H "Transfer-Encoding: chunked" -T localfile.txt http://example.com/upload

Conversely, if a target server does not support chunked encoding and rejects the upload, you must avoid streaming. You can resolve this by uploading a physical file directly so curl can calculate the Content-Length before transmitting, or by buffering your stream to a temporary local file before initiating the upload.