概览:
我正在处理的文档中有两个嵌套数组 - contentMetaData 和 text_content。
在 contentMetaData 中,我们有 text_content 和 content_flag。根据 content_flag 的值,我需要隐藏 text_content 中的特定字段。
要求:
content_flag 为真,text_content 应该有一个 child - text_note。content_flag 为 false,则 text_content 应该有一个 child - text_description。使用的版本: Mongo 2.6
示例文档:
{
"_id": ObjectId("56f8dd19e4b0365115927b0f"),
"contentId": "cbc91805-2faa-4eff-8f84-02547173c152",
"contentMetaData": [
{
"_id": "1574b58f-b7fa-4cd5-b34f-98beeb657c97",
"name": "text_content",
"attributes": [],
"children": [
{
"_id": "97340ecf-fdbd-41e5-a6b2-01cc542f16ee",
"name": "text_note",
"value": "abc",
"type": "java.lang.String",
"attributes": [],
"children": [],
"noOfChildren": 0,
"positionIndex": 1
},
{
"_id": "19c5a3fb-54a2-4368-a89d-ea1d2554402d",
"name": "text_description",
"value": "def",
"type": "java.lang.String",
"attributes": [],
"children": [],
"noOfChildren": 0,
"positionIndex": 2
}
],
"noOfChildren": 2,
"positionIndex": 1
},
{
"_id": "4e8ef7c9-cffd-4b36-9109-89b263dff3c8",
"name": "content_flag",
"value": "true",
"type": "java.lang.String",
"attributes": [],
"children": [],
"noOfChildren": 0,
"positionIndex": 2
}
]
}
示例输出:
{
"_id": ObjectId("56f8dd19e4b0365115927b0f"),
"contentId": "cbc91805-2faa-4eff-8f84-02547173c152",
"contentMetaData": [
{
"_id": "1574b58f-b7fa-4cd5-b34f-98beeb657c97",
"name": "text_content",
"attributes": [],
"children": [
{
"_id": "97340ecf-fdbd-41e5-a6b2-01cc542f16ee",
"name": "text_note",
"value": "abc",
"type": "java.lang.String",
"attributes": [],
"children": [],
"noOfChildren": 0,
"positionIndex": 1
}
],
"noOfChildren": 2,
"positionIndex": 1
},
{
"_id": "4e8ef7c9-cffd-4b36-9109-89b263dff3c8",
"name": "content_flag",
"value": "true",
"type": "java.lang.String",
"attributes": [],
"children": [],
"noOfChildren": 0,
"positionIndex": 2
}
]
}
我尝试使用 $map 但它没有用。我尝试使用 $unwind,但无法以所需格式$push 返回数据。
示例 Mongo 代码:
db.content.aggregate([
{
$project: {
_id: 1,
contentId: 1,
contentMetaData: 1
tempMetaData: "$contentMetaData"
}
},
{
$unwind: "$contentMetaData"
},
{
$match: {
"contentMetaData.name": "content_flag"
}
},
{
$project: {
_id: 1,
contentId: 1,
contentMetaData: "$tempMetaData",
content_flag_value: "$contentMetaData.value"
}
},
{
$project: {
_id: 1,
contentId: 1,
contentMetaData: 1,
tempMetaData: "$contentMetaData",
content_flag_value: 1
}
},
{
$unwind: "$contentMetaData"
},
{
$match: {
"contentMetaData.name": "text_content"
}
},
{
$project: {
_id: 1,
contentId: 1,
contentMetaData: 1,
tempMetaData: "$contentMetaData",
content_flag_value: 1,
text_content : "$contentMetaData.children",
temp_text_content: "$text_content"
}
},
{
$unwind: "$text_content"
},
{
$group:{
_id:"$_id",
contentId:{$first:"$contentId"},
text_content:
{$max:
{$cond:
[
{$eq: ["$content_flag_value", "true"]},
{$cond:
[{$or:[
{$eq: ["$text_content.name","wk_link_url"]},
{$eq: ["$text_content.name","wk_link_description"]}
]},
"$text_content",
null]
},
null
]
}
},
contentMetaData:{$first:"$contentMetaData"}
}
},
{
$group:{
_id:"$_id",
contentId:{$first:"$contentId"},
contentMetaData:{$push:{"text_content":"$text_content"}}
}
},
{
$project: {
_id: 0,
contentId: 1,
contentMetaData: 1
}
}]).pretty()
我是 Mongo 的新手。有人可以帮我解决这个问题吗?
最佳答案
您可以尝试以下聚合。
$map 结合 $setDifference 提取 text_content 和 content_flag 数组。
$unwind 到 content_flag 文档。
$map 将当前值保存在 text_content 和 $map 中,结合 $setDifference 进行过滤标准上的 children。
$setUnion 将 text_content 和 content_flag 数组加入到 contentMetaData
db.collection.aggregate({
$project: {
_id: 1,
contentId: 1,
text_content: {
"$setDifference": [{
"$map": {
"input": "$contentMetaData",
"as": "text",
"in": {
"$cond": [{
$eq: ['$$text.name', "text_content"]
},
"$$text",
false
]
}
}
},
[false]
]
},
content_flag: {
"$setDifference": [{
"$map": {
"input": "$contentMetaData",
"as": "content",
"in": {
"$cond": [{
$eq: ['$$content.name', "content_flag"]
},
"$$content",
false
]
}
}
},
[false]
]
}
}
}, {
$unwind: "$content_flag"
}, {
$project: {
"_id": 1,
contentId: 1,
"contentMetaData": {
$setUnion: [{
$map: {
input: "$text_content",
as: "text",
in: {
"_id": "$$text._id",
"name": "$$text.name",
"attributes": "$$text.attributes",
"noOfChildren": "$$text.noOfChildren",
"positionIndex": "$$text.positionIndex",
"children": {
"$setDifference": [{
"$map": {
"input": "$$text.children",
"as": "child",
"in": {
"$cond": [{
"$cond": [{
$eq: ["$content_flag.value", "true"]
}, {
$eq: ["$$child.name", "text_note"]
}, {
$eq: ["$$child.name", "text_description"]
}]
},
"$$child",
false
]
}
}
},
[false]
]
}
}
}
},
["$content_flag"]
]
}
}
})
更新:
$map 结合 $setDifference 提取 content_flag 数组。
$unwind 到 content_flag 文档。
$redact 一次遍历文档级别并递归查找 name 字段并执行 $$DESCEND 和 $$PRUNE 标准。
$project 格式化最终响应。
db.collection.aggregate({
$project: {
_id: 1,
contentId: 1,
contentMetaData: 1,
content_flag: {
"$setDifference": [{
"$map": {
"input": "$contentMetaData",
"as": "content",
"in": {
"$cond": [{
$eq: ['$$content.name', "content_flag"]
},
"$$content",
false
]
}
}
},
[false]
]
}
}
}, {
$unwind: "$content_flag"
}, {
$redact: {
$cond: [{
$or: [{
$eq: ["$name", "text_content"]
}, {
$not: "$name"
}, {
$eq: ["$name", "content_flag"]
}, {
$and: [{
$eq: ["$name", "text_note"]
}, {
$eq: ["$$ROOT.content_flag.value", "true"]
}]
}, {
$and: [{
$eq: ["$name", "text_description"]
}, {
$eq: ["$$ROOT.content_flag.value", "false"]
}]
}]
},
"$$DESCEND",
"$$PRUNE"
]
}
}, {
$project: {
_id: 1,
contentId: 1,
contentMetaData: 1
}
});
关于mongodb - 根据其他字段的值投影数组中存在的特定字段,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41893098/
我试图在一个项目中使用rake,如果我把所有东西都放到Rakefile中,它会很大并且很难读取/找到东西,所以我试着将每个命名空间放在lib/rake中它自己的文件中,我添加了这个到我的rake文件的顶部:Dir['#{File.dirname(__FILE__)}/lib/rake/*.rake'].map{|f|requiref}它加载文件没问题,但没有任务。我现在只有一个.rake文件作为测试,名为“servers.rake”,它看起来像这样:namespace:serverdotask:testdoputs"test"endend所以当我运行rakeserver:testid时
我有多个ActiveRecord子类Item的实例数组,我需要根据最早的事件循环打印。在这种情况下,我需要打印付款和维护日期,如下所示:ItemAmaintenancerequiredin5daysItemBpaymentrequiredin6daysItemApaymentrequiredin7daysItemBmaintenancerequiredin8days我目前有两个查询,用于查找maintenance和payment项目(非排他性查询),并输出如下内容:paymentrequiredin...maintenancerequiredin...有什么方法可以改善上述(丑陋的)代
我正在寻找执行以下操作的正确语法(在Perl、Shell或Ruby中):#variabletoaccessthedatalinesappendedasafileEND_OF_SCRIPT_MARKERrawdatastartshereanditcontinues. 最佳答案 Perl用__DATA__做这个:#!/usr/bin/perlusestrict;usewarnings;while(){print;}__DATA__Texttoprintgoeshere 关于ruby-如何将脚
我的代码目前看起来像这样numbers=[1,2,3,4,5]defpop_threepop=[]3.times{pop有没有办法在一行中完成pop_three方法中的内容?我基本上想做类似numbers.slice(0,3)的事情,但要删除切片中的数组项。嗯...嗯,我想我刚刚意识到我可以试试slice! 最佳答案 是numbers.pop(3)或者numbers.shift(3)如果你想要另一边。 关于ruby-多次弹出/移动ruby数组,我们在StackOverflow上找到一
我需要读入一个包含数字列表的文件。此代码读取文件并将其放入二维数组中。现在我需要获取数组中所有数字的平均值,但我需要将数组的内容更改为int。有什么想法可以将to_i方法放在哪里吗?ClassTerraindefinitializefile_name@input=IO.readlines(file_name)#readinfile@size=@input[0].to_i@land=[@size]x=1whilex 最佳答案 只需将数组映射为整数:@land边注如果你想得到一条线的平均值,你可以这样做:values=@input[x]
我正在使用puppet为ruby程序提供一组常量。我需要提供一组主机名,我的程序将对其进行迭代。在我之前使用的bash脚本中,我只是将它作为一个puppet变量hosts=>"host1,host2"我将其提供给bash脚本作为HOSTS=显然这对ruby不太适用——我需要它的格式hosts=["host1","host2"]自从phosts和putsmy_array.inspect提供输出["host1","host2"]我希望使用其中之一。不幸的是,我终其一生都无法弄清楚如何让它发挥作用。我尝试了以下各项:我发现某处他们指出我需要在函数调用前放置“function_”……这
我有一个表单,其中有很多字段取自数组(而不是模型或对象)。我如何验证这些字段的存在?solve_problem_pathdo|f|%>... 最佳答案 创建一个简单的类来包装请求参数并使用ActiveModel::Validations。#definedsomewhere,atthesimplest:require'ostruct'classSolvetrue#youcouldevencheckthesolutionwithavalidatorvalidatedoerrors.add(:base,"WRONG!!!")unlesss
我想向我的Controller传递一个参数,它是一个简单的复选框,但我不知道如何在模型的form_for中引入它,这是我的观点:{:id=>'go_finance'}do|f|%>Transferirde:para:Entrada:"input",:placeholder=>"Quantofoiganho?"%>Saída:"output",:placeholder=>"Quantofoigasto?"%>Nota:我想做一个额外的复选框,但我该怎么做,模型中没有一个对象,而是一个要检查的对象,以便在Controller中创建一个ifelse,如果没有检查,请帮助我,非常感谢,谢谢
这个问题在这里已经有了答案:Checktoseeifanarrayisalreadysorted?(8个答案)关闭9年前。我只是想知道是否有办法检查数组是否在增加?这是我的解决方案,但我正在寻找更漂亮的方法:n=-1@arr.flatten.each{|e|returnfalseife
我有一个这样的哈希数组:[{:foo=>2,:date=>Sat,01Sep2014},{:foo2=>2,:date=>Sat,02Sep2014},{:foo3=>3,:date=>Sat,01Sep2014},{:foo4=>4,:date=>Sat,03Sep2014},{:foo5=>5,:date=>Sat,02Sep2014}]如果:date相同,我想合并哈希值。我对上面数组的期望是:[{:foo=>2,:foo3=>3,:date=>Sat,01Sep2014},{:foo2=>2,:foo5=>5:date=>Sat,02Sep2014},{:foo4=>4,:dat