一句话结论
对于跑在单核CPU上的运算类API, 根据业务需求(最大响应时间)来调试找到最大线程数,然后依据线程数调试出heap大小(主要看年老代的回收次数)
若有理解不到位之处,请在评论区留言,跪谢!
背景
断断续续忙碌了几个月,终于自己写的开源项目算是有了雏形,打包成Docker image发布到AWS EC2后,写代码算是告一段落。随之而来的问题就是“我的项目能够支撑多少QPS” ,由于用了Docker, 即变成了“我的项目基于Docker的配置能够支撑多少QPS”, 更进一步细化这个问题的话,有以下几点:
说句题外话,我认为按照服务商提供的最小单元来划分的好处在于:减少开销。500M的费用只有1G的一半,而且将来项目动态伸缩的灵活度高,粒度更小。
俗话说的好, 抛开业务需求来谈IT就是耍流氓。
项目是开源项目,业务需求那就只好我自己定了,一般来说我们并不希望用户登录过快(并且并发登录的情况虽然有但是确实比较少见),这次的api (oauth/token) 我定在了2秒的最大值,以此为基础来找出性能瓶颈。
那么在不改动项目代码的前提下,可以调整哪些参数来提升性能的呢?
对于计算为主的项目,主要关注点还是在max-threads,设置合理的话可以减少CPU上下文切换带来的性能开销,以及合适的Heap大小来避免频繁触发GC所造成性能抖动。
虽然标题是基于Docker的性能测试,但是我还是想对比一下用与不用Docker上的性能差异,所以测试会分为两个部分, 以下为jre的基本信息
ubuntu@ip-xxx-xx-xx-xxx:~$ java -version
openjdk version "11.0.4" 2019-07-16
OpenJDK Runtime Environment (build 11.0.4+11-post-Ubuntu-1ubuntu218.04.3)
OpenJDK 64-Bit Server VM (build 11.0.4+11-post-Ubuntu-1ubuntu218.04.3, mixed mode, sharing)复制代码
ubuntu jre 信息
/ # java -version
openjdk version "11" 2018-09-25
OpenJDK Runtime Environment 18.9 (build 11+28)
OpenJDK 64-Bit Server VM 18.9 (build 11+28, mixed mode)复制代码
docker jre 信息
3.1.1 Heap 固定,不同线程数关系图
50m Heap大小在100个线程的情况下OOM,所以这里为0
3.1.2 线程数固定,不同Heap大小下关系图
直接上对比图
上图为不限制Docker 容器大小的结果
上图限制了Docker 容器大小为450M
上图100 threads 50m Heap 的时候程序直接崩溃了所以为0
很明显,Docker会带来一定的性能开销,并且随着线程数的增加与QPS的增加,这种开销会更加明显。但是并不是说Docker不好,毕竟性能开销只要多开一个节点就搞定,和Docker带来的便利性相比,几乎可以无视。
这里的讨论仅限于单核CPU负载较高的运算类API,Serial GC
对于跑在单核CPU上的运算类API, 根据业务需求(最大响应时间)来调试找到最大线程数,然后依据线程数调试出heap大小(主要看年老代的回收次数)
很简单,10 threads 100m heap
原文转自:https://juejin.im/post/5d4cd38cf265da03b120394c