DEV Community

Cover image for Javascript Immediately invoked function expressions (IIFE)
Johnny Simpson
Johnny Simpson

Posted on • Originally published at fjolt.com

Javascript Immediately invoked function expressions (IIFE)

Immediately invoked function expressions, or IIFE, are functions which are run as soon as you define the function. You may also see people refer to them as anonymous functions. They give us an easy way to isolate variables within a function, and not globally - after which we can easily run the function immediately. They are also useful for running async functions, when a top level await is not available.

While we usually define functions like this:

let x = () => {
    console.log("hello");
}
let y = function() {
    console.log("world");

}

function z() {
    console.log("!");
}

x(); y(); z();
Enter fullscreen mode Exit fullscreen mode

Defining an IIFE means invoking the function as we write it. So we can define an IIFE like this:

(function() {
    console.log("hello world!")
})()
Enter fullscreen mode Exit fullscreen mode

This function is anonymous (it has no name) - and it runs immediately. You can also run it using arrow notation, like this:

(() => {
    console.log("hello world!")
})()
Enter fullscreen mode Exit fullscreen mode

While the IIFEs above to do not have names, you can give them names. It doesn't really make sense, though, since you can't call them anywhere else. Once the function is created and called in this format, it cannot be used anywhere else. That means that in the example below, trying to call myFunction() somewhere else will not work:

(function myFunction() {
    console.log("hello world!")
})()
Enter fullscreen mode Exit fullscreen mode

Anonymous or Immediately invoked function expressions can be used to encapsulate async behaviour. You can still make an IIFE asynchronous by using the async keyword:

(async () => {
    console.log("hello world!")
})()
Enter fullscreen mode Exit fullscreen mode

 Giving arguments to IIFEs in Javascript

We can pass variables straight into an IIFE using the expected format. For example, below we have an argument in our IIFE - which is x. We can pass in a value for x by using the last set of parenthesise:

let getNumber = 10;
(function(x) {
    console.log(x + 10)
})(getNumber) // console logs 20
Enter fullscreen mode Exit fullscreen mode

 The defensive semi colon in IIFEs

You may sometimes see the following code when IIFEs are defined where a semi colon is added to the start.

;(() => {
    return 10;
})
Enter fullscreen mode Exit fullscreen mode

This seems confusing but it's to avoid a weird issue where, if the previous line doesn't have a semi colon, the function last line will be used as the function name. Consider this code:

let b = 5
let c = 10
let a = b + c
(function () {
    return 10
})();
Enter fullscreen mode Exit fullscreen mode

If someone forgot to put a semi colon on let a = b + c, or if you imported the IIFE onto a line where the previous one did not contain a semi colon, you may run into some weird bugs. In the above example, you'll get the error Uncaught TypeError: c is not a function. This is because the code interprets this as trying to run the c function. In essence, the code sees this:

c(() => {
    return 10
})()
Enter fullscreen mode Exit fullscreen mode

So defensive semi colons at the start of IIFEs is an easy way to avoid this scenario.

 Conclusion

IIFEs are commonly found in Javascript code bases and have been a useful way to perform a number of things like asynchronous code and scoping variables or code within a specific function block. While there are now other ways to achieve this in Javascript, you're still going to see these all over the place - so understanding how they work is important.

Top comments (0)