Ошибка канала связи из-за: java.io.EOFException - PullRequest
3 голосов
/ 14 декабря 2010

Мое веб-приложение работает на Tomcat 5.5, я объявил источник данных в web.xml:

<resource-ref>
    <res-ref-name>jdbc/OrdiniWebDS</res-ref-name>
    <res-type>javax.sql.DataSource</res-type>
    <res-auth>Container</res-auth>
    <res-sharing-scope>Shareable</res-sharing-scope>
</resource-ref>

В context.xml (tomcat conf):

<Resource 
  auth="Container" 
  driverClassName="com.mysql.jdbc.Driver" 
  maxActive="100" 
  maxIdle="30" 
  maxWait="10000" 
  name="jdbc/OrdiniWebDS" 
  password="[mypassword]" 
  type="javax.sql.DataSource" 
  url="jdbc:mysql://[myHost:port]/ordiniweb" 
  username="[myusername]"
 />

База данныхMySql 5.0.Все работает хорошо, за исключением того, что иногда, после нескольких часов «неиспользования», при первом доступе я получаю следующее исключение:

com.mysql.jdbc.CommunicationsException: Communications link failure due to underlying exception: 

** BEGIN NESTED EXCEPTION ** 

java.io.EOFException

STACKTRACE:

java.io.EOFException
 at com.mysql.jdbc.MysqlIO.readFully(MysqlIO.java:1956)
 at com.mysql.jdbc.MysqlIO.reuseAndReadPacket(MysqlIO.java:2368)
 at com.mysql.jdbc.MysqlIO.checkErrorPacket(MysqlIO.java:2867)
 at com.mysql.jdbc.MysqlIO.sendCommand(MysqlIO.java:1616)
 at com.mysql.jdbc.MysqlIO.sqlQueryDirect(MysqlIO.java:1708)
 at com.mysql.jdbc.Connection.execSQL(Connection.java:3255)
 at com.mysql.jdbc.PreparedStatement.executeInternal(PreparedStatement.java:1293)
 at com.mysql.jdbc.PreparedStatement.executeQuery(PreparedStatement.java:1428)
 at org.apache.tomcat.dbcp.dbcp.DelegatingPreparedStatement.executeQuery(DelegatingPreparedStatement.java:93)
 at com.blasetti.ordiniweb.dao.OrdiniDAO.caricaOrdine(OrdiniDAO.java:263)
...
** END NESTED EXCEPTION **



Last packet sent to the server was 0 ms ago.
 com.mysql.jdbc.MysqlIO.reuseAndReadPacket(MysqlIO.java:2579)
 com.mysql.jdbc.MysqlIO.checkErrorPacket(MysqlIO.java:2867)
 com.mysql.jdbc.MysqlIO.sendCommand(MysqlIO.java:1616)
 com.mysql.jdbc.MysqlIO.sqlQueryDirect(MysqlIO.java:1708)
 com.mysql.jdbc.Connection.execSQL(Connection.java:3255)
 com.mysql.jdbc.PreparedStatement.executeInternal(PreparedStatement.java:1293)
 com.mysql.jdbc.PreparedStatement.executeQuery(PreparedStatement.java:1428)
 org.apache.tomcat.dbcp.dbcp.DelegatingPreparedStatement.executeQuery(DelegatingPreparedStatement.java:93)
 com.blasetti.ordiniweb.dao.OrdiniDAO.caricaOrdine(OrdiniDAO.java:263)
...

Мне нужно обновить, и оно снова работает хорошо.Любая идея?Благодаря.

1 Ответ

9 голосов
/ 14 декабря 2010

MySQL сбрасывает неиспользуемые соединения через некоторое время, поскольку предполагает, что другая сторона забыла закрыть его.

Что вам нужно сделать, это настроить проверку, которую Tomcat должен применить, прежде чем он повторно использует соединение в пуле. Для этого добавьте ?autoReconnect=true&useUnicode=true&characterEncoding=utf8 в конец URL-адреса и добавьте validationQuery="Select 1" к элементу Resource:

<Resource 
  auth="Container" 
  driverClassName="com.mysql.jdbc.Driver" 
  maxActive="100" 
  maxIdle="30" 
  maxWait="10000" 
  name="jdbc/OrdiniWebDS" 
  password="[mypassword]" 
  type="javax.sql.DataSource" 
  url="jdbc:mysql://[myHost:port]/ordiniweb?autoReconnect=true&useUnicode=true&characterEncoding=utf8" 
  username="[myusername]"
  validationQuery="Select 1"
 />

[РЕДАКТИРОВАТЬ] Эта страница содержит более подробную информацию: Настройка источника данных MySQL в Apache Tomcat

...