我正在通过具有相当高延迟(~80ms)但带宽相对较高的连接连接到 MySQL(InnoDB)数据库。
我注意到查询时间根据查询的发出方式而有很大差异。在以下示例中,我将按主键对单个小行执行查询。查询时间为:
- 命令行客户端 (
mysql
): ~160ms - 原始 JDBC:~240 毫秒
- 休眠:~400ms(~0ms 开始,~160ms 获取,~240ms 提交)
- 休眠,L2:~240ms(~0ms 开始,~0ms 获取,~240ms 提交)
- 休眠,c3p0:~880ms(~160ms 开始,~240ms 获取,~480ms 提交)
- 休眠,L2+c3p0:~640ms(~160ms 开始,~0ms 获取,~480ms 提交)
(“L2”表示启用了 Hibernate 二级缓存,“c3p0”表示启用了 c3p0,“begin”、“get”和“commit”是查询期间调用的各种子方法的计时)
这些大致是“稳定状态”的结果,所以 L2 缓存是热的,Hibernate 启动时间被忽略。我假设启用 L2 缓存时“get”通常为 0ms,因为实际上没有发出 get。
我的问题是:
- 为什么所有查询都是网络延迟的倍数?即使是
mysql
命令行客户端似乎也需要 2 次往返才能进行简单查询。 - 为什么所有的 JDBC/Hibernate 查询都比命令行客户端慢得多?即使是原始的 JDBC 客户端似乎也需要 3 次往返。
- 为什么 c3p0 似乎让一切变得更糟?据我所知,我已经禁用了连接测试,否则它可以解释事情。