Skip to content

Instantly share code, notes, and snippets.

@vasanthk
Created December 14, 2018 08:15
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save vasanthk/72d8a6b45481a839b13ca869042ddbd6 to your computer and use it in GitHub Desktop.
Save vasanthk/72d8a6b45481a839b13ca869042ddbd6 to your computer and use it in GitHub Desktop.
Avoid Creating Unnecessary Promises!!
const { promisify } = require('util')
const timeout = promisify(setTimeout)
async function bar() { await timeout(1000) }
// The idea here is that we don't know if foo
// is going to return a Promise or not, so just
// in case, force it to return a Promise.
// Unfortunately, doing it this way creates
// quite a few additional unnecessary Promises
//
async function foo(a) {
return a || await bar()
}
foo(true).then(console.log)
foo(false).then(console.log)
// Run this code with
// node --trace-event-categories node.async_hooks bad.js
//
// Then open chrome://tracing and load the `node_trace.1.log`
// to see just how many Promises are created
const { promisify } = require('util')
const timeout = promisify(setTimeout)
async function bar() { await timeout(1000) }
// By using Promise.resolve() and not forcing
// foo to be async, we achieve the exact same
// result with fewer Promises created. However,
// that Promise.resolve() is still creating a
// completely unnecessary Promise in this case
// leading to unnecessary scheduling delay and
// memory allocation. Bad foo!
function foo(a) {
return a ? Promise.resolve(a) : bar()
}
foo(true).then(console.log)
foo(false).then(console.log)
// Run this code with
// node --trace-event-categories node.async_hooks better.js
//
// Then open chrome://tracing and load the `node_trace.1.log`
// to see just how many Promises are created
const { promisify } = require('util')
const timeout = promisify(setTimeout)
async function bar() { await timeout(1000) }
// WHAT!? Callbacks *with* my Promises, you
// must be joking!!? Nope... with this approach
// you don't have to even think about whether
// you're dealing with a Promise or not. When
// the data is available, sync or async, the
// callback will be invoked and no unnecessary
// Promises will be created.
function foo(a, cb) {
if (a) cb(null, a)
else {
bar().then(cb.bind(null, null))
.catch(cb.bind(null))
}
}
foo(true, console.log)
foo(false, console.log)
// Run this code with
// node --trace-event-categories node.async_hooks best.js
//
// Then open chrome://tracing and load the `node_trace.1.log`
// to see just how many Promises are created
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment