美团:某动态线程池框架是官方开源的么?
如果不了解动态线程池概念的同学可以深入了解下。文章深入浅出,讲的很透彻,同时也是美团罪受欢迎的文章之一。
在此之后,美团官方并没有基于动态线程池这个 IDEA 做任何的产出。不过,开源社区基于美团这篇文章做了很多开源框架,比如笔者开源的 Hippo4j,以及另外一位开源作者 DynamicTP 框架等。
说完 Hippo4j 是否美团动态线程池开源后,接下来和大家聊两件和平常工作有关并且有意思的事。
美团动态线程池框架为什么没有开源
根据我的想法,如果当初美团推出动态线程池概念后,顺势推出一款开源框架,肯定会“爆火”。
毕竟,对于工作这么多年的开发来说,谁的线上环境还没有被线程池“坑”过呢。
但是,实际却没有按照这种设想发展,我就找了在美团工作的朋友聊了聊,下面根据我的了解说下是怎么回事。
1. 依赖办公软件大象
动态参数通知和线程池运行中报警,都需要通过办公通信软件或者邮件进行通知。
通过上面提到的美团动态线程池文章可知,在线程池变更通知和过载告警功能上,依赖了美团办公通信软件大象。
如果要开源,如何进行改造呢?
基于通知报警方案,其实很好解决,抽象出去一个通知接口以及核心参数,并提供 SPI 加载方式,基本上就能完成开源兼容适配。
2. 依赖监控工具 Cat
美团线程池支持查看内部任务级别的执行情况,进行细粒度任务级别监控。
核心原理是通过 Cat Transaction 打点进行的支持,下图表就是从 Cat 上汇总进行展示。
Cat 这种依赖,不太好替换,因为会对原有业务代码进行侵入。如果说开源方案的话,可能就需要牺牲一部分功能性或者针对动态线程池框架底层实现这一功能。
3. 依赖消息队列 Kafka
通过美团文章中看到线程池框架使用了 Kafka 消息队列,这里暂且当一个存疑点,动态线程池中哪部分业务需要使用 Kafka 呢?
如果说使用动态线程池功能,还需要依赖消息队列,这可能对于大部分场景来说是说不通用的。
如果要进行开源,我的建议和想法是将这里设置为可替换项。也就是说默认不支持 MQ 功能,同时对市场上主流 MQ 进行适配。如果客户端项目想用的话,可根据项目实际选择。
比较常见的是 Seata 和 SkyWalking 的做法,以 SkyWalking 举例,链路数据存储支持 H2、MySQL、ElasticSearch 等数据库,让用户根据场景以及服务体量灵活选择。
4. 动态线程池是监控体系中的“小”模块
之前有和美团的一位技术朋友沟通过,为什么美团的动态线程池框架没有开源出来?
他给我的回复是,动态线程池框架只是美团监控体系下一个“小”模块。
而且,根据不可靠消息,似乎内部该框架的实现不止一个,如果有美团的哥们看到可以评论下。
5. 小结
经过上面的分析,在这里我得出一个结论:美团在最初设计开发动态线程池时,似乎就没有打算对外开源。因此才会依赖如此多的组件以及美团内部的产品。
上文中所有想法都是笔者主观想法,实际情况有待考究。
如何识别框架是否官方开源
1. 开源仓库
国内公司中开源框架比较多的,基本上都会在 GitHub 命名空间下运维项目。
这里列举一些大厂开源公司对应的官方 GitHub 地址。
- 阿里巴巴:github.com/alibaba
- 腾讯:github.com/tencent
- 美团:github.com/meituan
- ......
2. 依赖包地址
在我们导入依赖包的时候,会输入 groupId、artifactId、version 三种信息,是否官方开源在 groupId 上基本就能体现出来。
groupId:一般由三部分组成,标识.公司名.项目名
,拿 Apache、Alibaba 两个组织的 groupId 举例子说明。
<dependency> <groupId>org.apache.shardingsphere</groupId> <artifactId>shardingsphere-jdbc-core-spring-boot-starter</artifactId> <version>${shardingsphere-jdbc-core-spring-boot-starter.version}</version> </dependency> <dependency> <groupId>com.alibaba.cloud</groupId> <artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId> <version>${spring-cloud-starter-alibaba-nacos-discovery.version}</version> </dependency> 复制代码
所以,如果说项目为官方开源,那么通过 groupId 很容易就能辨别出来。
3. 非官方地址就不是官方开源的么
非官方地址就不是官方开源的么,也不一定,并不是所有项目都在公司命名空间下发展。
有些项目是独立于公司创建的命名空间,比如说阿里的 seata、ant-design 等。
再比如美团一篇比较火的文章,讲的是操作日志如何记录,相信大多数同学也都有看到。
GitHub:github.com/mouzt/mzt-b…
同样不是官方开源,但是开源项目是由文章本人进行维护,代码质量和项目活跃度不输官方维护项目。
什么是 Hippo4j
上面说了很多关于开源的小知识,接下来向大家介绍下笔者开源的动态线程池框架 Hippo4j。
原理:通过对 JDK 线程池的增强,以及扩展三方框架底层线程池等功能,为业务系统提高线上运行保障能力。
Hippo4j 提供了两种模式,一种是 依赖配置中心,另一种是 无中间件依赖,部署个 Jar 包就能带来 Web 端控制台使用。
GitHub:github.com/opengoofy/h…
Gitee:gitee.com/magestack/h…
1. 线程池痛点
如果有在项目中实际使用线程池,相信你可能会遇到以下痛点:
- 线程池随便定义,线程资源过多,造成服务器高负载。
- 线程池参数不易评估,随着业务的并发提升,业务面临出现故障的风险。
- 线程池任务执行时间超过平均执行周期,开发人员无法感知。
- 线程池任务堆积,触发拒绝策略,影响既有业务正常运行。
- 当业务出现超时、熔断等问题时,因为没有监控,无法确定是不是线程池引起。
- 原生线程池不支持运行时变量的传递,比如 MDC 上下文遇到线程池就 GG。
- 无法执行优雅关闭,当项目关闭时,大量正在运行的线程池任务被丢弃。
- 线程池运行中,任务执行停止,怀疑发生死锁或执行耗时操作,但是无从下手。
2. 功能支持
基于以上痛点,Hippo4j 提供以下线程池功能扩展支持:
- 全局管控 - 管理应用线程池实例。
- 动态变更 - 应用运行时动态变更线程池参数,包括但不限于:核心、最大线程数、阻塞队列容量、拒绝策略等。
- 通知报警 - 内置四种报警通知策略,线程池活跃度、容量水位、拒绝策略以及任务执行时间超长。
- 数据采集 - 支持多种方式采集线程池数据,包括但不限于:日志、内置采集、Prometheus、InfluxDB、ElasticSearch 等。
- 运行监控 - 实时查看线程池运行时数据,自定义时间内线程池运行数据图表展示。
- 功能扩展 - 支持线程池任务传递上下文;项目关闭时,支持等待线程池在指定时间内完成任务。
- 多种模式 - 内置两种使用模式:依赖配置中心 和 无中间件依赖。
- 容器管理 - Tomcat、Jetty、Undertow 容器线程池运行时查看和线程数变更。
- 框架适配 - Dubbo、Hystrix、RabbitMQ、RocketMQ 等消费线程池运行时数据查看和线程数变更。
- 变更审核 - 提供多种用户角色,普通用户变更线程池参数需要 Admin 用户审核方可生效。
- 动态化插件 - 内置多种线程池插件,支持用户自定义插件以及运行时扩展。
- 多版本适配 - 经过实际测试,已支持客户端 SpringBoot 1.5.x => 2.7.5 版本(更高版本未测试)。
3. 小结
截止目前,共计 30+ 公司 线上使用 Hippo4j 管理应用线程池,使用公司中包括支付、电商、快递、保险以及教育等行业。
同时,共有 86 名 开源同学对 Hippo4j 进行了代码贡献,有 10 名 小伙伴持续投入较多精力维护,晋升为 Hippo4j Committer,得到官方支持 Jetbrains 全家桶 Licenses。
最后总结
关于动态线程池的热度一直居高不下,本篇文章讲述了美团动态线程池的上下文,以及对为什么没有开源进行了简单分析。
最终得出的结论是:美团最初设计动态线程池时就没有打算开源,所以才会依赖美团相关中间件以及 Kafka 等“重量级”组件。
同时针对有些同学说无法分辨框架是否官方开源,笔者针对这个话题做了几项总结输出。