【发布时间】:2014-12-16 23:31:04
【问题描述】:
在我用 JAVA 编写的应用服务器中,出现以下症状:
每小时一次或两次,对 MySQL 的查询非常慢(8-10 秒/查询)。
我的服务器查询了2个不同的数据库服务器,它们都有这个症状,但不是同时出现。
为了排除网络原因,我运行了一个网络监视器,它报告应用程序服务器和数据库服务器之间的网络良好。而且,我的应用服务器有4个线程,只有1个线程查询慢,其他3个仍然查询良好。
在两个数据库服务器上,我将连接超时设置为 10s,有一些查询超时(>10s),一些查询没有超时但很慢(查询时间长于 1s,通常是 8s-9s)。
奇怪的是,尽管客户端有慢查询,但数据库服务器端却没有慢查询日志(我配置的慢查询时间是1s)。
这是我用来连接数据库的一段代码:
public boolean checkSession(String sessionId) {
Connection conn = null;
conn = getDBConnection();
if(conn == null)
return false;
try {
PreparedStatement stm = conn.prepareStatement("SELECT uid FROM sessions WHERE sid=?");
stm.setString(1, sessionId);
ResultSet rs = stm.executeQuery();
if(rs.next()){
if(rs.getInt("uid") == tamtayId){
conn.close();
return true;
}
}
conn.close();
return false;
} catch (SQLException e1) {
e1.printStackTrace();
}
return false;
}
public void setDbConfigString(String str){
conStr = str;
}
public Connection getDBConnection(){
Connection conn = null;
try{
conn = DriverManager.getConnection(conStr);
}
catch (Exception e) {
e.printStackTrace();
}
return conn;
}
【问题讨论】:
-
您的所有代码都是正确的。必须与您的 sql 服务器有关
-
确保
SELECT uid FROM sessions WHERE sid=?使用索引来访问表。用EXPLAIN SELECT uid FROM sessions WHERE sid=?检查它 -
我想知道你的服务器的内存和垃圾收集设置如何。我有一种直觉,“每小时一次或两次”可能只是正在进行的大量垃圾收集清理。虽然 4 线程测试结果可能与此相矛盾。
-
PS:代码的格式很差。您应该真正关闭结果集和语句,即使连接关闭 - 应该 - 这样做。几行额外的代码,你就做对了。
-
首先使用连接池,目前每次需要连接时都会创建一个新的连接,然后销毁。如果出现异常,您还可以保持连接打开。理想情况下,您应该在 finally 块中关闭连接和资源。我真的怀疑查询速度很慢,但获得连接需要一段时间。
标签: java mysql performance yslow