mongo:聚合$ project中的新Date()

led*_*edy 18 mongodb aggregation-framework

对于我的一个集合,它必须保持unix时间戳而不是isodate,我通常将时间戳转换为新的Date(unix_timestamp).

现在我需要new Date(ts)聚合.(示例是在PHP中)

'$ project'=> array('day'=>'$ new Date(ts)',...

'$ group'=> array("_ id"=> array('day'=>'$ day)',...),...

没有到达结果.结果中的字段"日"完全丢失.

如何在聚合中转换?

小智 26

为了能够从文档中添加时间戳字段,您可以这样做,给定:

{"ts": 1400512120100}
Run Code Online (Sandbox Code Playgroud)

汇总为日期:

db.foo.aggregate({
   $project: {
       date: { $add: [new Date(0), "$ts"] }
   }
})
Run Code Online (Sandbox Code Playgroud)


小智 3

对于投影中的其他计算字段,您需要使用 $add 运算符,如下所示:(控制台示例)

db.so.aggregate([{$project: {date: {$add: Date() }}}])
Run Code Online (Sandbox Code Playgroud)

但这是错误的,我们收到一条错误消息:

exception: $add does not support strings (or dates)
Run Code Online (Sandbox Code Playgroud)

但我发现了一个简单的技巧 =)

db.so.aggregate([{$project: {date: {$substr: [Date(), 0, -1] }}}])
Run Code Online (Sandbox Code Playgroud)

在这种情况下,我们将得到带有日期的预期结果此外,在 PHP 输出中,您可以看到如下错误:

exception: disallowed field type Date in object expression (at 'date')
Run Code Online (Sandbox Code Playgroud)

现在,解决方案(php 5.4 语法):

$so->aggregate([
    ['$project' => ["date" => ['$substr' => [new MongoDate(), 0, -1]] ] ]
]);
Run Code Online (Sandbox Code Playgroud)

  • 这不会将字段 ts 的值转换为 mongo 日期。它只接受 php 字符串或数字作为输入,而不接受集合本身的值:/ (2认同)