How to Make AJAX Calls with JavaScript
Published June 13, 2024 at 8:04 pm
Are you finding it challenging to make AJAX calls with JavaScript?
Look no further; this detailed guide will walk you through making AJAX calls using pure JavaScript.
Whether you’re trying to fetch data from a server, update part of a web page without reloading, or interact dynamically with a backend service, AJAX (Asynchronous JavaScript and XML) is your best friend.
This article will cover everything from the basics to advanced techniques, ensuring you can master AJAX calls with JavaScript.
TL;DR: How Do I Make AJAX Calls with JavaScript?
Use the XMLHttpRequest object to make asynchronous requests to a server and perform actions based on the response.
Here’s a quick example:
var xhr = new XMLHttpRequest(); // creates a new XMLHttpRequest object
xhr.open("GET", "https://api.example.com/data", true); // initializes a GET request
xhr.onreadystatechange = function() {
if (xhr.readyState === 4 && xhr.status === 200) { // checks if the request is complete and successful
console.log(xhr.responseText); // logs the response from the server
}
};
xhr.send(); // sends the request
What is AJAX?
AJAX stands for Asynchronous JavaScript and XML.
It allows you to send and receive data asynchronously without reloading the web page.
This means you can update parts of a web page dynamically without a full page reload.
Setting Up an AJAX Call
The XMLHttpRequest object is used to make AJAX calls in JavaScript.
Here is a step-by-step example of making a simple GET request:
var xhr = new XMLHttpRequest(); // creates a new XMLHttpRequest object
xhr.open("GET", "https://api.example.com/data", true); // initializes a GET request
xhr.onreadystatechange = function() {
if (xhr.readyState === 4 && xhr.status === 200) { // checks if the request is complete and successful
console.log(xhr.responseText); // logs the response from the server
}
};
xhr.send(); // sends the request
In this example, we:
- Create a new
XMLHttpRequestobject. - Initialize a GET request to “https://api.example.com/data”.
- Handle the response using the
onreadystatechangeevent listener. - Send the request to the server.
Handling Different HTTP Methods
AJAX calls support various HTTP methods such as GET, POST, PUT, and DELETE.
Here’s an example of how to make a POST request:
var xhr = new XMLHttpRequest();
xhr.open("POST", "https://api.example.com/data", true);
xhr.setRequestHeader("Content-Type", "application/json;charset=UTF-8"); // sets the request header
xhr.onreadystatechange = function() {
if (xhr.readyState === 4 && xhr.status === 200) {
console.log(xhr.responseText);
}
};
var data = JSON.stringify({ name: "John", age: 30 }); // converts data to JSON string
xhr.send(data); // sends the request with data
In this example, we:
- Initialized a POST request to “https://api.example.com/data”.
- Set the request header to “application/json”.
- Converted the data to a JSON string and sent it with the request.
Handling Errors
It’s crucial to handle errors in AJAX calls gracefully to improve the user experience.
Here’s how to handle errors in an AJAX call:
var xhr = new XMLHttpRequest();
xhr.open("GET", "https://api.example.com/data", true);
xhr.onreadystatechange = function() {
if (xhr.readyState === 4) {
if (xhr.status === 200) {
console.log(xhr.responseText);
} else {
console.error("Error: " + xhr.status); // log the error status
}
}
};
xhr.send();
In this example, we check the xhr.status value to determine if the request was successful.
If the status is not 200 (OK), we log the error status to the console.
Modern Approach: Fetch API
While the XMLHttpRequest object is still widely used, the Fetch API is a modern, promise-based alternative.
Here’s an example of making a GET request using the Fetch API:
fetch("https://api.example.com/data")
.then(response => response.json()) // parses the JSON response
.then(data => console.log(data)) // logs the parsed data
.catch(error => console.error("Error:", error)); // handles any errors
In this example, we:
- Used the
fetchfunction to make a GET request. - Parsed the JSON response.
- Logged the parsed data to the console.
- Handled any errors that occurred during the fetch.
Dealing with JSON Responses
AJAX calls often interact with JSON data.
Here’s an example of how to handle JSON responses:
var xhr = new XMLHttpRequest();
xhr.open("GET", "https://api.example.com/data", true);
xhr.onreadystatechange = function() {
if (xhr.readyState === 4 && xhr.status === 200) {
var jsonResponse = JSON.parse(xhr.responseText); // parse the JSON response
console.log(jsonResponse); // log the parsed JSON
}
};
xhr.send();
In this example, we parse the JSON response using JSON.parse and then log the parsed JSON object.
Using the Fetch API, the same can be achieved with:
fetch("https://api.example.com/data")
.then(response => response.json()) // parses the JSON response
.then(data => console.log(data)) // logs the parsed data
.catch(error => console.error("Error:", error)); // handles any errors
Handling CORS (Cross-Origin Resource Sharing)
Cross-Origin Resource Sharing (CORS) is a security feature implemented by browsers.
It restricts web pages from making requests to a different domain than the one that served the web page.
To enable CORS, the server needs to include specific headers in the response:
Access-Control-Allow-Origin: *
Access-Control-Allow-Methods: GET, POST, PUT, DELETE
Access-Control-Allow-Headers: Content-Type
These headers allow web applications to make requests across different origins.
AJAX and Promises
By using JavaScript promises with AJAX, you can write cleaner and more manageable asynchronous code.
Here’s how to wrap an AJAX call in a promise:
function ajaxPromise(url) {
return new Promise((resolve, reject) => {
var xhr = new XMLHttpRequest();
xhr.open("GET", url, true);
xhr.onreadystatechange = function() {
if (xhr.readyState === 4) {
if (xhr.status === 200) {
resolve(xhr.responseText); // resolves the promise with response text
} else {
reject("Error: " + xhr.status); // rejects the promise with error status
}
}
};
xhr.send();
});
}
ajaxPromise("https://api.example.com/data")
.then(response => console.log(response))
.catch(error => console.error(error));
In this example, we:
- Defined a function
ajaxPromisethat returns a promise. - Used the promise to make an AJAX call and handle the response.
Debugging AJAX Calls
Debugging AJAX calls is crucial for identifying issues in your application.
Use console.log to log the state and status of the requests.
The Network tab in browser developer tools provides details of all network requests.
FAQs
How can I make synchronous AJAX calls?
Although not recommended, you can make synchronous AJAX calls by setting the third parameter of xhr.open to false.
Can I use jQuery for AJAX calls?
Yes, jQuery simplifies AJAX calls with methods like $.ajax, $.get, and $.post.
Why do I get a CORS error?
CORS errors occur when the server does not include the necessary CORS headers in the response.
What is the difference between xhr.readyState and xhr.status?
xhr.readyState represents the state of the request.
xhr.status represents the HTTP status code returned by the server.
Can I send data with a GET request?
Data can be sent with a GET request by appending query parameters to the URL.
What are some alternatives to XMLHttpRequest and Fetch API?
Other alternatives include libraries like Axios and jQuery for making AJAX calls.
How can I handle timeouts in AJAX calls?
Set the xhr.timeout property and use the ontimeout event to handle timeouts.
What does the onreadystatechange event do?
This event is triggered whenever the ready state of the XMLHttpRequest changes.
When should I use the Fetch API over the XMLHttpRequest object?
Fetch API should be used for its modern syntax and promise-based handling of asynchronous operations.
Another Example: Fetch API POST Request
We’ve covered making GET requests using Fetch API, but what if you need to send data to the server?
Here’s how to make a POST request with Fetch API:
fetch("https://api.example.com/data", {
method: "POST", // specifies the request method
headers: {
"Content-Type": "application/json" // sets the content type
},
body: JSON.stringify({ name: "John", age: 30 }) // converts data to JSON
})
.then(response => response.json()) // parses the JSON response
.then(data => console.log(data)) // logs the response data
.catch(error => console.error("Error:", error)); // handles errors
In this example, we:
- Specify the request method as “POST”.
- Set the request headers to include “application/json” content type.
- Convert the data to JSON format with
JSON.stringify. - Handle the response and potential errors using promises.
Async/Await with Fetch API
Using async and await can make your asynchronous code easier to read and manage.
Here’s an example of how to use async/await with Fetch API:
async function fetchData() {
try {
let response = await fetch("https://api.example.com/data"); // waits for the fetch request to complete
let data = await response.json(); // waits for the response to be parsed
console.log(data); // logs the parsed data
} catch (error) {
console.error("Error:", error); // handles errors
}
}
fetchData();
In this example, we:
- Use the
asynckeyword to define an asynchronous function. - Use
awaitto wait for the fetch request and response parsing. - Handle errors with a
try...catchblock.
Sending Form Data using AJAX
You might need to send HTML form data using AJAX.
Here’s how to do it with XMLHttpRequest:
var form = document.querySelector("form");
form.addEventListener("submit", function(event) {
event.preventDefault(); // prevents the default form submission
var xhr = new XMLHttpRequest();
xhr.open("POST", "https://api.example.com/data", true);
xhr.setRequestHeader("Content-Type", "application/x-www-form-urlencoded");
xhr.onreadystatechange = function() {
if (xhr.readyState === 4 && xhr.status === 200) {
console.log(xhr.responseText); // logs the response on success
}
};
var formData = new FormData(form); // collects form data
xhr.send(new URLSearchParams(formData).toString()); // sends the form data
});
In this example, we:
- Add an event listener to the form submission event.
- Create a new
XMLHttpRequestobject and set its method to POST. - Set the request header to encode form data properly.
- Convert form data to a URL-encoded string using
URLSearchParams. - Send the form data with the request.
Real-Time Updates with AJAX
AJAX can also be used to update web page content in real-time.
Here’s a simple example of real-time updates:
function updateContent() {
var xhr = new XMLHttpRequest();
xhr.open("GET", "https://api.example.com/data", true);
xhr.onreadystatechange = function() {
if (xhr.readyState === 4 && xhr.status === 200) {
document.getElementById("content").innerHTML = xhr.responseText; // updates the content
}
};
xhr.send();
}
// Call updateContent function every 5 seconds
setInterval(updateContent, 5000);
In this example, we:
- Define a function to make an AJAX call and update the web page content.
- Use
setIntervalto call this function every 5 seconds.
AJAX Polling vs WebSockets
For real-time updates, you can use either AJAX polling or WebSockets.
AJAX Polling:
- Repeatedly makes requests to the server at regular intervals.
- Simple to implement but can be inefficient due to constant requests.
WebSockets:
- Establishes a continuous connection to the server.
- More efficient for real-time communication but more complex to implement.
Implementing WebSockets for Real-Time Communication
Instead of using AJAX polling, WebSockets provide a more efficient way to handle real-time updates.
Here’s how to implement WebSockets in JavaScript:
var ws = new WebSocket("wss://example.com/socket"); // creates a new WebSocket connection
ws.onopen = function() {
console.log("WebSocket connection opened."); // logs when the connection is opened
};
ws.onmessage = function(event) {
var message = JSON.parse(event.data); // parses the incoming message
console.log("Received message:", message); // logs the received message
};
ws.onclose = function() {
console.log("WebSocket connection closed."); // logs when the connection is closed
};
ws.onerror = function(error) {
console.error("WebSocket error:", error); // logs any errors
};
In this example, we:
- Create a new WebSocket connection to the server.
- Handle events such as
onopen,onmessage,onclose, andonerror. - Parse and log incoming messages from the server.
FAQs
How can I send custom headers in an AJAX request?
You can use the setRequestHeader method of the XMLHttpRequest object to set custom headers.
Is it possible to cancel an ongoing AJAX request?
Yes, you can call the abort method on the XMLHttpRequest object to cancel the request.
How do I handle large JSON responses efficiently?
You can parse the JSON response and process it in chunks to handle large data efficiently.
What are some security considerations when making AJAX calls?
Ensure secure transmission with HTTPS, validate server responses, and avoid exposing sensitive data.
Can I upload files using AJAX?
Yes, you can use the FormData object to upload files with AJAX.
How do I debug AJAX calls that aren’t working?
Use browser developer tools to inspect network requests and responses, and log relevant data with console.log.
What should I do if the AJAX request times out?
Set the timeout property on the XMLHttpRequest object and handle the ontimeout event.
How do I handle HTTP status codes other than 200?
Check the xhr.status value and implement custom error handling logic.
Can AJAX calls be cached?
Yes, browsers can cache AJAX responses. Use HTTP headers to control caching behavior.
Why should I use the Fetch API over XMLHttpRequest?
Fetch API provides a modern, promise-based way to make HTTP requests that is easier to use and more readable.
Shop more on Amazon