From what I read, race conditions occur when different threads try to change a shared variable, which can result in a value that's not possible with any serial order of execution of those threads.
But code in node.js runs in a single thread, so, does that mean code written in node.js is free of race conditions?
No. That's true you cannot have race condition on a single threaded, non I/O doing program.
But node.js is mainly fast because of its non blocking way of programming. Non blocking means that setting a listener to a response event, you can do something else while waiting this response.
Why ? Because the work for getting the response is done on another thread. Database, filesystem, run on other thread, client obviously runs on another computer and you program workflow can depend on its response.
So strictly speaking, node.js runs on one thread, but your program workflow, wich include I/O (database, filesystem), client and everything, runs on many thread.
So there still can be race condition if you do a request to add something to a database, and then just send a request to delete it without waiting for the response of the first request. There would be no race condition if the database was running in the same thread as node.js, and the request was just a function call executed immediatly.
Yes, race conditions (in the sense of a shared resource having an inconsistent value due to order of events) can still happen anywhere that there's a point of suspension that could lead to other code being run (with threads its at any line), take for example this piece of async code that is entirely single threaded:
This code has suspension points at every single await and as such could context switch between the two functions at a bad time producing "$50" rather than the expected "$100", this is essentially the same example as Wikipedia's example for Race Conditions in threads but with explicit points of suspension/re-entry.
Just like threads though you can solve such race conditions with things like a Lock (aka mutex). So we could prevent the above race condition in the same way as threads:
Race conditions can still happen as they really have nothing to do with threads, but on making assumptions about event timing and sequence, so threads are just an example of that.
Node.js is single-threaded, but still concurrent, and race conditions are possible. For example:
This program is supposed to send clients a size of their request. If you test it, will seem to work correct. But it is actually based on implicit assumption, that nothing happens between request start and end events. If there are 2 or more concurrent clients it will not work.
This happens here because
size
variable is shared, a lot like when two threads share a variable. You can think about an abstract "asynchrnous context", which is a lot like thread, but it can only be suspended at certain points.No. Node.js is free of race conditions that would be caused by context switching; however, you can still write a node.js program where asynchronous events happening in an unexpected order result in an inconsistent state.
For example, suppose you have two functions. The first sends a message through a WebSocket and, in a callback, saves the reply. The second function deletes all saved replies. Calling the functions in order does not guarantee an empty message list. It is important to consider all possible event orderings when doing asynchronous programming.
EDIT: Here's some example code
Yes. Node.js can run into race conditions as soon as you start sharing resources.
I mistakenly also thought you couldn't get race conditions in Node.js because it's single threaded nature, but as soon as you use a shared resource outside of node (e.g. a file from the file system) you can get into a race condition. I posted an example of this issue in this question when I was trying to understand this: node.js readfile woes
What is different in Node.js from other environments is that you have a single thread of JavaScript execution so there is only one JavaScript instance running your code (as oppossed to a threaded environment in which there are many threads executing your app code at the same time.)
Yes. It can.
Race condition in Nodejs is feasible when you use
cluster
module to initialise multiple workers.The case
Whenever you change the watched file, 4 workers will execute the handler at the same time. This behaviour causes the undetermined
newData
.The solution