Multi-threaded file download for Linux
When a large file is downloaded from a single HTTP or FTP server with a regular tool such as curl or wget, a single TCP connection is opened and the file is downloaded sequentially. On a fast network this can be limited by the server's per-connection rate limit, by TCP slow start, or by round-trip latency. Parallel download utilities open several connections to the same source at once, each fetching a different byte range, and reassemble the result locally. This works only if the server accepts HTTP range requests (responding with HTTP 206 Partial Content); on servers that do, the result is often a noticeably faster transfer than a single-stream tool produces.
In this article "multi-threaded download" refers to this pattern of parallel connections, rather than to threading inside the download process itself.
This article covers two such utilities for Linux: Axel and aria2.
Axel
Axel is a lightweight command-line download tool. It opens multiple connections to a single source and downloads byte ranges in parallel. It supports HTTP, HTTPS, FTP, and FTPS, and can resume an interrupted download.
Installing Axel
On Debian and Ubuntu:
sudo apt install axel
On RHEL, CentOS Stream, AlmaLinux, and Rocky Linux, enable EPEL first:
sudo dnf install epel-release sudo dnf install axel
On Fedora:
sudo dnf install axel
Using Axel
A basic download:
axel https://nl.lg.introserv.eu/1000MB.test
The -a flag enables a compact progress indicator:
axel -a https://nl.lg.introserv.eu/1000MB.test
Limit the maximum download speed in bytes per second with -s (or --max-speed). For example, to cap the transfer at 500 KB/s:
axel --max-speed=512000 https://nl.lg.introserv.eu/1000MB.test
Save the file under a different name with -o:
axel -o gigabyte.test https://nl.lg.introserv.eu/1000MB.test
Set the number of parallel connections with -n:
axel -n 10 https://nl.lg.introserv.eu/1000MB.test
Resume a partially downloaded file with -c:
axel -c https://nl.lg.introserv.eu/1000MB.test
With -c, if a local file with the same name already exists, Axel continues from where it left off instead of starting over.
aria2
aria2 covers the same parallel-download use case as Axel and offers a broader set of features. It supports HTTP, HTTPS, FTP, SFTP, BitTorrent, and Metalink, and can fetch the same file from several sources at once. Like Axel, it splits a file into segments and downloads them in parallel.
Key features:
- configurable per-server connection count, split size, and overall concurrency
- automatic resume of interrupted downloads
- checksum-based integrity verification
- support for HTTPS and FTPS
- native BitTorrent and Metalink clients
Installing aria2
On Debian and Ubuntu:
sudo apt install aria2
On RHEL, CentOS Stream, AlmaLinux, and Rocky Linux:
sudo dnf install aria2
On Fedora:
sudo dnf install aria2
Using aria2
A basic download:
aria2c https://nl.lg.introserv.eu/1000MB.test
Fetch the same file from two mirrors at once. aria2 combines the connections to both sources and reassembles the file locally:
aria2c "https://nl.lg.introserv.eu/1000MB.test" "https://uk.lg.introserv.eu/1000MB.test"
Mix HTTP and FTP sources, supplying FTP credentials:
aria2c --ftp-user=<USER> --ftp-passwd=<PASSWD> "ftp://<ftpserver_ip>/<file>" "https://uk.lg.introserv.eu/1000MB.test"
Open eight parallel connections to a single server, splitting the file into eight segments:
aria2c -x8 -s8 https://nl.lg.introserv.eu/1000MB.test
The -x flag (or --max-connection-per-server) caps the number of connections aria2 opens to one server (default 1). The -s flag (or --split) sets the maximum number of segments the file is divided into (default 5). For a single source, the effective number of parallel connections is the smaller of the two: -x8 -s5 opens 5 connections, -x5 -s8 also opens 5. To actually get 8 parallel connections to one server, both flags have to be raised, which is why they are usually set to the same value.
The -k flag (or --min-split-size) sets the smallest chunk into which the file is split. Smaller values allow more parallel segments at the cost of more overhead:
aria2c -x8 -s8 -k1M https://nl.lg.introserv.eu/1000MB.test
-x, -s, and -j solve different problems. -x controls the number of connections opened to one server when downloading one file. -s controls how many segments one file is split into. -j (or --max-concurrent-downloads) controls how many separate files aria2 downloads at the same time.
Download two files in parallel:
aria2c -j2 https://nl.lg.introserv.eu/1000MB.test https://uk.lg.introserv.eu/1000MB.test
Resume a partially downloaded file with -c:
aria2c -c https://nl.lg.introserv.eu/1000MB.test
When given a Metalink file, aria2 can pick mirrors automatically, verify the downloaded data against the checksums declared in the Metalink, and retry failed mirrors without manual intervention.
For repeated use, aria2 reads default options from ~/.aria2/aria2.conf if the file exists, so values such as max-connection-per-server and split can be set there once instead of being passed on every invocation.
Opening many parallel connections to a public mirror or CDN may violate the operator's usage policy and trigger rate limiting or temporary bans. For public sources, keep the connection count modest (4 to 8 is usually safe); use higher values only on infrastructure that is known to allow them
When parallel downloads help
Parallel downloads are most effective when the bottleneck is the server's per-connection rate limit or per-source throughput cap, not the local disk or the network link as a whole. On a fully saturated link, opening more connections does not increase total bandwidth; it just redistributes it. Some HTTP servers also reject range requests or limit the number of concurrent connections from one client, in which case a single-stream tool such as wget is just as fast as Axel or aria2.