本文内容95%译自这篇文章:https://github.com/brettwooldridge/HikariCP/wiki/About-Pool-Sizing 我在研究HikariCP(一个数据库连接池)时无意间在HikariCP的Github wiki上看到了一篇文章(即前面给出的链接),这篇文章有力地消除了我一直以来的疑虑,看完之后感觉神清气爽。故在此做译文分享。 接下来是正文 数据库连接池的配置是开发者们常常搞出坑的地方,在配置数据库连接池时,有几个可以说是和直觉背道而驰的原则需要明确。 1万并发用户访问 想象你有一个网站,压力虽然还没到Facebook那个级别,但也有个1万上下的并发访问——也就是说差不多2万左右的TPS。那么这个网站的数据库连接池应该设置成多大呢?结果可能会让你惊讶,因为这个问题的正确问法是: “这个网站的数据库连接池应该设置成多小呢?” 下面这个视频是Oracle Real World Performance Group发布的,请先看完: http://www.dailymotion.com/video/x2s8uec (因为这视频是英文解说且没有字幕,我替大家做一下简单的概括:) 视频中对Oracle数据库进行压力测试,9600并发线程进行数据库操作,每两次访问数据库的操作之间sleep 550ms,一开始设置的中间件线程池大小为2048: 初始的配置 压测跑起来之后是这个样子的: 2048连接时的性能数据 每个请求要在连接池队列里等待33ms,获得连接后执行SQL需要77ms 此时数据库的等待事件是这个熊样的: 各种buffer busy waits 各种buffer busy waits,数据库CPU在95%左右(这张图里没截到CPU) 接下来,把中间件连接池减到1024(并发什么的都不变),性能数据变成了这样: 连接池降到1024后 获取链接等待时长没怎么变,但是执行SQL的耗时减少了。 下面这张图,上半部分是wait,下半部分是吞吐量 wait和吞吐量 能看到,中间件连接池从2048减半之后,吐吞量没变,但wait事件减少了一半。 接下来,把数据库连接池减到96,并发线程数仍然是9600不变。 96个连接时的性能数据 队列平均等待1ms,执行SQL平均耗时2ms。 image.png wait事件几乎没了,吞吐量上升。 没有调整任何其他东西,仅仅只是缩小了中间件层的数据库连接池,就把请求响应时间从100ms左右缩短到了3ms。 But why? 为什么nginx只用4个线程发挥出的性能就大大超越了100个进程的Apache HTTPD?回想一下计算机科学的基础知识,答案其实是很明显的。 即使是单核CPU的计算机也能“同时”运行数百个线程。但我们都[应该]知道这只不过是操作系统用时间分片玩的一个小把戏。一颗CPU核心同一