dth2331 2016-05-20 11:11
浏览 60
已采纳

如何在mgo中对数组元素进行多级拉取?

I want to do a multi-level array element delete. My Structs are as follows:-

type Company struct {
    Id              bson.ObjectId `bson:"_id,omitempty"`
    CompanyName     string
    Process         []ProcessItem
}

type ProcessItem  struct{
    SortOrder       int
    Documents       []DocumentTemplate
}

type DocumentTemplate struct {
    Id              bson.ObjectId `bson:"_id,omitempty"`
    TemplateName    string
}

I want to delete an object of type DocumentTemplate. The DocumentTemplate is a struct array in ProcessItem which is a struct array in Company struct. I have Company Id(field of struct Company) and TemplateName(field of struct DocumentTemplate).

I tried the below mgo pull query but it is not working.

c := db.C("company")
pullQuery := bson.M{"process": bson.M{"documents.templatename": "xyz"}}
err := c.Update(bson.M{"_id": "123"}, bson.M{"$pull": pullQuery})

Please point out the mistakes I made here. Thanks.

Edit: Adding one example document for the clarity of the question

{
    "_id" : ObjectId("573da7dddd73171e42a84045"),
    "companyname" : "AAA",
    "process" : [ 
        {
            "processname" : "Enquiry",
            "sortorder" : 0,
            "documents" : [ 
                {
                    "templatename" : "xyz",
                    "processname" : "Enquiry"
                }, 
                {
                    "templatename" : "ss",
                    "processname" : "Enquiry"
                }
            ]
        }, 
        {
            "processname" : "Converted",
            "processtype" : 1,
            "sortorder" : 2,
            "documents" : [ 
                {
                    "templatename" : "dd",
                    "processname" : "Converted"
                }, 
                {
                    "templatename" : "fg",
                    "processname" : "Converted"
                }
            ]
        }
    ]
}

I need to pull out just one DocumentTemplete record, like the one below:

{
   "templatename" : "xyz",
   "processname" : "Enquiry"
}

N.B: TemplateName will be unique inside a Company.

  • 写回答

2条回答 默认 最新

  • duanliang1898 2016-05-20 12:10
    关注

    You'll need to use the $ positional operator (https://docs.mongodb.com/manual/reference/operator/projection/positional/). In order to be able to use that you'll also have to add to your query the following:

    "process.documents.templatename": "xyz"
    

    Your Update statement should look like this:

    c := db.C("company")
    pullQuery := bson.M{"process.$.documents": bson.M{"templatename": "xyz"}}
    err := c.Update(bson.M{"_id": "123", "process.documents.templatename": "xyz"}, bson.M{"$pull": pullQuery})
    
    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论
查看更多回答(1条)

报告相同问题?

悬赏问题

  • ¥15 ros的rviz仿真机器人
  • ¥15 关于#linux#的问题(输入输出错误):出现这个界面接着我重新装系统,又让修电脑的师傅帮我扫描硬盘(没有问题)用着用着又卡死(相关搜索:固态硬盘)
  • ¥15 cv::resize不同线程时间不同
  • ¥15 web课程,怎么做啊😭没好好听课 根本不知道怎么下手
  • ¥15 做一个关于单片机的比较难的代码,然后搞一个PPT进行解释
  • ¥15 python提取.csv文件中的链接会经常出现爬取失败
  • ¥15 数据结构中的数组地址问题
  • ¥15 maya的mel里,怎样先选择模型A,然后利用mel脚本自动选择有相同名字的模型B呢。
  • ¥15 Python题,根本不会啊
  • ¥15 会会信号与系统和python的来