SQL / JAVA通信链接错误偶尔会发生JDBC

时间:2015-07-13 00:21:07

标签: java mysql sql

com.mysql.jdbc.exceptions.jdbc4.CommunicationsException: Communications link failure

遇到此错误,如果有人可以使用我提供的代码在他们的答案中修复它会很棒。我不熟悉SQL我只是在帮朋友。

以下是代码:

public static Connection con = null;
public static Statement stmt;
public static boolean connectionMade;
public static void createConnection() {
    try {
        Class.forName("com.mysql.jdbc.Driver").newInstance();
        con = DriverManager.getConnection("jdbc:mysql://localhost/highscores","root","root");
        stmt = con.createStatement();
    } catch (Exception e) {
        e.printStackTrace();
    }
}
public static ResultSet query(String s) throws SQLException {
    try {
        if (s.toLowerCase().startsWith("select")) {
            ResultSet rs = stmt.executeQuery(s);
            return rs;
        } else {
            stmt.executeUpdate(s);
        }
        return null;
    } catch (Exception e) {
        destroyConnection();
        createConnection();
        e.printStackTrace();
    }
    return null;
}
public static void destroyConnection() {
    try {
        if(stmt != null)
        stmt.close();
        if(con!= null)
        con.close();
        connectionMade = false;
    } catch (Exception e) {
        e.printStackTrace();
    }
}

完整堆栈跟踪:

[9/07/15 19:23]: com.mysql.jdbc.exceptions.jdbc4.CommunicationsException: Communications link failure

