Конфигурация Tomcat с использованием DBCP - PullRequest
9 голосов
/ 10 февраля 2011

Мы получаем сообщение CommunicationsException (от DBCP) после некоторого времени ожидания (несколько часов). Сообщение об ошибке (в Исключении) находится в конце этого вопроса, но я не вижу wait_timeout, определенного в любом из файлов конфигурации. (Где мы должны искать? Где-нибудь из каталога tomcat / conf?).

Во-вторых, как предполагает Исключение, куда помещается «свойство соединения Connector / J 'autoReconnect = true'"? Вот определение ресурса в файле conf / context.xml в настройке tomcat:

<Resource name="jdbc/TomcatResourceName" auth="Container" type="javax.sql.DataSource"
           maxActive="100" maxIdle="30" maxWait="10000"
           removeAbandoned="true" removeAbandonedTimeout="60" logAbandoned="true"
           username="xxxx" password="yyyy"
           driverClassName="com.mysql.jdbc.Driver"
           url="jdbc:mysql://127.0.0.1:3306/dbname?autoReconnect=true"/>

В-третьих, почему JVM ожидает вызова executeQuery () для выдачи исключения? Если время соединения истекло, метод getConnection должен выдать исключение, не так ли? Это раздел исходного кода, о котором я говорю:

        try {
                conn = getConnection (true);
                stmt = conn.createStatement (ResultSet.TYPE_SCROLL_INSENSITIVE,
                                                ResultSet.CONCUR_READ_ONLY);
                rset = stmt.executeQuery (bQuery);
                while (rset.next()) {
                     ....

Наконец, вот несколько первых строчек трассировки стека ...

com.mysql.jdbc.exceptions.jdbc4.CommunicationsException: The last packet successfully received from the server was 84,160,724 milliseconds ago.  The last packet sent successfully to the server was 84,160,848 milliseconds ago. is longer than the server configured value of 'wait_timeout'. You should consider either expiring and/or testing connection validity before use in your application, increasing the server configured values for client timeouts, or using the Connector/J connection property 'autoReconnect=true' to avoid this problem.
at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:57)
at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
at java.lang.reflect.Constructor.newInstance(Constructor.java:532)
at com.mysql.jdbc.Util.handleNewInstance(Util.java:406)
at com.mysql.jdbc.SQLError.createCommunicationsException(SQLError.java:1074)
at com.mysql.jdbc.MysqlIO.send(MysqlIO.java:3291)
at com.mysql.jdbc.MysqlIO.sendCommand(MysqlIO.java:1938)
at com.mysql.jdbc.MysqlIO.sqlQueryDirect(MysqlIO.java:2107)
at com.mysql.jdbc.ConnectionImpl.execSQL(ConnectionImpl.java:2642)
at com.mysql.jdbc.ConnectionImpl.execSQL(ConnectionImpl.java:2571)
at com.mysql.jdbc.StatementImpl.executeQuery(StatementImpl.java:1451)
at org.apache.tomcat.dbcp.dbcp.DelegatingStatement.executeQuery(DelegatingStatement.java:208)

Это причины, по которым некоторые из нас думают: «забудьте dbcp, он может настолько зависеть от конфигураций IDE и магии, что DriverManager.getConnection (...) может быть более надежным» Есть комментарии по этому поводу? Спасибо за ваши идеи, - MS

Ответы [ 2 ]

14 голосов
/ 10 февраля 2011

Поскольку DBCP сохраняет возвращенные соединения mysql открытыми для будущих запросов на соединение, они становятся жертвами MySQL Server timeout .

DBCP имеет ряд функций, которые могут помочь (может использоваться, начиная с Tomcat 5.5 IIRC).

validationQuery="SELECT 1"
testOnBorrow="true"

Проверка подтверждает, что соединение является действительным, прежде чем вернуть его в веб-приложение, выполняющее метод заимствования. Флаг, конечно, включает эту функцию.

Если истекло время ожидания (я полагаю, 8 часов) и соединение разорвано, то новое соединение проверяется (если оно больше отсутствует, оно создается) и передается в веб-приложение.

Другие возможные подходы:

  1. используйте DBCP testWhileIdle="true" в настройках вашего ресурса, чтобы также проверить незанятые соединения до того, как будет обнаружен эффективный запрос.

  2. Используйте 'connectionProperties', чтобы укрепить ваше соединение MySQL (например, autoReconnect/autoReconnectForPools=true)

0 голосов
/ 10 февраля 2011

DBCP не предназначен для использования в производстве, даже авторы говорят, что (см. Эту презентацию: http://www.infoq.com/presentations/Tuning-Tomcat-Mark-Thomas).

Я предлагаю взглянуть на C3P0: http://www.mchange.com/projects/c3p0/index.html

...