JavaScript Promisify | Convert Callbacks to Promises
![JavaScript Promisify](https://www.jsmount.com/wp-content/uploads/2023/12/promisify-732x412.jpg)
JavaScript Promisify
What is Promisification?
Promisification represents transformation. It’s the conversion of a callback-accepting function into a promise-returning function.
What are Callbacks?
A JavaScript callback is a function that is supposed to run after another function’s completion. These are the functions that are passed to another function as arguments that are invoked inside that main function to complete some kind of operation.
Why do we need to convert callbacks to promises?
Callbacks have issues with memory leaks that lead to poor performance because we don’t have control over when it is called, under what context, or how many times it’s being called.
Using promises, we control these factors (especially error handling) so the code is more readable and maintainable.
If you have multiple tasks that need to run sequentially, one after another, and the output of the previous task is required to start the next task. So to implement this, we will apply nested callbacks. To manage errors, We need to specify an error argument in each callback which is redundant. Promise or async-await, you can just add a .catch method or block which will catch any errors that occur in the promise chain.
Callback based Programming
function getSum(a, b, cb) {
if (!a || !b) {
cb(new Error('Please provide inputs'));
}
return cb(null, a + b); // First parameter refers to Error
}
getSum(10, 10, (err, result) => {
if (err) {
console.log(err);
} else {
console.log('output with callback based fn ', result);
}
})
// output with callback based fn 20
Custom Promisify Function
Create an Outer function named Promisify that will take our async function as an argument. This Outer function will return an Inner function.
function promisify(asyncFn) {
return function (...inputs) {
console.log(inputs);
}
}
When calling the Inner function, we have to return a promise-based object, so create a new Promise inside the inner function.
function promisify(asyncFn) {
return function (...inputs) {
return new Promise((resolve, reject) => {
})
}
}
Inside Promise, call the async function (a callback-based function that we have to covert) with input arguments.
In Callback-based programming, the last parameter is always a callback function named cb. We can see this in the getSum
function.
If we receive an error reject the promise and if we get the result resolve the promise.
function promisify(asyncFn) {
return function (...inputs) {
return new Promise((resolve, reject) => {
// Call async function and pass callback function as last parameter
asyncFn(...inputs, (err, result) => {
if (err) {
reject(err);
} else {
resolve(result);
}
});
})
}
}
Run the above program.
function getSum(a, b, cb) {
if (!a || !b) {
cb(new Error('Please provide inputs'));
}
return cb(null, a + b); // First parameter refers to Error
}
// we have to convert above callback based function so pass this our custom promisify function.
const p = promisify(getSum);
p(10, 10).then((res) => {
console.log('output with promisify', res);
}).catch(console.error)
// output with callback based fn 20
// Try with no input parameter
p().then((res) => {
console.log('output with promisify', res);
}).catch(console.error)
// TypeError: cb is not a function
Handle Error cases
This is a common Promisify function that will convert to every async function. In case we don’t send enough arguments which are required then it will give an error like ‘TypeError: cb is not a function’.
So let’s add an If condition in our previous code to make this error more specific.
// return a promise
function promisify(asyncFn) {
return function (...inputs) {
return new Promise((resolve, reject) => {
// This If is extra safety check for validate number of input arguments which required to async function
// Reject Promise incase sufficient arguments are not passed
if (inputs.length !== asyncFn.length - 1) {
reject('Please validate number of inputs parameters')
}
// Call async function and pass callback function as last parameter
asyncFn(...inputs, (err, result) => {
if (err) {
reject(err);
} else {
resolve(result);
}
});
})
}
}
Now check all error cases to run the above function.
p(10).then((res) => {
console.log('output with promisify', res);
}).catch(console.error)
// Please validate number of inputs parameters
p().then((res) => {
console.log('output with promisify', res);
}).catch(console.error)
//Please validate number of inputs parameters
p(1, 2, 3, 4).then((res) => {
console.log('output with promisify', res);
}).catch(console.error)
// Please validate number of inputs parameters
- Unlocking the Secrets of Cookie | Power Your Web Experience
- AI vs Human: Exploring the Boundaries of Intelligence
- Enhancing User Experience with JavaScript Throttle and Debounce
- JavaScript Custom Promise | Promise Polyfill
- JavaScript Promisify | Convert Callbacks to Promises
- JavaScript Promise and Callbacks | Everything You Must Know
- CSS Display Property – Deep dive in block | inline | inline-block
- Implementation of Queue using Linked List | JavaScript
- Insert node in Linked list | Algorithm | JavaScript
- Insertion Sort in data structure | Algorithm with Examples
- Selection Sort Algorithm & K’th Largest Element in Array
- Quick Sort Algorithm with example | Step-by-Step Guide
- Dependency Inversion Principle with Example | Solid Principles
- Object-Oriented Programming | Solid Principles with Examples
- ASCII Code of Characters | String Operations with ASCII Code
- Negative Binary Numbers & 2’s Complement | Easy explanation
- Factors of a Number | JavaScript Program | Optimized Way
- LeetCode – Game of Life Problem | Solution with JavaScript
- Fibonacci series using Recursion | While loop | ES6 Generator
- JavaScript Coding Interview Question & Answers
- LeetCode – Coin Change Problem | Dynamic Programming | JavaScript
- HackerRank Dictionaries and Maps Problem | Solution with JavaScript
- React Redux Unit Testing of Actions, Reducers, Middleware & Store
- Micro frontends with Module Federation in React Application
- React Interview Question & Answers – Mastering React
- Top React Interview Question & Answer | React Routing
- React Interview Questions and Answers | React hooks
- Higher Order Component with Functional Component | React JS
- Top React Interview Questions and Answers | Must Know
- Interview Question React | Basics for Freshers and Seniors
Node JS Promisify of Util package – https://nodejs.org/api/util.html#utilpromisifyoriginal
JavaScript Promisify