Mongodb 如何从find方法返回Mongoose结果?
我所能找到的用于呈现mongoose结果页面的所有内容都表示要这样做:Mongodb 如何从find方法返回Mongoose结果?,mongodb,node.js,express,mongoose,Mongodb,Node.js,Express,Mongoose,我所能找到的用于呈现mongoose结果页面的所有内容都表示要这样做: users.find({}, function(err, docs){ res.render('profile/profile', { users: docs }); }); 我如何返回查询结果,更像这样 var a_users = users.find({}); //non-working example 这样我就可以在页面上发布多个结果 比如: 这可以做到吗?简单的方法: va
users.find({}, function(err, docs){
res.render('profile/profile', {
users: docs
});
});
我如何返回查询结果,更像这样
var a_users = users.find({}); //non-working example
这样我就可以在页面上发布多个结果
比如:
这可以做到吗?简单的方法:
var userModel = mongoose.model('users');
var articleModel = mongoose.model('articles');
userModel.find({}, function (err, db_users) {
if(err) {/*error!!!*/}
articleModel.find({}, function (err, db_articles) {
if(err) {/*error!!!*/}
res.render('profile/profile', {
users: db_users,
articles: db_articles
});
});
});
实际上,Node.js中的每个函数都是异步的。猫鼬的发现也是如此。如果你想连续调用它,你应该使用类似library的东西
但在您的情况下,我认为最简单的方法是嵌套回调(这允许f.e.为以前选定的用户查询文章),或者在异步库的帮助下完全并行地执行(请参阅)。您试图强制采用同步范例。就是不行。node.js在大多数情况下是单线程的——当io完成时,会生成执行上下文。通过回调来管理信令。这意味着您要么拥有嵌套回调、命名函数,要么拥有流控制库,以使事情看起来更好
我有一个函数,我经常使用它作为返回节点函数
function freturn (value, callback){
if(callback){
return callback(value);
}
return value;
};
然后我在所有签名中都有一个可选的回调参数 我正在处理一个非常类似的事情,但是使用socket.io和来自客户端的DB访问。我的发现是在数据库有机会获取数据之前将数据库的内容返回给客户端。。。因此,我将在这里分享我的发现: 用于检索数据库的My函数: //读板-完整数据库
var readBoards = function() {
var callback = function() {
return function(error, data) {
if(error) {
console.log("Error: " + error);
}
console.log("Boards from Server (fct): " + data);
}
};
return boards.find({}, callback());
};
我的套接字事件侦听器:
socket.on('getBoards', function() {
var query = dbConnection.readBoards();
var promise = query.exec();
promise.addBack(function (err, boards) {
if(err)
console.log("Error: " + err);
socket.emit('onGetBoards', boards);
});
});
因此,为了解决这个问题,我们使用mongoose给我们的承诺,然后一旦我们从DB接收到数据,我的套接字就会将其发送回客户端
为了它的价值 我将在这里扮演亡灵巫师,因为我仍然看到另一种更好的方式 使用Wonder promise库及其方法: 主要部分如下:
Promise.promisifyAll(mongoose);
使所有mongoose(及其模型)方法作为返回承诺的函数可用,并带有Async
后缀(.exec()
变为.execAsync()
,依此类推).promisifyAll()
方法在Node.JS世界中几乎是通用的-您可以在任何提供异步函数(将回调作为其最后参数)的情况下使用它
Promise.props({
users: users.find().execAsync(),
articles: articles.find().execAsync()
})
bluebird方法接受带有承诺的对象作为其属性,并返回集体承诺,当两个数据库查询(此处为承诺)返回其结果时,该集体承诺将得到解决。解析值是最终函数中的结果
对象:
-mongoose在数据库中找到的用户results.users
-猫鼬(d'uh)在数据库中找到的文章results.articles
承诺很酷。使用它们。您可以通过以下代码获得所需的结果。希望这对你有帮助
var async = require('async');
// custom imports
var User = require('../models/user');
var Article = require('../models/article');
var List1Objects = User.find({});
var List2Objects = Article.find({});
var resourcesStack = {
usersList: List1Objects.exec.bind(List1Objects),
articlesList: List2Objects.exec.bind(List2Objects),
};
async.parallel(resourcesStack, function (error, resultSet){
if (error) {
res.status(500).send(error);
return;
}
res.render('home', resultSet);
});
我想我可以这样做,但是没有解决我更大的底层问题。我的例子可能不是最好的。我理解保持异步,但最大的问题是,我试图将代码组织成更真实的MVC方式,并且很难做到这一点。我讨厌这样的想法:在控制器中,对于每个页面,我必须进行所有这些查询——在我看来,这些查询应该在模型中处理。因此,我试图找出一种方法,将模型保存在一个位置,请求信息并将其返回给控制器。@user776796在我的项目中,我将模型放置在单独的文件中,这些文件在控制器之前加载。Mongoose的模型在我的模型中,我为常用的查询添加了快捷功能。这听起来像是我的设置方式。如何从快捷方式函数返回查询结果?@user776796我不返回结果,而是传递给传递给快捷方式函数的回调。@josh有办法访问第二个函数中第一个函数的结果吗?或者它们仅在回调中可用?@pkyeck如果您使用瀑布或其他串行方法,则可以。在本例中,这两种方法都允许使用process.nextTick并行运行,这意味着函数1的结果对函数2Async NPM不可用。它似乎非常强大,有时我们需要一些同步任务。这很有效,是一个非常好的答案(投票结果为:上),但是现在,我要说的是,对并行任务使用
async
有点过时了。考虑到这个解决方案是在2011年编写的,这是完全可以理解的。在处理异步任务时,承诺提供了更多的灵活性,我建议任何人在诉诸不同解决方案之前考虑使用它们(免责声明:我在这个线程中张贴了答案,说明了在这种情况下的用法)。有没有办法在“结果”上访问属性?如results.users或results.articles?您的梦想将在何时实现。您应该签出,使函数看起来像是同步执行的。要更好地了解此问题及其解决方案,请参阅
Promise.promisifyAll(mongoose);
Promise.props({
users: users.find().execAsync(),
articles: articles.find().execAsync()
})
var async = require('async');
// custom imports
var User = require('../models/user');
var Article = require('../models/article');
var List1Objects = User.find({});
var List2Objects = Article.find({});
var resourcesStack = {
usersList: List1Objects.exec.bind(List1Objects),
articlesList: List2Objects.exec.bind(List2Objects),
};
async.parallel(resourcesStack, function (error, resultSet){
if (error) {
res.status(500).send(error);
return;
}
res.render('home', resultSet);
});