bym*_*nan 5 mongodb mongoid aggregation-framework
按照@NeilLunn优雅回答的这个问题,这是我的问题更详细.
这是一组文件,有些没有user_id.user_id表示创建文档的用户:
{ "user_id" : 11, "content" : "black", "date": somedate }
{ "user_id" : 6, "content" : "blue", "date": somedate }
{ "user_id" : 3, "content" : "red", "date": somedate }
{ "user_id" : 4, "content" : "black", "date": somedate }
{ "user_id" : 4, "content" : "blue", "date": somedate }
{ "user_id" : 90, "content" : "red", "date": somedate }
{ "user_id" : 7, "content" : "orange", "date": somedate }
{ "content" : "orange", "date": somedate }
{ "content" : "red", "date": somedate }
...
{ "user_id" : 4, "content" : "orange", "date": somedate }
{ "user_id" : 1, "content" : "orange", "date": somedate }
{ "content" : "red", "date": somedate }
{ "user_id" : 90, "content" : "purple", "date": somedate }
Run Code Online (Sandbox Code Playgroud)
前端是拉页面,所以每个页面都有10个项目,我用限制和跳过这样做,它运行得很好.
如果我们有一个登录用户,我想显示当前登录的用户文档,根据他与之交互的用户,他可能会首先发现这些文档更有趣.
当前用户可能感兴趣的用户列表按分数排序,位于mongo之外.所以第一个元素是我想要首先显示他的文档的最重要的用户,列表中的最后一个用户是最不重要的.
该列表是一个简单的数组,如下所示:[4,7,90,1].
创建此用户得分的系统不在mongo内,但如果有帮助,我可以复制数据.我也可以更改数组以包含分数.
我想要完成的是以下内容:
从列表中获取按user_id的重要性排序的文档,以便来自user_id 4的文档将是第一个显示的文档,来自user_id的文档是7秒,依此类推.如果列表中没有用户,我希望显示其余文档.像这样:
我该怎么做到这一点?我是从mongo那里问过多吗?
给定数组[4,7,90,1]你想要的查询是这样的:
db.collection.aggregate([
{ "$project": {
"user_id": 1,
"content": 1,
"date": 1,
"weight": { "$or": [
{ "$eq": ["$user_id": 4] },
{ "$eq": ["$user_id": 7] },
{ "$eq": ["$user_id": 90] },
{ "$eq": ["$user_id": 1] },
]}
}},
{ "$sort": { "weight": -1, "date": -1 } }
])
Run Code Online (Sandbox Code Playgroud)
那样做的是,对于该$or条件中包含的每个项目,该user_id字段将根据提供的值进行测试,并$eq返回1或0为true或false.
您在代码中执行的操作是针对您构建数组条件的数组中的每个项目$or.所以它只是为每个equals条件创建一个哈希结构,将它传递给一个数组并将其作为$or条件的数组值插入.
我可能应该将$ cond运算符从前面的代码中删除,所以这部分会更清楚.
这是Ruby Brain的一些代码:
userList = [4, 7, 90, 1];
orCond = [];
userList.each do |userId|
orCond.push({ '$eq' => [ 'user_id', userId ] })
end
pipeline = [
{ '$project' => {
'user_id' => 1,
'content' => 1,
'date' => 1,
'weight' => { '$or' => orCond }
}},
{ '$sort' => { 'weight' => -1, 'date' => -1 } }
]
Run Code Online (Sandbox Code Playgroud)
如果你想拥有单独的权重,我们将假设键值对,那么你需要使用$ cond嵌套:
db.collection.aggregate([
{ "$project": {
"user_id": 1,
"content": 1,
"date": 1,
"weight": { "$cond": [
{ "$eq": ["$user_id": 4] },
10,
{ "$cond": [
{ "$eq": ["$user_id": 7] },
9,
{ "$cond": [
{ "$eq": ["$user_id": 90] },
7,
{ "$cond": [
{ "$eq": ["$user_id": 1] },
8,
0
]}
]}
]}
]}
}},
{ "$sort": { "weight": -1, "date": -1 } }
])
Run Code Online (Sandbox Code Playgroud)
请注意,它只是一个返回值,这些不需要按顺序排列.你可以考虑一下这一代.
要生成此结构,请参见此处: