Quick Async One-Liners With Async Immediately Invoked Function Expressions

February 26, 2021

0

Illustration by my buddy Loor Nicolas


THE PROBLEM

We have to create a script that will do a GET request to the Chuck Norris jokes API and append that content to a div with the id #chucky.

A quick and easy way to do this would be chaining .then methods on the promises returned by fetch and .json :

fetch('https://api.chucknorris.io/jokes/random')
    .then(response => response.json())
    .then(({ value }) => {
        document.querySelector('#chucky').textContent = value
    })

Let’s refactor it to a more readable async/await. Now, the problem is that await doesn’t work unless it’s used inside an asyncfunction:

// Uncaught SyntaxError: await is only valid in async function
const response = await fetch('https://api.chucknorris.io/jokes/random')
const {value} = await response.json()

document.querySelector('#chucky').textContent = value

So a common pattern is to just wrap the async code in an async function and call it immediately. But we are polluting the namespace by adding this new go function which we call immediately:

async function go() {
    const response = await fetch('https://api.chucknorris.io/jokes/random')
    const { value } = await response.json()

    document.querySelector('#chucky').textContent = value
}

go()

A SOLUTION

So here’s a quick trick I’ve used in a job interview in the past.

We can do exactly the same in one step and without polluting the namespace with an Async Immediately Invoked Function Expression:

(async function() {
    const response = await fetch('https://api.chucknorris.io/jokes/random')
    const { value } = await response.json()
    document.querySelector('#chucky').textContent = value
})();

Written by Jon Portella.