limit mongodb 聚合_MongoDB 统计 group 操作用不了,试试 mapReduce 吧

51fc1b7b90ce5de59b8df0b5117ac730.png

问题回顾

今天,同事小张 Q 我, 说自己辛苦花了一天的时间,基于 mongodb 数据库开发的待办统计功能一直报错!

于是笔者花了近半小时了解小张的开发需求以及代码实现方式,大致明白问题出在对待办 collection 做统计时,调用 collection 的分组 group 函数、聚合 aggregate 函数的使用方式不对。

待办 collection 文档分组(group )函数代码

GroupByResults groupByResults = mongoTemplate.group(new Criteria().andOperator(criteriaArray),mongoTemplate.getCollectionName(PendingEntity.class), groupBy, PendingEntity.class);long resultCount = ((List)groupByResults.getRawResults().get("retval")).size();

待办 collection 文档聚合(aggregate)函数代码

AggregationResults results = mongoTemplate.aggregate(aggregation, "studentScore", PendingEntity.class);double totleScore = results.getUniqueMappedResult().getCollect();

问题定位

异常信息

Map-reduce supports operations on sharded collections, both as an input and as an output. This section describes the behaviors of mapReduce specific to sharded collections.However, starting in version 4.2, MongoDB deprecates the map-reduce option to create a new sharded collection as well as the use of the sharded option for map-reduce. To output to a sharded collection, create the sharded collection first. MongoDB 4.2 also deprecates the replacement of an existing sharded collection.Sharded Collection as InputWhen using sharded collection as the input for a map-reduce operation, mongos will automatically dispatch the map-reduce job to each shard in parallel. There is no special option required. mongos will wait for jobs on all shards to finish.Sharded Collection as OutputIf the out field for mapReduce has the sharded value, MongoDB shards the output collection using the _idfield as the shard key.

从异常信息提示来看,我注意到 errmsg 字段值:“can't do command: group on sharded collection”,大意是说分片文档(sharded collection)不能使用分组 group 函数。

笔者猜测是 sharded collection 的问题,于是笔者从一些技术博客和 mongodb 官网查了下使用 group 函数的一些限制,大致如下:

  • 分片表不能 group 分组
can't do command: group on sharded collection
  • group 操作不会处理超过 20000 个唯一键( group by 的关键字具有唯一性约束条件下)
exception: group() can't handle more than 20000 unique keys

显然,分片表不能 group 的限制,也验证了我的当初的猜想。

于是我问了下运维组的同事,也证实了 mongodb 在创建 collection 文档时,会指定文档数据分片到不同服务器上 ,这是出于对 mongodb 稳定性的考虑吧。

解决方案

既然分片表不能 group ,那如何解决分组统计的问题呢?

答案是用 “mapReduce” 。

想到什么呢?

是不是很类似 Hadoop 中的 Map-Reduce 的思想:

MapReduce最重要的一个思想: 分而治之. 就是将负责的大任务分解成若干个小任务, 并行执行. 完成后在合并到一起. 适用于大量复杂的任务处理场景, 大规模数据处理场景.

Map负责“分”,即把复杂的任务分解为若干个“简单的任务”来并行处理。可以进行拆分的前提是这些小任务可以并行计算,彼此间几乎没有依赖关系。

Reduce负责“合”,即对map阶段的结果进行全局汇总。

Hadoop 中的 Map-Reduce 执行流程

075b37bfd9528d184cef3d778611ac83.png

来源网络

翻阅 mongodb 官网文档,对 mapReduce 函数介绍如下:

Map-reduce supports operations on sharded collections, both as an input and as an output. This section describes the behaviors of mapReduce specific to sharded collections.

However, starting in version 4.2, MongoDB deprecates the map-reduce option to create a new sharded collection as well as the use of the sharded option for map-reduce. To output to a sharded collection, create the sharded collection first. MongoDB 4.2 also deprecates the replacement of an existing sharded collection

.

Sharded Collection as Input

When using sharded collection as the input for a map-reduce operation, mongos will automatically dispatch the map-reduce job to each shard in parallel. There is no special option required. mongos will wait for jobs on all shards to finish.

Sharded Collection as Output

If the out field for mapReduce has the sharded value, MongoDB shards the output collection using the _idfield as the shard key.

大意是 mapReduce 支持对 sharded collections 分片文档 input / output 操作,其处理逻辑如下:

