Building Your Learning Module...
Getting things ready for you!
Find videos you like?
Save to resource drawer for future reference!
AJAX (Asynchronous JavaScript And XML) is a technique for making HTTP requests without reloading the page. It uses XMLHttpRequest (XHR) to communicate with servers asynchronously, enabling dynamic content updates and better user experience.
fetch() instead.XMLHttpRequest goes through several states during a request:
// 1. Create XMLHttpRequest object
const xhr = new XMLHttpRequest();
// 2. Configure: GET request to URL
xhr.open('GET', 'https://api.example.com/data');
// 3. Set up callback for when response arrives
xhr.onload = function() {
if (xhr.status === 200) {
const data = JSON.parse(xhr.responseText);
console.log(data);
} else {
console.error('Error:', xhr.status);
}
};
// 4. Handle network errors
xhr.onerror = function() {
console.error('Network error');
};
// 5. Send the request
xhr.send();Explanation:
open() - Configure method and URLonload - Fires when request completes successfullyonerror - Fires on network errorssend() - Initiates the requestconst xhr = new XMLHttpRequest();
xhr.open('POST', 'https://api.example.com/users');
// Set Content-Type header for JSON
xhr.setRequestHeader('Content-Type', 'application/json');
xhr.onload = function() {
if (xhr.status === 201) {
console.log('Created:', JSON.parse(xhr.responseText));
}
};
// Send JSON data
const data = { name: 'John', email: 'john@example.com' };
xhr.send(JSON.stringify(data));const xhr = new XMLHttpRequest();
xhr.open('POST', 'https://api.example.com/upload');
const formData = new FormData();
formData.append('username', 'john_doe');
formData.append('file', fileInput.files[0]);
// No need to set Content-Type - automatically set for FormData
xhr.send(formData);Note: When sending FormData, don't set Content-Type header - the browser sets it automatically with the correct boundary.
onload - Request completedonerror - Network erroronabort - Request abortedontimeout - Request timed outonprogress - Progress updatesstatus - HTTP status codestatusText - Status messageresponseText - Response as textresponseXML - Response as XMLreadyState - Current stateconst xhr = new XMLHttpRequest();
// Track upload progress
xhr.upload.onprogress = function(event) {
if (event.lengthComputable) {
const percentComplete = (event.loaded / event.total) * 100;
console.log(`Upload: ${percentComplete.toFixed(2)}%`);
}
};
// Track download progress
xhr.onprogress = function(event) {
if (event.lengthComputable) {
const percentComplete = (event.loaded / event.total) * 100;
console.log(`Download: ${percentComplete.toFixed(2)}%`);
}
};const xhr = new XMLHttpRequest();
xhr.open('GET', 'https://api.example.com/data');
// Set timeout to 5 seconds
xhr.timeout = 5000;
xhr.ontimeout = function() {
console.error('Request timed out');
};
xhr.send();const xhr = new XMLHttpRequest();
xhr.open('GET', 'https://api.example.com/data');
xhr.onabort = function() {
console.log('Request aborted');
};
xhr.send();
// Cancel the request
xhr.abort();const xhr = new XMLHttpRequest();
xhr.open('GET', 'https://api.example.com/data');
// Set custom headers
xhr.setRequestHeader('Authorization', 'Bearer token123');
xhr.setRequestHeader('X-Custom-Header', 'value');
// Send credentials (cookies)
xhr.withCredentials = true;
xhr.send();| Feature | XMLHttpRequest | Fetch API |
|---|---|---|
| Promise-based | No (callbacks) | Yes ✅ |
| Async/Await support | No | Yes ✅ |
| Syntax | Verbose | Clean ✅ |
| Progress events | Yes ✅ | Limited |
| Browser support | All browsers ✅ | Modern browsers ✅ |
| Recommended | Legacy only | Yes ✅ |
function fetchWeatherData(city) {
const xhr = new XMLHttpRequest();
const statusDiv = document.getElementById('status');
const weatherDiv = document.getElementById('weather');
// Configure request
xhr.open('GET',
`https://api.weather.com/data?city=${city}`,
true
);
// Track upload progress
xhr.upload.addEventListener('progress', (e) => {
if (e.lengthComputable) {
const percent = (e.loaded / e.total) * 100;
statusDiv.innerHTML =
`Uploading: ${percent.toFixed(0)}%`;
}
});
// Track download progress
xhr.addEventListener('progress', (e) => {
if (e.lengthComputable) {
const percent = (e.loaded / e.total) * 100;
statusDiv.innerHTML =
`Loading: ${percent.toFixed(0)}%`;
}
});
// Handle response
xhr.onload = function() {
if (xhr.status === 200) {
const data = JSON.parse(xhr.responseText);
weatherDiv.innerHTML = `
<div class="weather-card">
<h2>${data.city}</h2>
<p>Temperature: ${data.temp}°C</p>
<p>Condition: ${data.condition}</p>
</div>
`;
statusDiv.innerHTML = 'Loaded!';
} else {
weatherDiv.innerHTML = `Error: ${xhr.status}`;
}
};
// Handle errors
xhr.onerror = function() {
weatherDiv.innerHTML = 'Network error occurred';
};
// Send request
xhr.send();
}
// Call the function
fetchWeatherData('London');📤 Status: Uploading: 45%
📥 Status: Loading: 78%
✓ Status: Loaded!
Temperature: 18°C
Condition: Partly Cloudy
❌ Error state (if API fails):
"Error: 404" or "Network error occurred"
✅ Progress tracking (upload/download)
✅ Multiple event handlers
✅ Success rendering
✅ Error handling
Older, callback-based approach
Good for upload/download progress
0-4 states tracking request lifecycle
Modern alternative for new code