How to Use onDownloadProgress in Axios

The onDownloadProgress callback in Axios is a built-in configuration option that allows developers to track and handle the progress of incoming data streams during HTTP requests in real time. This article explains the primary function of onDownloadProgress, the data it exposes via progress events, and how to implement it effectively in web applications to calculate download percentages and update user interfaces.

What is the onDownloadProgress Callback?

The onDownloadProgress option is a function passed within the Axios request configuration object. It listens for download progress events dispatched by the browser's underlying XMLHttpRequest (XHR) API whenever a chunk of data is received from the server.

Its primary purpose is to provide visibility into large file transfers—such as images, videos, documents, or large JSON payloads—allowing applications to display loading indicators, progress bars, and transfer statistics to the user.

Structure of the Progress Event

When triggered, the onDownloadProgress callback receives a ProgressEvent (or an Axios-enhanced progress object in newer versions) containing metadata about the download:

Basic Implementation Example

To monitor download progress, attach the onDownloadProgress function to an Axios request:

import axios from 'axios';

axios.get('https://example.com/large-file.zip', {
  responseType: 'blob',
  onDownloadProgress: (progressEvent) => {
    if (progressEvent.total) {
      const percentage = Math.round((progressEvent.loaded * 100) / progressEvent.total);
      console.log(`Download Progress: ${percentage}%`);
    } else {
      console.log(`Downloaded ${progressEvent.loaded} bytes (total size unknown)`);
    }
  }
})
.then((response) => {
  console.log('Download complete:', response.data);
})
.catch((error) => {
  console.error('Download failed:', error);
});

Calculating Download Percentages

To calculate a percentage completion accurately, the server must supply the Content-Length header in its HTTP response.

  1. When Content-Length is present: Use the formula (loaded / total) * 100 to calculate progress and update UI elements like progress bars.
  2. When Content-Length is absent: Indeterminate progress indicators (such as spinners) should be used, while progressEvent.loaded can be displayed to indicate the total data received to that point.

Important Considerations