我正在用Node.js和猫鼬编写一个webapp。如何对.find()
通话结果进行分页?我想要一个与"LIMIT 50,100"
SQL 相当的功能。
如何在Node.js中对Mongoose进行分页?
您可以这样编写查询。
mySchema.find().skip((page-1)*per_page).limit(per_page).exec(function(err, articles) {
if (err) {
return res.status(400).send({
message: err
});
} else {
res.json(articles);
}
});
page:来自客户端的页码,作为请求参数。
per_page:每页显示的结果数
如果您使用的是MEAN堆栈,则以下博客文章提供了许多信息,这些信息可用于在前端使用angular-UI引导程序创建分页,并在后端使用猫鼬跳过和限制方法。
参见:https : //techpituwa.wordpress.com/2015/06/06/mean-js-pagination-with-angular-ui-bootstrap/
您可以使用skip()和limit(),但是效率很低。更好的解决方案是对索引字段加limit()进行排序。Wunderflats的我们在这里发布了一个小型库:https : //github.com/wunderflats/goosepage 它使用第一种方法。
简单而强大的分页解决方案
async getNextDocs(no_of_docs_required: number, last_doc_id?: string) {
let docs
if (!last_doc_id) {
// get first 5 docs
docs = await MySchema.find().sort({ _id: -1 }).limit(no_of_docs_required)
}
else {
// get next 5 docs according to that last document id
docs = await MySchema.find({_id: {$lt: last_doc_id}})
.sort({ _id: -1 }).limit(no_of_docs_required)
}
return docs
}
last_doc_id
:您获得的最后一个文档ID
no_of_docs_required
:您要提取的文档数,即5、10、50等。
- 如果您不向
last_doc_id
方法提供,则将获得5份最新文档 - 如果提供了,
last_doc_id
那么您将获得接下来的5个文档。
最简单,最快捷的方法是,使用objectId示例进行分页;
初始负载条件
condition = {limit:12, type:""};
从响应数据中获取第一个和最后一个ObjectId
页面下一个条件
condition = {limit:12, type:"next", firstId:"57762a4c875adce3c38c662d", lastId:"57762a4c875adce3c38c6615"};
页面下一个条件
condition = {limit:12, type:"next", firstId:"57762a4c875adce3c38c6645", lastId:"57762a4c875adce3c38c6675"};
在猫鼬
var condition = {};
var sort = { _id: 1 };
if (req.body.type == "next") {
condition._id = { $gt: req.body.lastId };
} else if (req.body.type == "prev") {
sort = { _id: -1 };
condition._id = { $lt: req.body.firstId };
}
var query = Model.find(condition, {}, { sort: sort }).limit(req.body.limit);
query.exec(function(err, properties) {
return res.json({ "result": result);
});
您也可以使用以下代码行
per_page = parseInt(req.query.per_page) || 10
page_no = parseInt(req.query.page_no) || 1
var pagination = {
limit: per_page ,
skip:per_page * (page_no - 1)
}
users = await User.find({<CONDITION>}).limit(pagination.limit).skip(pagination.skip).exec()
该代码将在最新版本的mongo中工作
这是一个示例示例,您可以尝试一下,
var _pageNumber = 2,
_pageSize = 50;
Student.count({},function(err,count){
Student.find({}, null, {
sort: {
Name: 1
}
}).skip(_pageNumber > 0 ? ((_pageNumber - 1) * _pageSize) : 0).limit(_pageSize).exec(function(err, docs) {
if (err)
res.json(err);
else
res.json({
"TotalCount": count,
"_Array": docs
});
});
});
在这种情况下,您可以将查询page
和/或添加为limit
URL作为查询字符串。
例如:
?page=0&limit=25 // this would be added onto your URL: http:localhost:5000?page=0&limit=25
由于它将是a,因此String
我们需要将其转换为a Number
进行计算。让我们使用parseInt
方法进行操作,并提供一些默认值。
const pageOptions = {
page: parseInt(req.query.page, 10) || 0,
limit: parseInt(req.query.limit, 10) || 10
}
sexyModel.find()
.skip(pageOptions.page * pageOptions.limit)
.limit(pageOptions.limit)
.exec(function (err, doc) {
if(err) { res.status(500).json(err); return; };
res.status(200).json(doc);
});
BTW
分页始于0
在通过Rodolphe提供的信息仔细研究了Mongoose API之后,我想出了以下解决方案:
MyModel.find(query, fields, { skip: 10, limit: 5 }, function(err, results) { ... });
如果您使用猫鼬作为静态 API的来源,请查看“ restify-mongoose ”及其查询。它完全内置了此功能。
集合上的任何查询都提供了在这里有用的标题
因此,基本上,您将获得具有相对线性加载时间的通用服务器,用于查询集合。如果您想进入自己的实现中,那真是太棒了。