Mongodb查询查找子目录和查询

时间:2018-02-15 06:44:56

标签: mongodb mongoose mongodb-query

我有一个Job Schema和一个应用程序架构。应用程序架构已嵌入到作业架构中。这就像申请这项特殊工作的候选人一样

{
        "_id" : ObjectId("5a745a49e4a4d9203cf506ed"),
        "active" : true,
        "applications" : [ 
            {
                "applied" : true,
                "shortlisted" : true,
                "interviewed" : false,
                "offered" : false,
                "hired" : false,
                "rejected" : false,
                "candId":1
            }, 
            {
                "applied" : true,
                "shortlisted" : false,
                "interviewed" : false,
                "offered" : false,
                "hired" : false,
                "rejected" : false,
                "candId":2
            }, 
            {
                "applied" : true,
                "shortlisted" : false,
                "interviewed" : false,
                "offered" : false,
                "hired" : false,
                "rejected" : false,
                "candId":3
            }, 
            {
                "applied" : true,
                "shortlisted" : false,
                "interviewed" : false,
                "offered" : false,
                "hired" : false,
                "rejected" : false,
                "candId":4
            }
        ],
        "job_title" : "MERN Stack developer",
        "job_description" : "<p>If more than one component needs to make use of this, we have to either duplicate the function, or extract it into a shared helper and import it in multiple places - both are less than ideal.</p><p>Vuex allows us to define \"getters\" in the store. You can think of them as computed properties for stores. Like computed properties, a getter's result is cached based on its dependencies, and will only re-evaluate when some of its dependencies have changed.</p><p>Getters will receive the state as their 1st argument:</p>",
        "max_experience" : 3,
        "max_salary" : 4,
        "min_experience" : 2,
        "min_salary" : 3
    }

在我的申请中,我有候选人经历过的阶段(申请,入围,受访,提供......)

所以我想写一个查询,它会给我一个应用阶段的结果

           {
                "applied" : true,
                "shortlisted" : false,
                "interviewed" : false,
                "offered" : false,
                "hired" : false,
                "rejected" : false,
                "candId":2
            }, 
            {
                "applied" : true,
                "shortlisted" : false,
                "interviewed" : false,
                "offered" : false,
                "hired" : false,
                "rejected" : false,
                "candId":3
            }, 
            {
                "applied" : true,
                "shortlisted" : false,
                "interviewed" : false,
                "offered" : false,
                "hired" : false,
                "rejected" : false,
                "candId":4

            }

基本上只有应用应该设置为true而其他应用设置为false

并列入候选名单

           {
                "applied" : true,
                "shortlisted" : true,
                "interviewed" : false,
                "offered" : false,
                "hired" : false,
                "rejected" : false,
                "candId":1
            } 

查询结果与工作或没有工作没关系

修改

Job.find({
    _id : req.params.id,
    'applications.applied': req.body.applied,
    'applications.shortlisted' : req.body.shortlisted,
    'applications.interviewed' : req.body.interviewed,
    'applications.offered' : req.body.offered,
    'applications.hired' : req.body.hired,
    'applications.rejected' : req.body.rejected
  }).populate('applications.talentId').then((job, err) => {
    if(err){
      return res.status(500).send({error: "There was some error"})
    }
    res.status(200).json(job)
  })

我正在使用每个阶段的所有应用程序获得整个作业对象

3 个答案:

答案 0 :(得分:0)

您可以使用以下聚合

db.jobs.aggregate([
    { $match: { _id : ObjectId("5a745a49e4a4d9203cf506ed") } },
    { $unwind: "$applications" },
    {
        $replaceRoot: {
            newRoot: "$applications"
        }
    },
    {
        $match: {
            applied: true
        }
    }
])

基本上,为了过滤嵌套集合,您可以先使用$unwindapplications数组的每个元素分别创建文档。然后,您可以使用$replaceRoot重新整形它们,最终只有单个应用程序,然后您可以使用$ match来过滤它们,就好像它们是单个文档一样。您可以根据业务需求为$ match添加更多条件。

编辑:

  • $ uwind获取n个文档的嵌套数组,并返回n个文档,每个文档中包含该嵌套数组的一个元素。
  • $ replaceRoot只是简化每个文档,以便嵌套的子文档成为新的根(这里用来摆脱不必要的属性)

答案 1 :(得分:0)

对于applied:检查applied是否为真且shortlisted为假。

对于shortlisted:检查shortlisted是否为真且interviewed为假。

依旧......

您检查该阶段是true,下一阶段是false

例如,对于applied阶段的人,查询将是:

Job.find({"_id" : ObjectId("5a745a49e4a4d9203cf506ed"),
          applications: {$elemMatch: {applied: true, shortlisted: false}}}, 
         {applications: 1})

要查看应用阶段候选人,您必须使用聚合:

Job.aggregate([{$match: {_id: ObjectId("5a745a49e4a4d9203cf506ed") /* first match the job Id */ }},
               {$unwind: '$applications' /* expand the array */}, 
               {$match: {'applications.applied': true, 'applications.shortlisted': false}}])

答案 2 :(得分:0)

db.Job.aggregate(

    // Pipeline
    [
        // Stage 1
        {
            $unwind: {
                path: "$applications",
                preserveNullAndEmptyArrays: true // optional
            }
        },

        // Stage 2
        {
            $match: {
                'applications.applied': true,
                'applications.shortlisted': false,
                'applications.interviewed': false,
                'applications.offered': false,
                'applications.hired': false,
                'applications.hired': false,
                'applications.rejected': false
            }
        },

    ]



);