Mgo如何在嵌套数组中查找嵌套文档?

下面我设计的文档结构如下:


type MIS_Course struct {

    ID   bson.ObjectId `bson:"_id,omitempty"`

    Name string        `bson:"crse_name"`

}


type MIS_Department struct {

    ID      bson.ObjectId `bson:"_id,omitempty"`

    Name    string        `bson:"dept_name"`

    Courses []MIS_Course  `bson:"crse_list"`

}


type MIS_School struct {

    ID          bson.ObjectId    `bson:"_id,omitempty"`

    Name        string           `bson:"school_name"`

    Departments []MIS_Department `bson:"dept_list"`

}

初始化后,我会在众多学校中拥有一个“学校 ABC”,其中包含如下所示的内容:


{

    "_id" : ObjectId("55fbb522022aae7b3a000003"),

    "school_name" : "School ABC",

    "dept_list" : [

        {

            "dept_name" : "Department A",

            "crse_list" : [

                {

                    "crse_name" : "Class A"

                },

                {

                    "crse_name" : "Class B"

                },

            ]

        }

    ]

}

几个小时以来,我找不到通过给定 school_name、dept_name 和 crse_name 有效工作的解决方案:


找到dept_list的school_name>找到crse_list的dept_name>查找crse_name


之所以需要这样的发现链,是因为发现的范围应该仅限于学校,然后是部门。逻辑和内务处理发生在发现的每个阶段之后。


我试过代码,如


result := MIS_School{}


err := database.C("schools").Find(bson.M{"school_name": school}).Select(

bson.M{"dept_list": bson.M{"$elemMatch": bson.M{"dept_name": dept}}}).Select(

bson.M{"crse_list": bson.M{"$elemMatch": bson.M{"crse_name": crse}}}).One(&result)

但它不起作用,因为 Select 投影不能在 Mgo(?)


我从某处读到 mongodb 没有能力直接检索嵌套在深度超过 1-2 级的数组中的文档(在 A 数组中的 B 数组中获取文档 C)。真的吗?我该如何解决这个问题?


慕丝7291255
浏览 176回答 2
2回答

吃鸡游戏

您可以链接 Select 语句,但第二个调用的值将覆盖第一个调用的值,而不是执行示例所暗示的操作,即深入了解嵌套结构。为了实现您显然想要做的事情,您可以使用聚合框架以任意方式操作这些嵌套对象。例如,这是一个简单的管道,可以提取出完全匹配的课程:    pipeline := []bson.M{            {"$match": bson.M{"school_name": school}},            {"$unwind": "$dept_list"},            {"$unwind": "$dept_list.crse_list"},            {"$match": bson.M{                     "dept_list.dept_name": dept,                     "dept_list.crse_list.crse_name": crse,            }},    }    iter := coll.Pipe(pipeline).Iter()您可以像使用 Find 中的迭代器一样使用生成的迭代器。对于此管道,生成的对象将如下所示:    bson.M{            "_id":"...",            "dept_list": bson.M{                    "dept_name": "Department A",                       "crse_list": bson.M{                            "crse_name": "Class B",                    }            },            "school_name":"School ABC",    }不过,您可以以任意方式更改结果对象的形状。有关更多详细信息,请查看聚合框架文档。

largeQ

阅读蒙戈文档后,我认为做嵌套关系的首选方法是用物化路径用树形结构描述这里的蒙戈。还可以使用祖先和父/子引用数组的树。看一看。似乎使用树更简单、更优雅,并且省去了很多技术麻烦。
打开App,查看更多内容
随时随地看视频慕课网APP

相关分类

Go