MongoDB聚合中的Mongoose虚拟 [英] Mongoose Virtuals in MongoDB Aggregate

查看:58
本文介绍了MongoDB聚合中的Mongoose虚拟的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我的猫鼬模式如下:

var DSchema = new mongoose.Schema({
  original_y: {type: Number},,
  new_y: {type: Number},,
  date: {type: Date},
  dummy: [dummyEmbeddedDocuments]
  }, toObject: { virtuals: true }, toJSON: { virtuals: true}
});

DSchema.virtual('dateformatted').get(function () {
 return moment(this.date).format('YYYY-MM-DD HH:mm:ss');
});

module.exports = mongoose.model('D', DSchema);

我的架构中的文档如下:

{
 id:1,
 original_y: 200,
 new_y: 140,
 date: 2015-05-03 00:00:00.000-18:30,
 dummy: [
  {id:1, storage:2, cost: 10},
  {id:2, storage:0, cost: 20},
  {id:3, storage:5, cost: 30},
  ]
}

我的查询:

Item.aggregate([
{ 
    "$match": {
        "dummy.storage": {"$gt": 0}
    } 
},
{ 
    "$unwind": "$dummy"
},
{
    "$project": {
        "original_y": 1, 
        "new_y": 1,
        "dateformatted": 1,
        "dummy.id": "$dummy.id",
        "dummy.storage": "$dummy.storage",
        "dummy.cost": "$dummy.cost",
        "dummy.tallyAmount": {
            "$divide": [
                { "$add": ["$new_y","$original_y"] },
                "$dummy.cost"
            ]
        }
    }
},
{
    "$group": {
        "_id": "_$id",
        "original_y": { "$first": "$original_y" },
        "dateformatted": { "$first": "$dateformatted" },
        "new_y": { "$first": "$new_y" },
        "dummy": {
            "$addToSet": "$dummy"
        }
    }        
}
]).exec(callback);

此查询将 VIRTUAL 日期格式的属性返回为NULL.为什么会这样呢?

解决方案

文档谈谈这样做的原因:

  • 参数不转换为模型的架构,因为$project运算符允许在任何阶段重新定义文档的形状" 管道,可能会使文档格式不兼容.
  • 返回的文档是纯JavaScript对象,不是猫鼬文档(因为可以返回任何形状的文档).

但是它不止于此,因为aggregate操作是在服务器端执行的,在该服务器端,不存在任何客户端Mongoose概念(例如虚拟).

结果是,您需要在$project$group阶段中包含date字段,并根据date值在代码中将自己的dateformatted字段添加到结果中. /p>

My Mongoose Schema is as follows:

var DSchema = new mongoose.Schema({
  original_y: {type: Number},,
  new_y: {type: Number},,
  date: {type: Date},
  dummy: [dummyEmbeddedDocuments]
  }, toObject: { virtuals: true }, toJSON: { virtuals: true}
});

DSchema.virtual('dateformatted').get(function () {
 return moment(this.date).format('YYYY-MM-DD HH:mm:ss');
});

module.exports = mongoose.model('D', DSchema);

A document in my schema would be the following:

{
 id:1,
 original_y: 200,
 new_y: 140,
 date: 2015-05-03 00:00:00.000-18:30,
 dummy: [
  {id:1, storage:2, cost: 10},
  {id:2, storage:0, cost: 20},
  {id:3, storage:5, cost: 30},
  ]
}

My Query:

Item.aggregate([
{ 
    "$match": {
        "dummy.storage": {"$gt": 0}
    } 
},
{ 
    "$unwind": "$dummy"
},
{
    "$project": {
        "original_y": 1, 
        "new_y": 1,
        "dateformatted": 1,
        "dummy.id": "$dummy.id",
        "dummy.storage": "$dummy.storage",
        "dummy.cost": "$dummy.cost",
        "dummy.tallyAmount": {
            "$divide": [
                { "$add": ["$new_y","$original_y"] },
                "$dummy.cost"
            ]
        }
    }
},
{
    "$group": {
        "_id": "_$id",
        "original_y": { "$first": "$original_y" },
        "dateformatted": { "$first": "$dateformatted" },
        "new_y": { "$first": "$new_y" },
        "dummy": {
            "$addToSet": "$dummy"
        }
    }        
}
]).exec(callback);

This query however returns the VIRTUAL dateformatted attribute as NULL. Any thoughts as to why this is happening?

解决方案

A couple notes in the docs touch on why this is so:

  • Arguments are not cast to the model's schema because $project operators allow redefining the "shape" of the documents at any stage of the pipeline, which may leave documents in an incompatible format.
  • The documents returned are plain javascript objects, not mongoose documents (since any shape of document can be returned).

But it goes beyond this because the aggregate operation is performed server-side, where any client-side Mongoose concepts like virtuals do not exist.

The result is that you'll need to include the date field in your $project and $group stages and add your own dateformatted field to the results in code based on the date values.

这篇关于MongoDB聚合中的Mongoose虚拟的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