487b46c94f7104246c414570fd67da89.png
  1. mongos接收到mapreduce的操作请求后,根据query条件,将map-reduce任务发给持有数据的shards(sharding collection将会被分裂成多个chunks并分布在多个shards中,shard即为mongod节点)。
  2. 每个shards都依次执行mapper和reducer,并将结果写入到本地的临时collection中,结果数据是根据_id(即reducer的key)正序排列。
  3. 当所有的shards都reduce完成之后,将各自结果数据中_id的最大值和最小值(即min、max key)返回给mongos。
  4. mongos负责shuffle和partition,将所有shards反馈的min、max key进行汇总,并将整个key区间分成多个partitions,每个partition包含[min,max]区间,此后mongos将partiton信息封装在finalReduce指令中并发给每个shard,最终每个shard都会收到一个特定的partition的任务;partition不会重叠。
  5. 此后每个shard将与其他所有的shards建立链接,根据partition信息,从min到max,遍历每个key。对于任何一个key,当前shard都将从其他shards获取此key的所有数据,然后执行reduce和finalize方法,每个key可能会执行多次reduce,这取决于values的条数,但是finalize只会执行一次,最终将此key的finalize的结果通过本地方式写入sharding collection中。
  6. 当所有的shards都处理完毕后,mongos将处理结果返回给客户端(inline)。

mapReduce 语法格式:

db.collection.mapReduce(,         ,                         {                           out: ,                           query: ,                           sort: ,                           limit: ,                           finalize: ,                           scope: ,                           jsMode: ,                           verbose: ,                           bypassDocumentValidation:                          }                       )

参数说明:

  • map:映射函数(生成键值对序列,作为reduce函数参数)
  • reduce:统计函数
  • query:目标记录过滤
  • sort:目标记录排序
  • limit:限制目标记录数量
  • out:统计结果存放集合(不指定使用临时集合,在客户端断开后自动删除)
  • finalize:最终处理函数(对 reduce 返回结果进行最终整理后存入结果集合)
  • Scope:向map、reduce、finalize导入外部变量
  • jsMode说明:为 false 时 BSON-->JS-->map-->BSON-->JS-->reduce-->BSON,可处理非常大的mapreduce,为 true 时 BSON-->js-->map-->reduce-->BSON
  • verbose:显示详细的时间统计信息

于是,我让小张同学把 group 换成 mapReduce 函数,问题解决!

String reducef = "function(key,values){var total = {count:0};for(var i=0;i mrr = readMongoTemplate.mapReduce(query,readMongoTemplate.getCollectionName(ReadingEntity.class), map, reducef, BasicDBObject.class);

问题总结

有时候,问题就出在最显眼的问题描述上,需要有心人去细细琢磨。

另外,其实大部分问题都可以在官网上找到相关技术解决方案,却又苦于受英语单词的折磨。。。

参考

https://docs.mongodb.com/manual/aggregation/

https://docs.mongodb.com/manual/core/map-reduce-sharded-collections/

https://www.cnblogs.com/chenpingzhao/p/7913247.html

https://blog.csdn.net/weixin_42582592/article/details/83080900

https://blog.csdn.net/iteye_19607/article/details/82644559

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/511845.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

基于 EMR OLAP 的开源实时数仓解决方案之 ClickHouse 事务实现

简介:阿里云 EMR OLAP 与 Flink 团队深度合作,支持了 Flink 到 ClickHouse 的 Exactly-Once写入来保证整个实时数仓数据的准确性。本文介绍了基于 EMR OLAP 的开源实时数仓解决方案。 作者简介:阿里云 EMR-OLAP 团队;主要负责开源…

【ClickHouse 技术系列】- 在 ClickHouse 中处理实时更新

简介:本文翻译自 Altinity 针对 ClickHouse 的系列技术文章。面向联机分析处理(OLAP)的开源分析引擎 ClickHouse,因其优良的查询性能,PB级的数据规模,简单的架构,被国内外公司广泛采用。本系列技…

从“数字化出海”到“出海数字化”,亚马逊云科技如何助力出海业务数字化转型

国内市场快速发展之外,全球也是广阔的市场。 据中国贸促会《中国企业对外投资现状及意向调查报告(2021年版)》显示,我国对外直接投资流量和存量稳居全球前三。在开拓海外市场的成绩里,2021全球《财富》世界500强榜单里…

amos调节变量怎么画_插画师该怎么收费?两个方法一看就懂。

任何自由插画师都逃不过要给客户报价这么一个令人头痛的环节,包括医学插画师。甲方往往希望看到一个菜单一样的价格表,把一切类型的插画安排的明明白白。而这样简单粗暴的算法,作为乙方又何尝不想要呢!纵观插画圈,萌新…

技术实践第二期|Flutter异常捕获

简介:应用性能稳定是良好用户体验中非常关键的一环,为了更好保障应用性能稳定,异常捕获在保证线上产品稳定中扮演着至关重要的角色。我们团队在推出了U-APM移动应用性能监控的产品后,帮助开发者定位并解决掉很多线上的疑难杂症。随…

请结合计算机硬件论述指令执行的过程,【计算机组成原理】计算机软硬件组成...

