私はBluebird
に新規で、新しいユーザーを作成しようとしていますが、reject
関数が期待通りに機能しません。Bluebirdが新しいユーザーを作成する
エラーThere nickname is already in use
を起動しても、user
が作成されるという問題があります。
ここではコードを貼り付けます。
user.jsの
var User = require('../models/user');
var Promise = require('bluebird');
module.exports = {
validateFields: function (nickname) {
return new Promise(function (response, reject) {
if (!nickname) {
reject('You must provide the nickname');
} else if (nickname.length < 4 || nickname.length > 20) {
reject('The nickname must be longer than 4 and shorter than 20 characters');
} else {
nickname = nickname.trim();
User.findOne({ "nickname": nickname }).exec()
.then(function (user) {
if (user) {
reject('There nickname is already in use');
} else {
response();
}
}, function (err) {
reject('There is an error trying to verify the nickname');
});
}
});
},
registerUser: function (user_id, nickname) {
return new User({ user_id: user_id, nickname: nickname }).save();
}
};
register.js
var validator = require('validator');
var Promise = require('bluebird');
var Account = require('../../models/account');
module.exports = {
validateFields: function (email, password) {
return new Promise(function (response, reject) {
if (!email) {
reject('You must provide the email');
} else if (!password) {
reject('You must provide the password');
} else if (email.length < 6) {
reject('The email is too short');
} else if (email.length > 40) {
reject('The email is too long');
} else if (!validator.isEmail(email)) {
reject('The email is not valid');
} else {
Account.findOne({ email: email }).exec()
.then(function (account) {
if (account) {
reject('There is already an email');
} else {
console.log(account);
response();
}
}, function (err) {
reject('There is an error trying to verify the email');
});
}
});
},
registerAccount: function (email, password) {
return new Account({ email: email, password: password }).save();
}
};
routes.js
var Promise = require('bluebird');
var user = require('./routes/user');
var account = require('./routes/auth/register');
router.post('/register', function (req, res, next) {
account.validateFields(req.body.email, req.body.password)
.then(function() {
return user.validateFields(req.body.nickname);
}, function (err) {
return res.status(400).json({ msg: err });
})
.then(function() {
req.body.email = req.body.email.trim();
req.body.password = req.body.password.trim();
console.log('bien');
return account.registerAccount(req.body.email, req.body.password);
}, function (err) {
console.log('mal');
return res.status(400).json({ msg: 'There was an error trying to save the email' });
})
.then(function (data) {
return user.registerUser(data, req.body.nickname);
}, function (err) {
return res.status(400).json({ msg: 'There was an error trying to save the user' });
})
.then(function() {
return res.status(200);
}, function (err) {
console.log(err);
return res.status(400).json({ msg: err });
})
.catch(function (err) {
console.log('catch');
return res.status(400).json({ msg: err });
});
});
アドバイスに感謝します。
UPDATEちょうど約束で開始し、ベストプラクティスを探している皆を明確にするために、私はthisリンクが便利ですね。
['Promise'コンストラクタのアンチパターン](http://stackoverflow.com/q/23803743/1048572)は避けるべきです。 [ES6 Promisesで事前条件を慣習的に扱う]を見てください(http://stackoverflow.com/q/35856041/1048572) – Bergi
は、検証を受け入れる '新しい約束事 'の作成に関連するあなたのヒントです。 'mongoose'約束? 'Promise.reject(新しいエラー(何かエラーが発生した場合))')と 'mongoose'約束を返すような検証を分けるべきでしょうか? – DevStarlight
はい、正確です。あなたがマングースの約束を返すのではなく、ブルーバードの約束を返すことを望むなら、 'return Promise.resolve(... .findOne(...).exec())、then(...)' – Bergi