Lesson 3: AJAX
An Asynchronous call is when you can move from one task to another, before the current one finishes. Conversely, there is a Synchronous call, which is when you have to wait for one thing to execute before moving onto the next. A good way of remembering it is to think of it as a line at the bank. An example of an Asynchronous set-up at the bank would be if there were multiple lines and multiple tellers- in this way, there are many deposits, withdrawals, etc. that are being executed all at once. A Synchronous set-up would be if there were only one line and one teller- in this instance, one person must be taken care of before the next can be attended to- only one thing can be done at a time.
Okay, so now that that’s out there- why do we use AJAX? We use AJAX when we want to update a page without navigating away from it. And, in order to use AJAX, we have to make HTTP Requests.
To make HTTP Requests, we need to know what the HTTP Methods are as well as what the HTTP Status Codes are.
- GET- Requests data from a specified resource; it pulls from the resource
- POST- Submits data to be processed to a specified resource; it creates the resource
- DELETE- Deletes the specified resource; it removes the resource
HTTP Status Codes:
- 100-level: indicates that the request was received and understood, but nothing has happened yet. It is essentially saying: “We got the request. Hold on just a sec.”
- 200-level: indicates that the action requested by the client was received, understood, accepted, and processed successfully. “Here you go, the request was successful!”
- 300-level: indicates the client must take additional action to complete the request, often used for redirection. “Go away, you’re being redirected.”
- 400-level: the error seems to have been caused by the client. “Yikes, you messed up…”
- 500-level: the server failed to fulfill a valid request. “The server is messed up.”
To make an HTTP Request with AJAX, you need to use a method to call a function, or file, and handle the response upon a successful status code; and handle errors with an unsuccessful one.
Here is an example of an AJAX request:
In plain English, here is what each line is doing:
Line 1: Creates a new XMLHttpRequest object and assigns it to the variable
Line 3: Adds an event listener to
a (the object), that listens for
readystatechange and that listens to the response of an API call made with
function (r) is a callback function,
r being the captured event
Line 4: Gets the status of the event (
r); we put in a status of 200 because the desired response is a successful one
Line 5: If we get a successful response, it will be printed via the
Line 9: This is where we start to make the actual AJAX request!
a opens up a GET call to the GitHub users API. When
a.open runs, the event listener is triggered because the state change of
a is going to change, which is when we’ll get
r (the actual event object). Note: whenever you get an event object captured in an event listener, you do `whateveryoureventiscalled.target` to get the actual object that was captured by that event
Line 10: Sends the API call
*phew* That was a lot. But! There is a different way to make an AJAX request. There are libraries and APIs that can make an AJAX Request a wee bit cleaner. Fetch API (only in modern browsers) is a newer browser API that provides a more powerful and flexible feature set than XMLHttpRequests.
Here’s what using the fetch API looks like!
And here’s what the code is doing:
Line 1: Calls the fetch function on the URL
Line 2: After we get the response (from calling the fetch function on the URL), and the promise (more on promises in a bit) is fulfilled, we say ‘Hey, after these things are done, THEN …’
Line 3: This has the
Line 5: ‘After this is done, THEN…’ Whatever is returned in the first
.then (Line 3) is passed in as the parameter to the next
.then on this line.
Line 6: Prints
j (in this case, in the console),
j is the result of the previous function
This way of doing it is so much shorter! The
.thens are a bit confusing, so let me provide a bit more information. First, it’s good to know that the
then calls are very similar to callbacks, but they’re used in something called promises.
Promises have 3 different states:
- Pending: Incomplete; its still being worked on
- Fulfilled: Complete
- Rejected: Failed
Typically, you construct a promise object with functions built in that resolve it (a.k.a. make it hit the fulfilled state); or reject it (a.k.a. make it hit the failed state). Also, you can daisy-chain fulfilled promises with the
.thenfunction. In our example, the fetch API handles the construction phase of promises.
NB: Fetch defaults to making GET requests (like we’re doing), but you can set it up to make POST requests, too.
Back to the example for a second: once we construct our GET request, this creates a promise that is pending. While this promise is pending, we call the first
then, and when that promise is resolved, the function inside the
thenwill be called. Then, the result of the first function is passed in as the variable
r, which is a response object.
A response object is very specific to fetch and had specific features, such as:
- Status- which will give an HTTP status code
- A URL property, and several others…check out more on response objects here.
Here, at long last, is the result in the console:
Next up, JSON!