Подтвердить что ты не робот

Когда нужно закрыть Connection, Statement, PreparedStatement и ResultSet в JDBC

Несколько вопросов по кодированию JDBC:

  • Для одного клиентского приложения нам нужен пул соединений?
  • Это хорошая идея создать соединение в начале и сохранить его в живых, не закрывая его до выхода приложения? Почему?
  • PreparedStatement связан с Connection, если мое соединение не закрывается после каждого запроса, почему бы не сохранить PreparedStatement в активном состоянии и повторно использовать его другими способами?
  • Если мы создадим PreparedStatement для каждого запроса, знает ли он, что это тот же PreparedStaement и игнорирует ненужные действия после первого раза?
  • PreparedStatement не создает один раз и повторно использует много раз инструкцию? если да, зачем каждый раз закрывать его?

Я знаю, что вызов функции close() освободит ресурс. Но если мы знаем, что мы будем использовать его позже, зачем его выпускать, а затем запросить позже?

Как о многоклиентском приложении? нам нужен пул соединений и поэтому нам нужно каждый раз создавать и закрывать Connection, Statement и PreparedStatement?

спасибо,

4b9b3361

Ответ 1

Лично я бы использовал пул, так как это позаботится обо всем управлении ресурсами для вас. Если ваши требования к подключению меняются, вы можете легко изменить конфигурацию пула. С пулом на месте вы можете открывать/закрывать соединения и готовить заявления в соответствии с наилучшей практикой и оставлять управление ресурсами пулом.

Как правило, при использовании пула:

  • закрытие соединения фактически просто вернет его в пул
  • акт подготовки инструкции будет либо извлекать предварительно подготовленный оператор из кэша операторов соединения, либо если он недоступен, создайте новый оператор и кешируйте его для последующего использования.
  • Акт закрытия PreparedStatement фактически просто вернет его в кеш оператора приложений.

Кроме того - в зависимости от реализации пула - он может уведомить вас, когда есть утечки ресурсов, что упрощает идентификацию этих проблем в вашем коде.

Взгляните на источник примера реализации, например DBCP - довольно интересно посмотреть, как они работают.

Ответ 2

1. Даже если у вас есть один клиент, пул соединений может по-прежнему быть полезным. Подключение к базе данных может занять значительное время, поэтому очень часто это может замедлить работу приложения с медленными сетевыми запросами. Кроме того, как объясняет @teabot, пул может помочь определить, не закрыто ли какое-либо соединение.

2. Не рекомендуется открывать соединение и оставлять его открытым навсегда по двум причинам. Сначала соединение может погибнуть, если есть временное прерывание сети. Чем дольше он открыт, тем больше вероятность, что он будет мертв, когда потребуется. Во-вторых, неудавшаяся транзакция может оставить соединение в состоянии, не подходящем для продолжения работы. Лучше всего открыть несколько соединений, повторно использовать их в течение пяти или десяти минут, а затем переработать их.

3. В зависимости от базы данных и драйвера соединение может иметь готовый кэш инструкций. Даже при использовании другого соединения RDBMS обычно кэширует операторы, которые в точности совпадают, включая параметры. Поэтому SELECT * FROM table WHERE value =? поскольку подготовленный оператор будет кэшироваться через соединения, но если вы укажете значение параметра, например SELECT * FROM table WHERE value = 'your_data', то, вероятно, он не будет кешировать сервер.

4. Как объясняется в 3, зависит от реализации РСУБД, выполните контрольный тест.

5. Нет необходимости закрывать и готовить снова выражение, которое будет повторно использоваться с разными параметрами. Просто заново установите параметры и выполните.

Для нескольких клиентов база данных всегда будет иметь ограничение одновременного подключения, которое обычно не является большим числом. Если все клиенты проходят через webapp, то в качестве пула, такого как DBCP, все в порядке. Но, очевидно, нежелательно создавать пул для каждого клиента с постоянным открытием нескольких соединений.