“每天计数”的 MongoDB 聚合查询(第 1 部分)

一则或许对你有用的小广告

欢迎加入小哈的星球 ,你将获得:专属的项目实战 / 1v1 提问 / Java 学习路线 / 学习打卡 / 每月赠书 / 社群讨论

  • 新项目:《从零手撸:仿小红书(微服务架构)》 正在持续爆肝中,基于 Spring Cloud Alibaba + Spring Boot 3.x + JDK 17...点击查看项目介绍 ;
  • 《从零手撸:前后端分离博客项目(全栈开发)》 2 期已完结,演示链接: http://116.62.199.48/ ;

截止目前, 星球 内专栏累计输出 63w+ 字,讲解图 2808+ 张,还在持续爆肝中.. 后续还会上新更多项目,目标是将 Java 领域典型的项目都整一波,如秒杀系统, 在线商城, IM 即时通讯,权限管理,Spring Cloud Alibaba 微服务等等,已有 2200+ 小伙伴加入学习 ,欢迎点击围观

我需要一个 MongoDB 查询来检索每天的文档计数,以便为我的业余无线电接收信号历史可视化服务 SpotViz 提供热图显示(使用 https://kamisama.github.io/cal-heatmap/ )。

提供给 Cal-heatmap 的数据如下所示:


 {
  "946721039":4,
  "946706853":2,
  "946706340":7,
  ...
}

这个数据结构的有趣之处在于属性名称是可变的,我不确定如何将结果投影到 MongoDB 查询中的属性名称中。我在 StackOverflow 上问了这个问题: “Return a computed value as field name in MongoDB query?” – 到目前为止我还没有得到任何答案或建议,所以我不确定这是否可行。

似乎没有办法完全满足我的需要,所以我的下一个挑战是如何每天对文档进行分组(忽略日期的时间部分),并返回每天的计数。

我从 shell 中的工作聚合查询开始,然后使用 MongoDB Java api 实现它。此查询的挑战在于,似乎没有任何开箱即用的功能允许您根据日期选择匹配文档并排除 new Date() 的时间部分。我需要的是等同于“查找按同一天分组的文档数”。要注意的是不要按完全相同的 yyyy/MM/dd hh:mm:ss 值对文档进行分组,而是仅按相同的 yyyy/MM/dd 值进行分组。

由于有一种方法可以使用聚合 $year、$month、$dayOfMonth 运算符从日期中提取年、月和日值,这些可用于获取我需要的结果(每天的计数),但这种格式不能帮助我获取 1970 年 1 月 1 日之后几秒内计数的属性名称,例如“946721039”。

使用这种方法的查询如下所示:


 {
  "946721039":4,
  "946706853":2,
  "946706340":7,
  ...
}

…此方法遵循 此 SO 帖子 的建议。

这种按天对文档计数进行分组的方法很好,但它不会返回自 1/1/1970 以来每天以秒表示的格式的文档。

更好的方法是按日期分组,然后返回该值。然而,将 mongo 中的日期转换为另一种格式似乎有些挑战——我可能花了太多时间来计算一个查询来执行此操作,接近了,但仍然不是我想要的,并以这个相当复杂的查询结束:


 {
  "946721039":4,
  "946706853":2,
  "946706340":7,
  ...
}

我试图用这种方法做的是使用 $project 阶段从每个时间戳值中减去转换为毫秒的 $hour、$minute 和 $second 值,以获得 yyyy/MM/dd 的毫秒值但忽略时间部分。这与我得到的差不多,但我无法让数学工作,或者至少无法在类型之间进行转换,因此计算将按照我想要的方式进行。

我的下一次尝试是基于 这篇 SO 帖子 中的建议。这是解决问题的一种更简单的方法——我的新查询如下所示:


 {
  "946721039":4,
  "946706853":2,
  "946706340":7,
  ...
}

如果我尝试将其分解为文字,那么我正在做的是:

– 对于日期 x,计算自 1/1/1970(纪元日期)以来的毫秒数

– 从中减去自一天开始以来的毫秒数(这是自 1/1/1970 以来的毫秒数 mod 一天中的毫秒数,余数除以另一个)

...结果是每个日期在午夜的毫秒数,即不包括时间部分。

好的,差不多了!我如何处理这个查询并将其转换为 MongoDB Java Drvier API 将在第 2 部分中介绍。



如果您喜欢这篇文章并想了解有关 MongoDB 的更多信息,请查看有关 MongoDB 的所有 教程和文章的集合

相关文章