将ISOdate转换为yyyy-mm-dd格式

鉴于收集(#name:用户)结构:

{ "_id" : ObjectId("57653dcc533304a40ac504fc"), "username" : "XYZ", "followers" : [ { "count" : 31, "ts" : ISODate("2016-06-17T18:30:00.996Z") }, { "count" : 31, "ts" : ISODate("2016-06-18T18:30:00.288Z") } ] } 

我想根据用户名字段来查询这个集合,ts以'yyyy-mm-dd'格式返回。 预期产出:

 { "_id" : ObjectId("57653dcc533304a40ac504fc"), "username" : "XYZ", "followers" : [ { "count" : 31, "date" : "2016-06-17" }, { "count" : 31, "date" : "2016-06-18" } ] } 

我曾尝试过这样的事情:

 db.users.aggregate([ {$match:{"username":"xyz"}}, {$project:{ "followers":{"count":1, "date":"$followers.ts.toISOString().slice(0,10).replace(/-/g,'-')" }} } ]) 

但似乎没有工作。 任何人都可以请帮忙? 非常感谢。

考虑运行一个聚合pipe道,这将允许您首先压扁数据列表,使用$dateToString运算符投影新的字段,然后重新组合拼合的文档以获得所需的结果。

以上可以显示在三个不同的pipe道:

 db.users.aggregate([ { "$match": { "username": "xyz" } }, { "$unwind": "$followers" }, { "$project": { "username": 1, "count": "$followers.count", "date": { "$dateToString": { "format": "%Y-%m-%d", "date": "$followers.ts" } } } }, { "$group": { "_id": "$_id", "username": { "$first": "$username" }, "followers": { "$push": { "count": "$count", "date": "$date" }} } } ]) 

使用MongoDB 3.4及更新版本,您可以使用新的$addFieldsstream水线步骤与$map一起创build数组字段,而无需展开和分组:

 db.users.aggregate([ { "$match": { "username": "xyz" } }, { "$addFields": { "followers": { "$map": { "input": "$followers", "as": "follower", "in": { "count": "$$follower.count", "date": { "$dateToString": { "format": "%Y-%m-%d", "date": "$$follower.ts" } } } } } } } ]) 

最好也是最简单的方法是使用$map操作符来转换数组中的每个元素。 当然,在“in”expression式中,您需要使用$dateToString将“date”转换为使用格式说明符的string。

 db.coll.aggregate( [ { "$match": { "username": "XYZ" } }, { "$project": { "username": 1, "followers": { "$map": { "input": "$followers", "as": "f", "in": { "count": "$$f.count", "date": { "$dateToString": { "format": "%Y-%m-%d", "date": "$$f.ts" } } } } } }} ] ) 

这产生:

 { "_id" : ObjectId("57653dcc533304a40ac504fc"), "username" : "XYZ", "followers" : [ { "count" : 31, "date" : "2016-06-17" }, { "count" : 31, "date" : "2016-06-18" } ] }