Last packet sent to the server was 10 ms ago.
[9/07/15 19:23]:        at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
[9/07/15 19:23]:        at sun.reflect.NativeConstructorAccessorImpl.newInstance(Unknown Source)
[9/07/15 19:23]:        at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(Unknown Source)
[9/07/15 19:23]:        at java.lang.reflect.Constructor.newInstance(Unknown Source)
[9/07/15 19:23]:        at com.mysql.jdbc.Util.handleNewInstance(Util.java:406)
[9/07/15 19:23]:        at com.mysql.jdbc.SQLError.createCommunicationsException(SQLError.java:1074)
[9/07/15 19:23]:        at com.mysql.jdbc.MysqlIO.reuseAndReadPacket(MysqlIO.java:2985)
[9/07/15 19:23]:        at com.mysql.jdbc.MysqlIO.reuseAndReadPacket(MysqlIO.java:2871)
[9/07/15 19:23]:        at com.mysql.jdbc.MysqlIO.checkErrorPacket(MysqlIO.java:3414)
[9/07/15 19:23]:        at com.mysql.jdbc.MysqlIO.sendCommand(MysqlIO.java:1936)
[9/07/15 19:23]:        at com.mysql.jdbc.MysqlIO.sqlQueryDirect(MysqlIO.java:2060)
[9/07/15 19:23]:        at com.mysql.jdbc.ConnectionImpl.execSQL(ConnectionImpl.java:2536)
[9/07/15 19:23]:        at com.mysql.jdbc.StatementImpl.executeUpdate(StatementImpl.java:1564)
[9/07/15 19:23]:        at com.mysql.jdbc.StatementImpl.executeUpdate(StatementImpl.java:1485)
[9/07/15 19:23]:        at server.util.SQL.query(SQL.java:29)
[9/07/15 19:23]:        at server.util.SQL.saveHighScore(SQL.java:55)
[9/07/15 19:23]:        at server.model.mobile.players.Client.logout(Client.java:581)
[9/07/15 19:23]:        at server.model.mobile.players.packets.Clicking.ClickingButtons.processPacket(ClickingButtons.java:2190)
[9/07/15 19:23]:        at server.model.mobile.players.PacketHandler.processPacket(PacketHandler.java:118)
[9/07/15 19:23]:        at server.model.mobile.players.Client.processQueuedPackets(Client.java:769)
[9/07/15 19:23]:        at server.model.mobile.players.PlayerHandler.process(PlayerHandler.java:191)
[9/07/15 19:23]:        at server.Server$1.execute(Server.java:103)
[9/07/15 19:23]:        at server.task.Task2.tick(Task2.java:105)
[9/07/15 19:23]:        at server.event.TaskScheduler.run(TaskScheduler.java:100)
[9/07/15 19:23]:        at java.util.concurrent.Executors$RunnableAdapter.call(Unknown Source)
[9/07/15 19:23]:        at java.util.concurrent.FutureTask.runAndReset(Unknown Source)
[9/07/15 19:23]:        at java.util.concurrent.ScheduledThreadPoolExecutor$ScheduledFutureTask.access$301(Unknown Source)
[9/07/15 19:23]:        at java.util.concurrent.ScheduledThreadPoolExecutor$ScheduledFutureTask.run(Unknown Source)
[9/07/15 19:23]:        at java.util.concurrent.ThreadPoolExecutor.runWorker(Unknown Source)
[9/07/15 19:23]:        at java.util.concurrent.ThreadPoolExecutor$Worker.run(Unknown Source)
[9/07/15 19:23]:        at java.lang.Thread.run(Unknown Source)
[9/07/15 19:23]: Caused by: java.io.EOFException: Can not read response from server. Expected to read 4 bytes, read 0 bytes before connection was unexpectedly lost.
[9/07/15 19:23]:        at com.mysql.jdbc.MysqlIO.readFully(MysqlIO.java:2431)
[9/07/15 19:23]:        at com.mysql.jdbc.MysqlIO.reuseAndReadPacket(MysqlIO.java:2882)
[9/07/15 19:23]:        ... 24 more
[9/07/15 19:23]: com.mysql.jdbc.exceptions.jdbc4.CommunicationsException: Communications link failure
Last packet sent to the server was 10 ms ago.
[9/07/15 19:23]:        at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
[9/07/15 19:23]:        at sun.reflect.NativeConstructorAccessorImpl.newInstance(Unknown Source)
[9/07/15 19:23]:        at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(Unknown Source)
[9/07/15 19:23]:        at java.lang.reflect.Constructor.newInstance(Unknown Source)
[9/07/15 19:23]:        at com.mysql.jdbc.Util.handleNewInstance(Util.java:406)
[9/07/15 19:23]:        at com.mysql.jdbc.SQLError.createCommunicationsException(SQLError.java:1074)
[9/07/15 19:23]:        at com.mysql.jdbc.MysqlIO.reuseAndReadPacket(MysqlIO.java:2985)
[9/07/15 19:23]:        at com.mysql.jdbc.MysqlIO.reuseAndReadPacket(MysqlIO.java:2871)
[9/07/15 19:23]:        at com.mysql.jdbc.MysqlIO.checkErrorPacket(MysqlIO.java:3414)
[9/07/15 19:23]:        at com.mysql.jdbc.MysqlIO.sendCommand(MysqlIO.java:1936)
[9/07/15 19:23]:        at com.mysql.jdbc.MysqlIO.sqlQueryDirect(MysqlIO.java:2060)
[9/07/15 19:23]:        at com.mysql.jdbc.ConnectionImpl.execSQL(ConnectionImpl.java:2536)
[9/07/15 19:23]:        at com.mysql.jdbc.StatementImpl.executeUpdate(StatementImpl.java:1564)
[9/07/15 19:23]:        at com.mysql.jdbc.StatementImpl.executeUpdate(StatementImpl.java:1485)
[9/07/15 19:23]:        at server.util.SQL.query(SQL.java:29)
[9/07/15 19:23]:        at server.util.SQL.saveHighScore(SQL.java:55)
[9/07/15 19:23]:        at server.model.mobile.players.Client.logout(Client.java:581)
[9/07/15 19:23]:        at server.model.mobile.players.packets.Clicking.ClickingButtons.processPacket(ClickingButtons.java:2190)
[9/07/15 19:23]:        at server.model.mobile.players.PacketHandler.processPacket(PacketHandler.java:118)
[9/07/15 19:23]:        at server.model.mobile.players.Client.processQueuedPackets(Client.java:769)
[9/07/15 19:23]:        at server.model.mobile.players.PlayerHandler.process(PlayerHandler.java:191)
[9/07/15 19:23]:        at server.Server$1.execute(Server.java:103)
[9/07/15 19:23]:        at server.task.Task2.tick(Task2.java:105)
[9/07/15 19:23]:        at server.event.TaskScheduler.run(TaskScheduler.java:100)
[9/07/15 19:23]:        at java.util.concurrent.Executors$RunnableAdapter.call(Unknown Source)
[9/07/15 19:23]:        at java.util.concurrent.FutureTask.runAndReset(Unknown Source)
[9/07/15 19:23]:        at java.util.concurrent.ScheduledThreadPoolExecutor$ScheduledFutureTask.access$301(Unknown Source)
[9/07/15 19:23]:        at java.util.concurrent.ScheduledThreadPoolExecutor$ScheduledFutureTask.run(Unknown Source)
[9/07/15 19:23]:        at java.util.concurrent.ThreadPoolExecutor.runWorker(Unknown Source)
[9/07/15 19:23]:        at java.util.concurrent.ThreadPoolExecutor$Worker.run(Unknown Source)
[9/07/15 19:23]:        at java.lang.Thread.run(Unknown Source)
[9/07/15 19:23]: Caused by: java.io.EOFException: Can not read response from server. Expected to read 4 bytes, read 0 bytes before connection was unexpectedly lost.
[9/07/15 19:23]:        at com.mysql.jdbc.MysqlIO.readFully(MysqlIO.java:2431)
[9/07/15 19:23]:        at com.mysql.jdbc.MysqlIO.reuseAndReadPacket(MysqlIO.java:2882)
[9/07/15 19:23]:        ... 24 more

1 个答案:

答案 0 :(得分:1)

一般来说,您所依赖的CalendarConnection似乎已被关闭,无论是您自己还是由服务器隐式显示。

作为一般的良好做法,您应该只在需要时创建一个新的Statement并在您做的时候关闭它,例如......

Statement

良好做法还建议您使用public Connection createConnection() throws SQLException { Connection con = null; try { Class.forName("com.mysql.jdbc.Driver").newInstance(); con = DriverManager.getConnection("jdbc:mysql://localhost/highscores", "root", "root"); } catch (ClassNotFoundException | InstantiationException | IllegalAccessException ex) { throw new SQLException("Unable to load JDBC driver", ex); } return con; } public void makeQuery() throws SQLException { try (Connection con = createConnection()) { try (PreparedStatement stmt = con.prepareStatement("...")) { // Fill in parameters to the statement try (ResultSet rs = stmt.executeQuery()) { while (rs.next()) { // Get the results } } } } } 来确保您的代码不会成为SQL注入攻击的受害者

有关详细信息,请查看The try-with-resources StatementUsing Prepared Statements

我还鼓励您对连接池进行一些研究,因为它可以帮助您节省创建多个连接并帮助管理其生命周期的时间。

我还要注意使用PreparedStatement,因为这会增加线程问题的风险,让一个线程关闭连接而另一个线程试图使用它。