我一直在围绕只读与读写数据库事务的性能进行一些研究。 MySQL服务器在慢速VPN链接上是远程的,因此我很容易看到事务类型之间的差异。这是连接池,我知道它基于比较第一次和第二次JDBC调用。
当我将Spring AOP配置为在我的DAO调用上使用只读事务时,与读写相比,调用的速度为30-40% :
<!-- slower -->
<tx:method name="find*" read-only="true" propagation="REQUIRED" />
...
// slower
@Transaction(readOnly = true)
对战:
<!-- faster -->
<tx:method name="find*" read-only="false" propagation="REQUIRED" />
...
// faster
@Transaction
看看tcpdump,似乎只读事务在与MySQL交谈时做得更多。这是read-only dump与read-write的对比。
任何人都可以解释为什么只读通话需要更长的时间。这是预期的吗?
除了改善网络外,还有什么我做错了或能做些什么来提高速度?刚刚发现这篇精彩的帖子有一些good performance recommendations。还有其他意见吗?
非常感谢。
答案 0 :(得分:29)
为什么spring / hibernate只读数据库事务的运行速度比读写速度慢?
好的,这是一个有趣的旅程。很多我可以学习和分享。下面的一些内容应该是显而易见的,但希望我的无知和我所学到的知识对其他人有所帮助。
&LT; tldr&GT;对问题#1的简短回答是,hibernate从@Transaction(readOnly = true)
会话开始,具有set session.transaction.read.only
同步JDBC调用,并以set session.transaction.read.write
调用结束。执行读写调用时不会发送这些调用,这就是为什么只读调用较慢的原因。 &LT; / tldr&GT;
问题#2的答案较长,涉及我尝试降低远程数据库性能的步骤的以下详细信息:
我们做的第一件事是在阅读OpenVPN optimization page后将数据库VPN从TCP切换到UDP。叹。我应该知道这一点。我还将以下设置添加到OpenVPN客户端和服务器配置中。只读事务开销从480ms降至141ms,但仍然超过读写的100ms。大赢。
; Got these from: https://community.openvpn.net/openvpn/wiki/Gigabit_Networks_Linux
proto udp
tun-mtu 6000
fragment 0
mssfix 0
仔细观察tcpdump输出(获胜的tcpdump ... -X
),我注意到有很多不必要的自动提交和只读/读写JDBC调用。升级到我们使用的真棒HikariCP connection pool库的更新版本对此有所帮助。在版本2.4.1中,他们添加了一些智能,减少了一些这些调用。只读事务开销低至120ms。读写仍然是100ms。好的。
HikariCP的作者Brett Wooldridge向我指出了可能有用的MySQL驱动程序设置。非常感谢老兄。将以下设置添加到我们的MySQL JDBC URL会告诉驱动程序使用连接的软件状态,而不是询问服务器的状态。
jdbc:mysql://.../database?useLocalSessionState=true&useLocalTransactionState=true
这些设置导致删除了更多的同步JDBC命令。只读事务开销降至60ms,现在与读写相同。呜呜。
编辑/警告:我们实际上在发现驱动程序没有发送交易信息的错误后回滚添加useLocalTransactionState=true
。
但是在查看tcpdump输出时,我仍然看到发送了只读/读写事务设置。我的最后一个修复是编写一个自定义只读检测池,如果它看到第一次连接调用是connection.setReadOnly(true)
,它会从特殊池中发出连接。
使用此自定义池会将只读和读写连接的事务开销降低到20毫秒。我认为它基本上删除了最后一个JDBC事务开销调用。这是我的主页two classes that I wrote的来源,写下了所有这些内容。代码相对脆弱,并依赖于Hibernate首先执行connection.setReadOnly(true)
但它似乎运行良好,我在XML和代码中仔细记录它。
因此基本的@Transaction
开销在几天的工作中从480毫秒增加到20毫秒。 100&#34;现实生活&#34; hibernate调用dao.find(...)
方法从55秒开始,以4.5秒结束。漂亮踢屁股。希望速度提高10倍总是很容易。
希望我的经历能帮助他人。