Bluebird vs Native vs Async/Await — State of Promises performances in 2019
Recently we started working on Kuzzle v2.
This new major version will contain very few functional breaking changes but mostly updates of our dependencies, including the transition from Elasticsearch 5 to 7 and from Node.js 6 to 10.
Concerning the transition from Elasticsearch 5 to 7, I will discuss this in detail in a future article.
About the transition to Node.js 10, the biggest question was what we were going to do about the current promises used in Kuzzle core. And especially if we finally went to use async/await in the whole core.
Doxbee benchmark
For all our tests, we used the Doxbee benchmarks developed by the Bluebird team based on an article analyzing the different asynchronous patterns in Javascript.
These benchmarks simulate a situation in which requests are executed competitively with blocking read/write actions.
To reproduce them, you can clone this Github repository: https://github.com/petkaantonov/bluebird/
The benchmarking tools are in the benchmark/ folder.
TL;DR:
In Node.js 10, it is impossible to do without Bluebird in critical code areas given the performance of its promises compared to native promises and async/await.
In Node.js 12, the performance of async/await is comparable to that of Bluebird, so we can use async/await throughout Kuzzle core.
Node.js 6
Currently we use the Bluebird library for performance reasons. Indeed, Bluebird promises are up to 300% faster and consume 200% less memory than native Node.js 6 promises.
Node.js 10
With this upgrade, we wanted to know if we would finally be able to do without Bluebird.
We did not find any recent benchmark results comparing the performance of Node.js 10 promises so we launched the benchmark with Node.js 10 ourselves:
We can see that even in Node.js 10, Bluebird promises are 20% faster than native promises and consume 40% less memory.
Similarly, Bluebird’s performance exceeds that of promises managed with async/await.
So we decided to keep Bluebird to manage promises in critical code areas such as document writing and retrieval because these functions can be called several thousand times per second and any performance gain is good to take.
However, we will be able to use async/await in non-critical locations to simplify the readability and maintainability of Kuzzle code. In particular, we will be able to remove all the core generator functions.
Node.js 12
Out of curiosity, we also benchmarked the performance of the promises in Node.js 12.
As a reminder, this new version of Node.js includes a significant performance gain on the management of promises with async/await. (See this excellent article on the V8 blog https://v8.dev/blog/fast-async)
We can see that the performance of promises managed with async/await is comparable to Bluebird’s promises!
Unfortunately the LTS of Node.js 12 is released in October and we absolutely need to release Kuzzle v2 beforehand to compensate for the end of the official support Elasticsearch 5 and Node.js 6.
On the other hand, we will not hesitate to replace all the Bluebird promises of Kuzzle’s core with async/await promises for Kuzzle v3 ;-)
Originally published at https://blog.kuzzle.io.