如何解耦和封装长Node.js方法?

时间:2017-03-10 20:23:17

标签: javascript node.js

我有以下方法,简化:

var component = require('../../component.js')
exports.bigMethod = function (req, res) {
    var connection = new sql.Connection(process.config.sql, function (err) {
        new sql.Request(connection)
            .input('input', sql.VarChar, 'value')
            .execute('dbo.sp1')
            .then(function (data) {
                if(data[0].length === 0) {
                    res.status(500).send({ message: 'Some Error' });
                }

               // set some local variable I'll use later: localVar

                new sql.Request(connection)
                    .input('input1', sql.Int, req.query.input1)
                    .input('input2', sql.Int, req.query.input2)
                    .input('input3', sql.DateTime2, req.query.input3)
                    .input('input4', sql.DateTime2, req.query.input4)
                    .execute('dbo.sp2')
                    .then(function (recordset) {
                        json2csv( { data: recordset[0] }, function(err, data) {
                            if (err) {
                                res.status(500).json(err);
                            }
                            fs.writeFile(localVar.path, data, function (err) {
                                if (err) {
                                    res.status(500).json(err);
                                }
                                try {
                                    var email = new component.Email();
                                    email.set_callback(function (error) {
                                        if (error) {
                                            res.status(500).send({ message: 'Another error' });
                                        }
                                        res.jsonp([]);
                                    });
                                    email.send(
                                        localVar,
                                        {
                                            filename: localVar.name,
                                            path: localVar.path
                                        }
                                    );
                                } catch (e) {
                                    res.status(500).send({ message: 'Another Error' });
                                }
                            })
                        });

                    })
                    .catch(function (err) {
                        res.status(500).send({ message: 'Another Error' });
                    });
            })
            .catch(function (err) {
                res.status(500).send({ message: 'Another Error' });
            });

    });
};

正如你所看到的,这是一个很长的方法,这是一种反模式。此外,对sp2的调用实际上是一个重复:还有另一个组件进行类似的调用,只是直接返回json2csv的结果。

现在,我不太确定如何将此方法划分为充分利用可重用性。我应该在返回Promises的函数中封装数据库调用吗?我应该使用一些咖喱吗?

感谢。

1 个答案:

答案 0 :(得分:1)

将代码划分为不同的函数应该是您的top priority - 仅此功能就是处理太多可以轻易划分的事情。

您可以通过分解回调和承诺来使您的代码功能更加清晰,正如您所怀疑的那样。

回调示例:

new sql.Connection(..., handleSQLConnection);
handleSQLConnection(error) { ... }

承诺示例:

doSomething
  .then((a) => doOtherStuff(a))
  .then((b) => doSmthElse(b));

doOtherStuff(a) { ... }
doSmthElse(b) { ...}

尽管如此,refactoring非常自以为是。但是你应该试着避免上帝的功能,而是编写one thing but they do it well的函数。