文章目录分层结构软件系统硬件系统I/O设备控制器存储器运算器先上张图,对计算机的软硬件组成有个大体的认识,接下来就是掰开揉碎这张大图ψ(`∇)ψ,本文绝大多数图片均为手绘分层结构其中操作系统的重要性不言而喻,也就…

F5:API 网关、流量网关发展各异,推出NGINX企阅版提供开源软件+企业级服务

作者 | 宋慧 出品 | CSDN 云计算 全球 80%互联网流量经过的 NGINX,全球有超过 4 亿个域名使用 NGINX 为载体,NGINX 无疑是成功的开源网关产品。 近日,F5 宣布 NGINX 在社区开源版本基础之上,推出NGINX企阅版(NGINX Op…

Spring Boot Serverless 实战系列“架构篇” 首发 | 光速入门函数计算

简介:如何以 Serverless 的方式运行 Spring Boot 应用? 作者 | 西流(阿里云函数计算专家) Spring Boot 是基于 Java Spring 框架的套件,它预装了 Spring 一系列的组件,开发者只需要很少的配置即可创建独立…

实现 消息提醒图标_用了5年苹果手机都不知道,原来小汽车图标是这个意思 ! ! !...

阅读本文前,请您先点击上面的“蓝色字体”,再点击“关注”,这样您就可以继续免费收到文章了。每天都会有分享,都是免费订阅,请您放心关注。注图文来源网络,侵删 …

技术分享:从双11看实时数仓Hologres高可用设计与实践

简介:本文将会从阿里巴巴双11场景出发,分析实时数仓面临的高可用挑战以及针对性设计。 2021年阿里巴巴双11完美落下为帷幕,对消费者来说是一场购物盛宴,对背后的业务支撑技术人来说,更是一场年度大考。在这场大考中&a…

操作系统如何实现:什么是宏内核、微内核

作者 | 陆小凤来源 | 码农的荒岛求生操作系统和普通的大型应用程序项目类似,都涉及代码组织方式的问题,但操作系统的独特之处在于其核心部分必须运行在内核态,kernel model,所谓内核态严格讲是指在该状态下程序拥有对硬件(hardwar…

雷神开机logo更改_九代酷睿i9加持的性能怪兽 雷神911黑武士Ⅱ评测

随着英特尔9代酷睿CPU的到来,品牌台式机也逐渐迎来了全新的升级,各大厂商也竞相抢占台式整机市场。而对于DIY组装机来说,相对于玩家门槛和售价又相对较高。国产台式机品牌雷神也抓住了这次契机,推出了“911黑武士”的第二代“911黑…

阿里云高级技术专家周晶:基于融合与协同的边缘云原生体系实践

简介:2020年 5G 商用元年以来,各种边缘场景开始火热起来,边缘计算又重回人们视野,这次的回归还伴随着云计算的普及与通信技术的颠覆式发展。边缘云作为 5G 与中心云计算的中继节点,处于云网融合、承上启下的关键位置。…

进程调度:我太难了!

作者 | 轩辕之风O来源 | 编程技术宇宙1、任务切换现在有一块CPU,但是有两个程序都想来执行,我们需要开发一个任务调度程序。只有两个程序,so easy啦!让它们交替执行就行了。为了实现切换,我们提供一个API,这…

阿里千万实例可观测采集器-iLogtail正式开源

简介:11月23日,阿里正式开源可观测数据采集器iLogtail。作为阿里内部可观测数据采集的基础设施,iLogtail承载了阿里巴巴集团、蚂蚁的日志、监控、Trace、事件等多种可观测数据的采集工作。iLogtail运行在服务器、容器、K8s、嵌入式等多种环境…

重启报错_Win10蓝屏,提示收集错误信息,反复重启报错

操作步骤:电脑为Win10系统,偶尔遇到微软Win10检测机制收集错误信息的提示,需要重启,重启之后恢复正常,但是在使用过程中收到此报错之后机器会反复的重启蓝屏提示。您可参考以下方式调试:方案一:1、按下“Wi…

一款跑在云上的定制容器专属 OS 来了——LifseaOS | 龙蜥技术

简介:如果可以把运维 API 化,那我们是不是可以把 OS 也作为一个 K8S 可以管理的资源,让 K8S 像管理容器一样管理OS? 引言 在 2021 年 10 月的云栖大会上,为云原生而生的 OS Lifsea 正式对外发布,并集成进入…

使用云效Codeup10分钟紧急修复Apache Log4j2漏洞

简介:2021年12月10日,国家信息安全漏洞共享平台(CNVD)收录了Apache Log4j2远程代码执行漏洞(CNVD-2021-95914),此漏洞是一个基于Java的日志记录工具,为Log4j的升级。作为目前最优秀的…

mysql时间相减得到天数保留两位_【敲黑板!】分布式事务数据库 —-MySQL 数据库开发规范(第四节)...

今天Amy着重为大家讲解一下关于函数的一些硬核知识,也是本文中非常重要的一个章节,记得认真看(dianzan)哦~第四节、函数4.1 字符串连接函数MySQL 数据库中字符串连接方法,需使用 CONCAT() 或 CONCAT_ WS()函数&#xf…

3类代码安全风险如何避免?

简介:企业和开发者在解决开源依赖包漏洞问题的同时,还需要考虑如何更全面地保障自己的代码数据安全。那么有哪些安全问题值得我们关注呢? 编者按:本次 Apache Log4j2 开源依赖包漏洞为所有人敲响警钟,企业的代码作为最…