📊 AJAX – Monitoring Request Progress: Track Uploads and Downloads in Real-Time
🧲 Introduction – Why Monitor AJAX Request Progress?
AJAX enables background communication between the browser and server, but by default, users have no idea what’s happening. Monitoring progress is essential for actions like:
- Uploading files
- Downloading large JSON/XML payloads
- Displaying loading indicators or progress bars
- Enhancing UX with feedback during long-running operations
By tracking progress with the XMLHttpRequest object, you can inform users, prevent duplicate actions, and make your app feel responsive.
🎯 In this guide, you’ll learn:
- How to use the
progressevent in AJAX - Track both upload and download operations
- Build a progress bar with real-time feedback
- Handle stalled, failed, and completed transfers gracefully
🛠️ XMLHttpRequest – Key Events for Monitoring
const xhr = new XMLHttpRequest();
xhr.onprogress = function (e) {
if (e.lengthComputable) {
const percent = (e.loaded / e.total) * 100;
console.log(`Download: ${percent.toFixed(0)}%`);
}
};
xhr.upload.onprogress = function (e) {
if (e.lengthComputable) {
const percent = (e.loaded / e.total) * 100;
console.log(`Upload: ${percent.toFixed(0)}%`);
}
};
✅ xhr.onprogress monitors download progress
✅ xhr.upload.onprogress monitors upload progress
📤 Upload Progress Example – With HTML Progress Bar
✅ HTML Form:
<form id="uploadForm">
<input type="file" name="file" required />
<progress id="uploadProgress" value="0" max="100"></progress>
<button type="submit">Upload</button>
</form>
<div id="status"></div>
✅ JavaScript:
document.getElementById("uploadForm").addEventListener("submit", function (e) {
e.preventDefault();
const file = this.file.files[0];
const formData = new FormData();
formData.append("file", file);
const xhr = new XMLHttpRequest();
xhr.open("POST", "upload.php");
xhr.upload.onprogress = function (e) {
if (e.lengthComputable) {
const percent = (e.loaded / e.total) * 100;
document.getElementById("uploadProgress").value = percent;
}
};
xhr.onload = function () {
document.getElementById("status").innerText = "Upload complete!";
};
xhr.onerror = function () {
document.getElementById("status").innerText = "Upload failed!";
};
xhr.send(formData);
});
✅ The <progress> element updates in real-time as the upload progresses.
📥 Download Progress Example – Large JSON or File
const xhr = new XMLHttpRequest();
xhr.open("GET", "large-data.json", true);
xhr.onprogress = function (e) {
if (e.lengthComputable) {
console.log(`Downloaded ${(e.loaded / e.total * 100).toFixed(1)}%`);
} else {
console.log(`Downloaded ${e.loaded} bytes`);
}
};
xhr.onload = function () {
console.log("Download complete!");
};
xhr.send();
✅ Even if lengthComputable is false, you can still track bytes loaded.
📈 Visualizing Progress – With CSS Bar
<div id="progressContainer">
<div id="progressBar"></div>
</div>
#progressContainer {
width: 100%;
background: #eee;
}
#progressBar {
width: 0%;
height: 20px;
background: #4caf50;
}
xhr.onprogress = function (e) {
if (e.lengthComputable) {
const percent = (e.loaded / e.total) * 100;
document.getElementById("progressBar").style.width = percent + "%";
}
};
✅ Add CSS animations for smooth transitions.
🚦 Handling Progress States
| Event | Description |
|---|---|
onloadstart | Request starts |
onprogress | Ongoing transfer |
onload | Request completed successfully |
onerror | Request failed |
onabort | Manually cancelled |
ontimeout | Timed out (requires timeout set) |
✅ Best Practices
| Tip | Why It Matters |
|---|---|
Always check lengthComputable | Not all responses provide total size |
| Provide fallback text like “Loading…” | Improves accessibility and clarity |
Use xhr.upload.onprogress for uploads | Downloads use xhr.onprogress |
| Clean up listeners after complete | Prevents memory leaks |
Add retries on onerror | Improves robustness for unstable networks |
📌 Summary – Recap & Takeaways
Monitoring request progress in AJAX ensures a responsive UI, informs the user, and improves perceived performance. It’s especially useful for file uploads, large downloads, or slow network conditions.
🔍 Key Takeaways:
- Use
xhr.upload.onprogressfor tracking uploads - Use
xhr.onprogressfor tracking downloads - Combine with
<progress>or animated bars for visuals - Handle errors, timeouts, and aborts for better UX
⚙️ Next Steps:
- Add cancel upload feature with
xhr.abort() - Combine with drag-and-drop uploaders
- Use JavaScript libraries like Axios with progress support
❓ FAQs – Monitoring AJAX Progress
❓ What’s the difference between onprogress and upload.onprogress?
✅ onprogress tracks download progress, while upload.onprogress tracks upload progress.
❓ How do I monitor progress using fetch()?
❌ You can’t directly monitor upload progress with fetch() yet. Use XMLHttpRequest for uploads.
❓ Why does lengthComputable return false?
✅ The server may not include a Content-Length header. In such cases, only loaded bytes are available.
❓ Can I cancel an AJAX request midway?
✅ Yes. Use xhr.abort() and handle it in onabort.
❓ Is it safe to show percentage to users?
✅ Yes. Just ensure to handle non-computable lengths gracefully (e.g., show spinner).
Share Now :
