Asynchronous vs Synchronous Callbacks in JS
Tags: javascript, webdev, beginners, tutorial
Published: 2022-05-10 18:37:53

Callbacks are a concept I struggled implementing when I was first introduced to them in bootcamp. I understood their purpose but it's inevitable that not everything you learn will immediately stick the first time around. Hopefully this dive into callbacks will help you understand their function and purpose!

<img width="100%" src="https://media.giphy.com/media/zIPKUgO2Ln6XC/giphy.gif" >

**What are callbacks in JavaScript?**

The first thing you wanna know is that a callback is a function. In JavaScript, functions are first-class objects, meaning they can be: 

-stored in a variable, object, or array

-passed as an argument to a function. returned from a function

-returned from a function

A **callback** is a function that is passed inside another function as an argument. It is invoked inside the outer function or "higher order function" that "calls back" the callback function to complete the task. 

**What is a higher order function?**

A higher order function is a function that takes another function as an input, returns a function or does both.

**When can callbacks be used?**

Callbacks can be used for asynchronous and synchronous tasks within our code.

Let's look at an example of a **synchronous** callback: 

```JavaScript
console.log("Start");
function isEvenOrOdd(num, callbck) {
    //callback function invoked
    callbck(num);
}

//callback function logic

function callbck(num){
    if (num % 2 == 0) {
        console.log(`${num} is even`);
    } else {
        console.log(`${num} is odd`);
    }
}

//calling outer function 

isEvenOrOdd(37, callbck);

console.log("End");


```

To test our code and check out output, I use the console in Google Chrome. 

Observe the order of our output to full understand the code flow of this snippet. I find using the google chrome console or a code sandbox to observe the order of the output.


![Google chrome console with synchronous callback function and output](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/9eo3bics3p3icjphbsoz.png)

Our output should console.log("Start"), tell us if our input is even or odd, and console.log("End"). The logic that occurs is:

-function isEvenOrOdd is an outer function that takes `callbck` and `num`, our callback as an argument

-the callback function is invoked when we call `callbck(num)`

-function callbck(num) gives us the callback logic when it is invoked

-`isEvenOrOdd(37, callbck)` calls the outer function, it  invokes `callbck(num)` which calls on the callback logic

*Notice that in synchronous callbacks, callbacks are executed immediately in their order where the output is initiated with the console.log("Start"), the functions are established, invoked, and logic is called, followed by the console.log("End"). 

Synchronous callbacks are blocking, which means the higher-order function doesn't complete its execution until the callback is done executing


Now, let's look at an **asynchronous callback**:

```JavaScript
console.log("Start");
function isEvenOrOdd(num, callbck) {
    //callback function invoked inside Timeout
    setTimeout(() => {
        callbck(num);
    }, 0);
    
}

//callback function logic

function callbck(num){
    if (num % 2 == 0) {
        console.log(`${num} is even`);
    } else {
        console.log(`${num} is odd`);
    }
}

//calling outer function 

isEvenOrOdd(37, callbck);

console.log("End");

```

This code snippet is similar to our first code snippet, except we incorporate the setTimeout function. 

Let's take a look at our output:

![Asynchronous output with Timeout logic](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/p5rdy4pp6a8hblg3qjze.png)

Our asynchronous output has changed, what's going on?

With this asynchronous callback, the callback is enclosed within the setTimeout function. 

By default, the setTimeout function is an asynchronous function because it causes the code flow to delay until the task has been completed.

The asynchronous callback is executed after the execution of the higher-order function.

he asynchronous way to invoke the callbacks:

-The higher-order function starts execution: `console.log("Start")`

-The higher-order function completes its execution: `console.log("End")`

-The callback function executes after the Timeout() is finished: `37 is odd`

Asynchronous callbacks are non-blocking which means the higher-order function completes its execution without waiting for the callback. The higher-order function makes sure to execute the callback later on a certain event.

This is what causes us to see a difference in the order of our output. 

<img width="100%" src="https://media.giphy.com/media/PjocMfAvxO0EZPed6M/giphy.gif" >

Conclusion:
 Understanding the code flow of callbacks is advantageous because you'll gain a deeper insight into how tasks are being performed, manipulating data, and debugging. I get fuzzy on these concepts still, fearing I'm not using the right syntax, so it always helps to have resources to refresh your knowledge! 


References:

https://dmitripavlutin.com/javascript-callback/

https://www.freecodecamp.org/news/discover-the-power-of-first-class-functions-fd0d7b599b69/

https://dev.to/koladev/a-simple-guide-to-asynchronous-javascript-callbacks-promises-async-await-4m03