在NodeJS中修改Promise原型

时间:2018-07-26 12:24:25

标签: javascript node.js es6-promise

基本说明:我正在写一个包装nodeJS mysql函数的类。在该类中,我具有一个select函数,该函数创建要运行的查询。我返回了Promise,因此可以轻松使用.then和.catch功能。

问题:是否有比我在这里的基本设置更好的添加.before函数的方法?还是修改Promise有不利之处?

function beforePromise(add){
    var before = [];
    
    var p = new Promise(function(resolve){

        if(typeof add !== "number"){
            throw new Error("argument 'add' is not a valid number.");
        }
        var number = 0;
        number += add;

        setTimeout(function(){
            for(var i = 0; i < before.length; i++){
                number = before[i](number);
            }

            // get the query from database

            // resolve
            resolve(number);
        }, 0);

    });

    // add the .before function
    p.before = function(callback){
        if(typeof callback === "function"){
            before.push(callback);
        }
        return p;
    };
    return p;
}

beforePromise(10)
  .before((num) => num * 1.2) // num = 12
  .before((num) => num + 2) // num = 14
  .then(num => console.log(num))// output 14
  .catch((err) => console.error(err));
  
beforePromise(10)
  .then((num) => console.log(num));// output 10
  
/*
beforePromise()
  .then((num) => console.log(num))
  .catch(err) => console.log(err));
  */

1 个答案:

答案 0 :(得分:0)

修改承诺不是主要问题,但是setTimeout引入了潜在的意外行为。

如果我阅读代码:

beforePromise(10)
  .before((num) => num * 1.2) // num = 12
  .before((num) => num + 2) // num = 14
  .then(num => console.log(num))// output 14
  .catch((err) => console.error(err));

然后对我来说,不清楚我是否不允许做这样的事情

var obj = beforePromise(10)

var val = await someAsyncTask()
obj = obj.before((num) => num * val) 
obj = obj.before((num) => num + 2)

obj.then(num => console.log(num))// output 14
.catch((err) => console.error(err));

这不会达到预期的结果。因此,您需要在文档中进行描述,并且代码的维护者/审阅者需要知道这一点或在文档中查找。

一种更好的方法是具有一个显式函数来触发该过程的执行。

before(10)
  .before((num) => num * 1.2) // num = 12
  .before((num) => num + 2) // num = 14
  .exec() // does returns the Promise and does the execution
  .then(num => console.log(num)) // output 14
  .catch((err) => console.error(err));

function before(add) {
  var callbacks = [];
  var obj = {
    before: before,
    exec: exec
  }


  function before(callback) {
    if (typeof callback === "function") {
      callbacks.push(callback);
    }
    return obj;
  }

  function exec() {
    if (typeof add !== "number") {
      throw new Error("argument 'add' is not a valid number.");
    }
    var number = 0;
    number += add;

    for (var i = 0; i < callbacks.length; i++) {
      number = callbacks[i](number);
    }

    return Promise.resolve(number)
  }

  return obj
}

before(10)
  .before((num) => num * 1.2) // num = 12
  .before((num) => num + 2) // num = 14
  .exec()
  .then(num => console.log(num)) // output 14
  .catch((err) => console.error(err));

before(10)
  .exec()
  .then((num) => console.log(num)); // output 10