遇到真正的高并发问题了,特来求助

2018-09-16 20:25:02 +08:00
 abcbuzhiming
以前做的项目,要么服务器够多,要么访问量比较分散,一天虽然人多,但是都是不同时段。所以没遭遇到访问瓶颈。这次真刀真枪的需要进行一次单服优化,然后就发现单服性能不可思议的低。大致情况如下:
应用服务器是 Tomcat,在阿里云上的 4 核心的 xero,8GB 内存,10MB 带宽,技术实现是 spring mvc,并不是特别复杂的计算业务,说难听点仅仅是 crud,而且输出的是纯粹的 json,没有其它的静态文件之类的东西。然后 MySQL 数据库在和应用服务器同一区域的另外一台阿里云服务器上,类似的配置,4 核心,8GB 内存,用的是高效 SSD。
这样的两台(一组)服务器,能抗住多少并发呢,500 不到。。。

然后开始初步分析,发现一个问题,就是哪怕是单纯的数据库读业务,从浏览器请求到服务器,服务器从数据库读取完毕到返回给前端,最快也要 20-30ms 左右,稍微复杂点的数据结构就上 100ms 了,如果按这个计算,每秒每个线程的处理能力理论最快也就 50 个并发请求,4 核心的机器上,JVM 的线程池一般也就核心的 1.5-2 倍,顶多不到 10 个线程,这样一算,单服理论并发处理能力确实只有 500 不到。。。

我不死心于是回头去找以前的类似服务器做测试,结果发现性能是类似的,只不过当年是靠着服务器够多顶住了罢了。

我知道肯定会有人说,上缓存啊,我当然知道上缓存,我的困惑是,难道只有上缓存一条路,那些并发上 w 的都是靠缓存顶住的吗?不上缓存的话,我现在服务器的性能指标到底是否正常?
34371 次点击
所在节点    程序员
183 条回复
night98
2018-09-16 20:33:44 +08:00
4c8g 应该性能不会这么差,排查下那几个点耗时长再优化
abcbuzhiming
2018-09-16 20:36:25 +08:00
@night98 没有长耗时,我检查过数据库,就是最简单的 select 单条记录,从浏览器前端到应用服务器,应用服务器从数据库读取再返回给前端,就要 20-30ms。所以我现在很想找个参照物,这个过程又没有能压到个位数毫秒级的让我见识一下
sujin190
2018-09-16 20:42:17 +08:00
没怎么用过 java,但是 python 的 tornado 做的 curd 延时平均差不多 3ms,内网延时普遍应该 1ms 吧,简单 sql 2 到 3ms 可以返回了吧,框架不可能慢吧,spring 应该有性能分析工具吧,可以看看是数据库慢还是框架慢

不过认真说,实际项目 500 感觉不低了吧,还是加机器缓存靠谱
sylxjtu
2018-09-16 20:44:24 +08:00
@abcbuzhiming 用 show profile 应该能知道在服务端的延时吧,可以知道到底网络问题还是 sql 的问题
ittianyu
2018-09-16 20:45:59 +08:00
500 就高并发?
你们公司规模得多小,手动滑稽。
让我这个曾经做安卓应届生来给你点小建议

数据复杂的可以考虑 join 拆分成多个单表查询,然后在 java 里面关联起来。
数据长时间不变的上缓存。
几万并发的集群+缓存基本就可以解决。

整个项目几万到十几万的并发,就拆分项目,也就是 SOA 或 微服务。主要是分摊压力,解决数据库和入口大流量瓶颈问题。

what ?在往上怎么办?这么大的用户群,会让我这种应届生来做架构?这种问题,有请下面的大佬来回答。
hopingtop
2018-09-16 20:48:10 +08:00
根据你描述的点可以测试两个点
1. 数据库机器到应用机器的网络,单纯的数据读取
2. 只测试序列化的时间

如果上述都 ok,在考虑线程是否优化,sql 等
ashes1122
2018-09-16 20:48:56 +08:00
@ittianyu 你连题主的描述和需求都没看完吧?
luban
2018-09-16 20:49:26 +08:00
500 并发我觉得不低了,工作七八年还没接触过超过 500 并发的系统
lxrmido
2018-09-16 20:56:35 +08:00
@ittianyu 你没看题,你这只是解决了你设想的高并发,然而楼主遇上的显然不是

建议楼主换高性能的 RDS
qiuqiuer
2018-09-16 20:59:18 +08:00
有个过时的东西叫,内存变硬盘
liprais
2018-09-16 21:00:35 +08:00
现在应届生阅读能力这么差了 ?
老实讲不上缓存 500 并发不低了,不过还是先做 profile 看看时间都花哪了
单表查询 mysql 应该可以做到 5ms 以内没问题
ooTwToo
2018-09-16 21:05:21 +08:00
想要马儿跑得快,又不给马儿吃草?
dengtongcai
2018-09-16 21:08:27 +08:00
20-30ms 整个请求响应过程,确实就算一个普通 select 最低也要这个时间
Ico945
2018-09-16 21:13:35 +08:00
首先赞同楼上的,用工具看看是哪部分慢。数据库的话 查看你的 crud 语句是不是可以继续优化,表的结构是不是合理
ittianyu
2018-09-16 21:19:09 +08:00
@ashes1122 不好意思,确实没往下看了,单机一个 tomcat 200-500 并发是正常的,多加机器,别折腾了。
metrxqin
2018-09-16 21:20:20 +08:00
> 这样的两台(一组)服务器,能抗住多少并发呢,500 不到

请把测试相关信息也发出来,比较关键的信息 CPU 负载情况、Tomcat 线程池使用情况、应用数据库连接使用情况,另外在高并发时使用 jstack 打印出最繁忙的线程堆栈。

另外还有主机的带宽使用情况和 ss -s 输出内容。
metrxqin
2018-09-16 21:23:44 +08:00
另外还有测试请求内容大小和响应大小。
xiaoshenke
2018-09-16 21:24:12 +08:00
性能问题一般就是带宽,数据库,线程数。你这个数据库有点慢了。
lhx2008
2018-09-16 21:28:36 +08:00
不上缓存的话,用 Netty 上面的异步框架进一步压缩一下多余的开销,然后暴力线程池来等 Mysql,至少能抗两三千吧,具体看业务了。
lhx2008
2018-09-16 21:32:01 +08:00
https://github.com/xenv/gushici#%E5%8D%95%E6%9C%BA%E5%8E%8B%E6%B5%8B

vert.x + netty + redis 可以做到超高并发的 10ms 内稳定返回,如果旧项目不好转的话 Spring Webflux + netty 也是不错的选择。

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/489883

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX