如何在mongodb中取消设置除一个或两个之外的所有文档属性?
我有一个关于实体的文档集合,这些实体具有如何在mongodb中取消设置除一个或两个之外的所有文档属性?,mongodb,mongodb-query,Mongodb,Mongodb Query,我有一个关于实体的文档集合,这些实体具有状态属性,可以是1或0。每个文档都包含大量数据并占用空间。 我想删除状态为statusequal0的文档上的大部分数据 因此,我希望集合中的每个文档 { _id: 234, myCode: 101, name: "sfsdf", status: 0, and: 23243423.1, a: "dsf", lot: 3234, more: "efsfs", properties: "sdfsd"
状态
属性,可以是1
或0
。每个文档都包含大量数据并占用空间。
我想删除状态为status
equal0
的文档上的大部分数据
因此,我希望集合中的每个文档
{
_id: 234,
myCode: 101,
name: "sfsdf",
status: 0,
and: 23243423.1,
a: "dsf",
lot: 3234,
more: "efsfs",
properties: "sdfsd"
}
…要小得多
{
_id: 234,
mycode: 101,
status: 0
}
所以,基本上我能做到
db.getCollection('docs').update(
{'statusCode': 0},
{
$unset: {
and: "",
a: "",
lot: "",
more: "",
properties: ""
}
},
{multi:true}
)
但是有大约40个属性,这将是一个巨大的列表,而且我不确定所有的对象都遵循相同的模式
有没有办法取消设置除两个属性之外的所有属性?这里最好的做法是将所有可能的属性都抛出,让它完成它的工作。您不能“通配符”这样的参数,因此没有更好的方法不写入另一个集合 如果您不想将它们全部输入,甚至不想知道它们的全部,那么只需执行一个过程来“收集”所有其他顶级属性 例如,您可以使用
.mapReduce()
:
为您提供一个包含完整字段列表的对象,以作为:
这是从整个集合中所有可能的顶级字段中获取的
您可以使用MongoDB 3.4中的.aggregate()
使用$objectToArray
执行相同的操作:
var fields = db.getCollection('docs').aggregate([
{ "$project": {
"fields": {
"$filter": {
"input": { "$objectToArray": "$$ROOT" },
"as": "d",
"cond": {
"$and": [
{ "$ne": [ "$$d.k", "_id" ] },
{ "$ne": [ "$$d.k", "myCode" ] }
]
}
}
}
}},
{ "$unwind": "$fields" },
{ "$group": {
"_id": "$fields.k"
}}
]).map( o => o._id )
.reduce((acc,curr) => Object.assign(acc,{ [curr]: "" }),{});
无论您以何种方式获得姓名列表,只需将其发送至:
类似于Bottom的是,它不关心这些属性是否存在于文档中,只会在它们存在的地方删除它们
另一种情况是,如果符合您的需要,只需将所有内容写入新的集合。这是作为聚合管道阶段的简单使用:
db.getCollection('docs').aggregate([
{ "$match": { "statusCode": 0 } },
{ "$project": { "myCode": 1 } },
{ "$out": "newdocs" }
])
您应该只覆盖而不是取消设置。类似于
db.getCollection('docs').update({'statusCode':0},{{u id:234,mycode:101,status:0})
并使用批量写入。我想到了这一点,但有两个缺陷:1。覆盖不适用于multi
参数。2.我需要保留可能不同的mycode
s,我不知道如何使用此方法保存它们。抱歉,我仍在更新我的评论。再次检查。是的,但是如何保持各种mycode
s未被触动?
var fields = db.getCollection('docs').aggregate([
{ "$project": {
"fields": {
"$filter": {
"input": { "$objectToArray": "$$ROOT" },
"as": "d",
"cond": {
"$and": [
{ "$ne": [ "$$d.k", "_id" ] },
{ "$ne": [ "$$d.k", "myCode" ] }
]
}
}
}
}},
{ "$unwind": "$fields" },
{ "$group": {
"_id": "$fields.k"
}}
]).map( o => o._id )
.reduce((acc,curr) => Object.assign(acc,{ [curr]: "" }),{});
db.getCollection('docs').update(
{ "statusCode": 0 },
{ "$unset": fields },
{ "multi": true }
)
db.getCollection('docs').aggregate([
{ "$match": { "statusCode": 0 } },
{ "$project": { "myCode": 1 } },
{ "$out": "newdocs" }
])