高级前端手写代码【Q701】实现函数 promisify,把回调函数改成 promise 形式

实现函数 promisify,把回调函数改成 promise 形式

Issue 欢迎在 Gtihub Issue 中回答此问题: Issue 723

Author 回答者: Asarua

function promisify(fn) {
  return function (...args) {
    let hasCb = args.some((v) => typeof v === "function");
    if (hasCb) {
      fn(...args);
    } else {
      return new Promise((resolve, reject) => {
        fn(...args, cb);
 
        function cb(err, data) {
          if (err) {
            reject(err);
          } else {
            resolve(data);
          }
        }
      });
    }
  };
}

Author 回答者: wangjiayan

首先明确nodeCallback的规范: 1、回调函数在主函数参数的位置是最后一个 2、回调函数的第一个参数是error 例如

function main(err, b, c, callback) {
  let data = b+c
  callback(err,data)
 }

所以实现的思路就是: 把结果由原先的放在callback中返回,改成放在Promise中返回

const promisify = (fnc) => (...args) => {
  return new Promise((resolve, reject) => {
    fnc.call(this, ...args, function (err, data) {
      if (err) {
        reject(err);
      } else {
        resolve(data);
      }
    });
  });
};

测试结果:

var func1 = function (a, b, c, callback) {
  let rst = a + b + c;
  callback(null, rst);
};
var func2 = promisify(func1);
func2(1, 2, 3).then((rst) => {
  console.log("rst", rst);
}); //输出6