DEV Community

Cover image for Concurrency In JavaScript
Kinanee Samson
Kinanee Samson

Posted on

Concurrency In JavaScript

JavaScript our dearly beloved programming is termed asynchronous and this is one of the things we love about it. JavaScript has an api for handling concurrent tasks, as is required of most high level languages. There is a neat way that JavaScript achieves this, which is quite different from what you'd be used to in Java or C. In this article we are going to explore this amazing part of JavaScript.

Concurrency

Often there is a need for a program to be able to execute certain commands out of the normal flow, without breaking other parts of the program. Much like you can see and listen at the same time, if we examine more closely you will find out these two phenomenal occur in parallel and at the same time, the collective result of both "programs" makes what's happening more clear to us. Similarly we as software engineers desire that our programs should behave in like manner.

It is very normal for a computer cpu to expose more than one core on which we can execute or run commands, JavaScript as a language was not designed to utilize more than one core, JavaScript code normally runs in a single thread manner where one statement is executed and then the next. This approach is logical, however there is often a need to "move" on to the next without waiting for the immediate to complete, going out of the normal flow as we pointed out earlier.

If we could not then our user would not get a good user experience, certain things like fetching data could cause glitches especially if your internet is not fast, thank God this isn't the case and we handle data fetching and other like actions asynchronously. We will now proceed to understanding how JavaScript implements its concurrency model.

Queue, Stack, Heap

Every JavaScript program is a self isolated process, it has its own queue a term we will look at shortly, stack another term we will look at, and its heap. The heap is a largely unstructured area of memory allocated to the objects in our code. Let's think of the heap as an area where messangers on horseback wait before they get to deliver their messages.

When it gets to the turn of a messenger they unmount and move to queue. This area they are attended to in a first in first out manner, when each messenger dispatches their message, there is usually a reaction to that message, which in our case is a function call, for every message in the queue there is a function associated with it, that function is called when the message is processed out of the queue.

Each function call creates a stack frame that contains the statement and expression in the function, when that function returns a value or void, its frame is then popped out, the next function will begin executing, if we call a function inside another function a frame will be created for each. The frame for the nested function sits on top of the frame for the function that called it, when the nested function is done executing it will return and get popped of and the main function will continue executing or return and get popped off. The items in stack are treated in a last in first out format. The stack is a data structure that holds the frame for each function, we can deduce that this is a synchronous process, so how is concurrency achieved with the stack and the queue.

Event Loop

The event loop is simply a loop that iterates through the queue and processes any message if any is in the queue. Since we are in a JavaScript development environment messages could also be added to the queue as a result of events happening in the DOM. The event loop does not really care, its job is to process the messages in the queue. Its js interesting to remember that a stack frame which is in essence a function call can emit an event that adds a new message to the queue or it can directly add a message to the queue. So when the result of an expression might take long, there are APIs that allow us to add that result as a message when it is available to the queue, we go on processing other things without waiting. This is the basis of callback based code. This is also how setTimeout and setInterval adds messages asynchronously to the queue. When we write a setTimeout function a message is added to the queue after the specified delay in milisecs.

console.log("hello");

setTimeout(() => {
 console.log("delayed")
}, 100)
Enter fullscreen mode Exit fullscreen mode

Hello gets logged because it is immediately added to the queue and since there is no other task waiting to be added to the queue except of course the one from the setTimeout, which is added immediately, there's no 100ms delay guarantee that the message will be added to the queue, rather this is just a maximum delay if there are other messages in the queue waiting to be processed, however if this is not the case and there are no messages waiting in the queue, the task from the SetTimeout is added immediately ignoring the delay.

getSomeData(place, action)
// do something with place
 let result = { data : place } // something
 setTimeout(() => {
   action(result)
 }, 0)
}

getSomeData("london", console.log)
console.log("hey")
// call back based code
Enter fullscreen mode Exit fullscreen mode

From the example above when the first function is executed a new stack frame is created, we create a variable and then use setTimeout to call the function passed in. as the second argument and give it the variable we created earlier when, if the first function has to take some time before completing the action would have to wait, but our code does not have to wait and it moves on to processing the next statement, when the result is ready action is called with the result passed in as an argument to the function. A new stack frame is created for it and the next message in the queue is processed if any.

The above process, the way the event loop as described above is synchronous, the event loop is usually expressed in terms of a while loop.

while(queue.waitForMessage()){
 queue.processNextMessage()
}
Enter fullscreen mode Exit fullscreen mode

When we pass in 0, as the delay this is does not always mean that the message will be added to the queue in zero seconds. The message will only be added to the queue when other messages in the queue has been processed. You should know that each stack frame must run to completion before another can be added on top of it. If you want to know more about asynchronous JavaScript i think you should read this article

Discussion (10)

Collapse
jcubic profile image
Jakub T. Jankiewicz • Edited on

This is one big misunderstandig from your part. Async nature of JavaScript have nothing to do witth concurency. The way conurency is handed is not exactly part of JavaScript langauge only part of the environment. In browsers concurency is handled by Web Workers.

In JavaScript as in any language concurency is handed by different threads or processes. Web Workers is a way to create new Thread in a browser.

Collapse
kalashin1 profile image
Kinanee Samson Author

Okay, I think I was badly misinformed by the Mozilla Developer documentation. Thank you tho.

Collapse
aliendreamer profile image
Teodor Stefanov

It is pity some people will read this, and think iti s correct. This is bulshit and your reply on the comment pointing how much you didn't understood the documentation is pity. And I can see as Jakub pointed you have no idea what async and concurency actually mean.

Thread Thread
kalashin1 profile image
Kinanee Samson Author

Okay i see... Someone needs to understand the basics.

Thread Thread
jcubic profile image
Jakub T. Jankiewicz

Just update the artice and title. Or unpablish it. It's really bad to share invalid information.

Thread Thread
kalashin1 profile image
Kinanee Samson Author

The fact that you cannot discernt that concurrent and asynchronous are two words for the same thing is baffling.

Thread Thread
jcubic profile image
Jakub T. Jankiewicz • Edited on

They are not the same thing. Sorry but you're wrong. JavaScript didn't had concurrency for a long time (also still it's part of environment not the language itself). But asynchronous code was from the beginning. Please read those Wikipedia Articles and stop sharing misinformation.

There are not many languages that have concurency on a language level. And JavaScript is not one of them.

The only langauge I know that has concurency build in is Erlang:

Maybe you've found in dictionary that those are synonymous, but not so much in Computer Science. Where things that sounds the same may have different meaning.

Thread Thread
jcubic profile image
Jakub T. Jankiewicz • Edited on

I think that you've read this article on MDN EventLoop, that is really confusing, not everything what is on MDN is true, this is community Wiki created by volunteers like WIkipedia. It can have mistakes. And this aricle is a proof. I will report this error immediately.

Thread Thread
jcubic profile image
Jakub T. Jankiewicz • Edited on

Note that Event Loop MDN article got updated after my intervention on GitHub. There no more concurrency in that article. You can correct your article now.

Collapse
ratrateroo profile image
ratrateroo

There are some articles to understand javascript a little bit easier written by Lydia Hallie here in dev called Javascript Visualized. Helps me a lot about the twist and turns of js.