node,mongodb和承诺的麻烦



我有工作代码,该代码使用一系列嵌套回调首先检查数据库,以查找使用查找命令的预先存在的条目。如果该条目存在,那就什么也不做。如果条目不存在,请将其插入DB。

此代码运行良好,但没有提供有意义的错误处理:

var MongoClient = require('mongodb').MongoClient;
MongoClient.connect("mongodb://localhost/peeps", function(err, db) {
        if(err) {
            if(db) db.close();
            return next();
        }
        var query = { section: req.body.section, year: req.body.year, semester: req.body.semester };
            db.collection("sections").find(query).toArray(function(err, result) {
            if( result.length >= 1  ) {
                db.close();
                if(callback) callback();
            } else {
                var days = [];
                for(var i = 1; i < 6; i++) {
                    if( field['starthour' + i]  != '') {
                        var oneDay = {};
                        oneDay.day = field['day' + i];
                        // more fields being stored here...
                        days.push(oneDay);
                    }
                }
                db.collection("sections").insertOne(
                    { 
                        coursetitle: req.body.course,
                        // more fields being stored here
                        days: days
                    }
                )
                db.close();
                if(callback) callback();
            }
        })
    })

输入承诺,这是一个假定的回调地狱和错误处理的修复程序。因此,我对承诺遇到的第一个问题(我已经搜索并尝试了使用关键字蒙哥多,承诺,节点和查找的每个帖子)是如何避免嵌套承诺的方法。

这是我尝试实施承诺策略的多种不同方式的一种方式:

var MongoClient = require('mongodb').MongoClient;
    MongoClient.connect("mongodb://localhost/peeps")
        .then(function(db) {
            var query = { section: req.body.section, year: req.body.year, semester: req.body.semester };
            db.collection("sections").find(query).toArray(function(err, result) {
                // I am assuming that returns from this callback won't return to the next .then statement...
                // how to avoid nesting promises?
                // If a nested promise is necessary, how do I set it up?  .find does not seem to return a promise... (I've tried)
                if(err) return err; // Where does it go?  probably not to the catch statement like I want it to :-(
                if(result.length >= 1)
                    return {db: db, preexist: true};
                else {
                    return {db: db, preexist: false};
                }
            })
        })
        .then(function(o){
            // o didn't make it here, so db doesn't exist nor preexist, they're undefined
            console.log(o.db + o.preexist)
            // do the insert one if necessary
        })      
        .catch(function(error) {
            console.log(error.message);
        })

因此,从本质上讲,我的主要问题是:如何避免筑巢?如果嵌套承诺是必要的,是否有一种方法可以将错误返回到最外面.catch?如果未指定回调,请找到返回承诺吗?如果.find可以返回诺言,那么将结果存储在数组中的适当语法是什么?

任何帮助将不胜感激。

mongodb就像大多数其他DB 提供商一样,提供了一种检索最新错误的方法。

对于MongoDB,您将使用db.getLastError()检索错误对象/文档。这是您可以从该文档中使用的字段。

从更抽象的角度来看,您的构建方式取决于数据模型本身,应用程序的逻辑以及可以安全执行的缓存数量。

可以使用 Promise.all 方法和DB操作的收集,而无需多个()语句和/或不必要的DB连接:

function updateDatabase (name, token) {
  return MongoClient.connect(MONGODB_URL)
     .then( (db) => 
          Promise.all([
            db.collection('testCollection').update({name}, {$pull: {tokens: {$in: [token]}}}),
            db.collection('log').insert({name, token})
          ]).then(() => db.close(true)
          ).then(`Invalid token: ${token} has been removed from: ${name}`
          ).catch((err) => { db.close(true); throw err }); //catch errors
     )
}

更多信息:https://stackoverflow.com/a/45845982/1848744

最新更新