如何在承诺链中使用变量

时间:2016-01-31 10:47:23

标签: javascript node.js mongodb express

我使用带有快速框架的nodejs和mongodb / mongoose来存储我的数据。

我有一个寄存器功能,可以完成4件事。创建用户,创建令牌,将令牌分配给用户,最后发送电子邮件。

我最初使用回调功能做得很好。我试图使用承诺现在我需要蓝鸟这样做。但是当一个promise完成时,我需要在下一个promise中使用返回的变量。

注册功能

module.exports.register = function(req, res) {

    var input = req.body;

    var newUser = new User ({

        username: input.username,
        email: input.email,
        password: input.password,
        active: false

    });

    var promise = newUser.save();

    promise.then(function(user) {

        return createToken('new', null, user._id);

    }).then(function(token) {

        user.tokens.push(token._id);

        return user.save();

    }).then(function(user) {

        //Do Email Stuff

    }).catch(function(err) {

        return res.json("Could Not Register");

    });
}

创建令牌功能

var createToken = function(type, expiry, userid) {

    var token = uuid.v4();

    return new Promise(function(resolve, reject) {

        var newToken = Token({

            type:type,
            token: token,
            expiry: expiry,
            user: userid

        });

        var promise = newToken.save();

        promise.then(function(token) {

            resolve(token);

        }).catch(function(err) {

            reject(err);

        });

    });

};

所以在我做“user.tokens.push”的地方找不到用户。香港专业教育学院读蓝鸟,我可以使用一些称为绑定的东西?然后使用“this”。谁能告诉我如何正确地做到这一点。

此外,如果每个承诺中都有错误,我希望catch方法是动态的。它不是“无法注册”,而是“无法保存用户”或“无法保存令牌”,具体取决于哪个承诺失败。

如果有一种方法可以让我更清洁,请告诉我。

1 个答案:

答案 0 :(得分:0)

使用寄存器函数范围中的var存储user的值以供以后使用

并不遗憾
module.exports.register = function(req, res) {
    var input = req.body;
    var newUser = new User ({
        username: input.username,
        email: input.email,
        password: input.password,
        active: false
    });
    var sUser; // store user in this var
    newUser.save()
    .then(function(user) {
        sUser = user; // save value user to use later on
        return createToken('new', null, user._id);
    }).then(function(token) {
        sUser.tokens.push(token._id); // sUser is user, huzzah
        return sUser.save();
    }).then(function(user) {
        //Do Email Stuff
    }).catch(function(err) {
        // use the content of err to return a meaningful error
        return res.json("something more meaningful based on the content of err");
    });
}

您还应该避免在createToken中使用新的Promise反模式

var createToken = function(type, expiry, userid) {
    var token = uuid.v4();
    var newToken = Token({
        type:type,
        token: token,
        expiry: expiry,
        user: userid
    });
    return newToken.save();
};

这会产生与您的代码相同的结果

另一种方法是将user发送到createToken函数并像这样重写代码

module.exports.register = function(req, res) {
    var input = req.body;
    var newUser = new User ({
        username: input.username,
        email: input.email,
        password: input.password,
        active: false
    });
    newUser.save()
    .then(function(user) {
        return createToken('new', null, user);
    }, function(err) { // optionally change errors to meaningful error messages
        throw "newUser.save failed";
    }).then(function(user) {
        //Do Email Stuff
        // you could throw "email failed" if there's an error
    }).catch(function(err) {
        // err could be "newUser.save failed", "newToken.save failed", "email failed"
        // use the content of err to return a meaningful error
        return res.json("something more meaningful based on the content of err");
    });
}

var createToken = function(type, expiry, user) {
    var token = uuid.v4();
    var newToken = Token({
        type:type,
        token: token,
        expiry: expiry,
        user: user._id
    });
    return newToken.save()
    .then(function(token) {
        user.tokens.push(token._id);
        return user.save();
    }) // you could add the following to make the errors suited to you
    .catch(function(err) {
        throw "newToken.save failed";
    });
};