#java #mysql #database #jdbc #connection
#java #mysql #База данных #jdbc #подключение
Вопрос:
Я использую Java MySQL. Я пытаюсь добавить объемные данные (около 40 миллионов записей). Мое приложение отлично работает для пары сотен тысяч записей, но после этого оно начинает выдавать мне следующее исключение:
Exception in thread "main" com.mysql.jdbc.exceptions.jdbc4.CommunicationsException: Communications link failure
The last packet sent successfully to the server was 0 milliseconds ago. The driver has not received any packets from the server.
at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
at sun.reflect.NativeConstructorAccessorImpl.newInstance(Unknown Source)
at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(Unknown Source)
at java.lang.reflect.Constructor.newInstance(Unknown Source)
at com.mysql.jdbc.Util.handleNewInstance(Util.java:411)
at com.mysql.jdbc.SQLError.createCommunicationsException(SQLError.java:1116)
at com.mysql.jdbc.MysqlIO.<init>(MysqlIO.java:344)
at com.mysql.jdbc.ConnectionImpl.coreConnect(ConnectionImpl.java:2333)
at com.mysql.jdbc.ConnectionImpl.connectOneTryOnly(ConnectionImpl.java:2370)
at com.mysql.jdbc.ConnectionImpl.createNewIO(ConnectionImpl.java:2154)
at com.mysql.jdbc.ConnectionImpl.<init>(ConnectionImpl.java:792)
at com.mysql.jdbc.JDBC4Connection.<init>(JDBC4Connection.java:47)
at sun.reflect.GeneratedConstructorAccessor5.newInstance(Unknown Source)
at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(Unknown Source)
at java.lang.reflect.Constructor.newInstance(Unknown Source)
at com.mysql.jdbc.Util.handleNewInstance(Util.java:411)
at com.mysql.jdbc.ConnectionImpl.getInstance(ConnectionImpl.java:381)
at com.mysql.jdbc.NonRegisteringDriver.connect(NonRegisteringDriver.java:305)
at java.sql.DriverManager.getConnection(Unknown Source)
at java.sql.DriverManager.getConnection(Unknown Source)
at net.jboss.Database.DatabaseConnection.getConnection(DatabaseConnection.java:48)
at net.jboss.emp.idm.adta(mde.java:96)
at net.jboss.emp.idm.main(mde.java:69)
Caused by: java.net.SocketException: No buffer space available (maximum connections reached?): connect
at java.net.PlainSocketImpl.socketConnect(Native Method)
at java.net.PlainSocketImpl.doConnect(Unknown Source)
at java.net.PlainSocketImpl.connectToAddress(Unknown Source)
at java.net.PlainSocketImpl.connect(Unknown Source)
at java.net.SocksSocketImpl.connect(Unknown Source)
at java.net.Socket.connect(Unknown Source)
at java.net.Socket.connect(Unknown Source)
at java.net.Socket.<init>(Unknown Source)
at java.net.Socket.<init>(Unknown Source)
at com.mysql.jdbc.StandardSocketFactory.connect(StandardSocketFactory.java:257)
at com.mysql.jdbc.MysqlIO.<init>(MysqlIO.java:294)
... 16 more
Я погуглил эту проблему и перепробовал почти все варианты (обновление реестра Windows, изменение моего файла.cnf, изменение глобальных параметров mysql и т.д.), Но это не работает.
Комментарии:
1. пожалуйста, не могли бы вы опубликовать здесь зарегистрированный код драйверов для jdbc
2. Пожалуйста, покажите нам свой код. Я предполагаю, что вы открываете соединение для каждой записи, но забываете закрыть его (вы должны открыть его только один раз и впоследствии использовать параметризованный запрос).
Ответ №1:
Я столкнулся с аналогичной проблемой пару часов назад. С настройками по умолчанию я мог бы записать около 15 тысяч записей за одну транзакцию. Попытка написать что-либо большее, чем это, выдала мне точно такое же сообщение («Нет свободного места в буфере (достигнуто максимальное количество подключений?): connect») .
Затем я разбил транзакции на фрагменты по 1000 записей (это позволяли требования моего приложения), и я все равно получил сообщение после 15-й итерации. Мое приложение старательно создавало новый EntityManager и закрывало его для каждой итерации.
Решением было очистить кэш для этого конкретного типа объекта в промежутках между итерациями (вы также можете очистить кэш по объекту) .
EntityManagerFactory.getCache().выселИть все или evict(…)
Ответ №2:
Кажется, соединение не закрывается должным образом. Я бы порекомендовал вам использовать cобъединение в пул
Также смотрите
Комментарии:
1. Спасибо за ответ, я правильно открываю и закрываю соединения. Если это так, то почему это работает для первых нескольких сотен тысяч записей?
2. в сообщении об ошибке говорится,
(maximum connections reached?)
что, вероятно, после некоторых транзакций соединение не закрывается должным образом, и поэтому результат..3. Я дважды проверил и не обнаружил никаких проблем с общим количеством подключений.
Ответ №3:
вероятно, это могло быть либо потерянное соединение с mysql, либо ваш код не смог закрыть существующее соединение, поскольку вы сказали, что это работает для запуска некоторых записей. поэтому увеличьте максимальное соединение с mysql или попробуйте проверить с помощью другой программы, когда вы получите это сообщение об ошибке, если mysql принимает соединение из другой программы.
Ответ №4:
У меня была точно такая же проблема, и я исправил ее с помощью connectionname.close();
инструкции после каждого вызова исполняемого оператора.
Ответ №5:
теперь это может решить вашу проблему 🙂 Исключение CommunicationsException
Комментарии:
1. пожалуйста, опубликуйте ответ здесь, а не ссылайтесь на свой WordPress