【问题标题】:Am I using Java PooledConnections correctly?我是否正确使用 Java PooledConnections?
【发布时间】:2011-01-22 03:40:10
【问题描述】:

我想在 Java 中使用池连接(因为每个线程创建一个连接的成本很高),所以我使用了MysqlConnectionPoolDataSource() 对象。我正在跨线程保留我的数据源。因此,我在整个应用程序中只使用一个数据源,如下所示:

  startRegistry();    // creates an RMI registry for MySQL
  MysqlConnectionPoolDataSource dataSource = new MysqlConnectionPoolDataSource();
  dataSource.setUser("username");
  dataSource.setPassword("password");
  dataSource.setServerName("serverIP");
  dataSource.setPort(3306);
  dataSource.setDatabaseName("dbname");

  InitialContext context = createContext();   // Creates a context
  context.rebind("MySQLDS", dataSource);

现在我已经创建了数据源,我将在每个单独的线程中执行以下操作:

  PooledConnection connect = dataSource.getPooledConnection();
  Connection sqlConnection = connect.getConnection();

  Statement state = sqlConnection.createStatement();

  ResultSet result = state.executeQuery("select * from someTable");
  // Continue processing results

我想我对dataSource.getPooledConnection();的调用感到困惑
这真的是在获取一个池连接吗?这个线程安全吗? 我注意到 PooledConnection 有诸如 notify() 和 wait() 之类的方法......这意味着我认为它没有做我认为它正在做的事情......

另外,我应该何时以及如何释放连接?

我想知道自己动手是否更有益,因为那样我会更熟悉一切,但在这种情况下我真的不想重新发明轮子:)。

非常感谢

【问题讨论】:

  • 所有 Java 类都有通知和等待,因为它们是从 java.lang.Object 继承的。不过,实际使用它们非常罕见。
  • 是的,我对 java 有点陌生,哈哈……我正在试一试
  • 这是一个来自 Apache DBCP 的示例:svn.apache.org/viewvc/commons/proper/dbcp/trunk/doc/…

标签: java mysql database multithreading


【解决方案1】:

这不是正确的方法。数据源需要由您在其中运行应用程序的任何容器管理。MysqlConnectionPoolDataSource 不是连接池。它只是javax.sql.DataSource 接口的具体实现。您通常在 JNDI 上下文中定义它并从那里获取它。 MySQL 本身也在their documentation 中明确声明了这一切。

现在,如何使用它取决于应用程序的目的。如果是 Web 应用程序,则需要参考相关 servletcontainer/appserver 的 JNDI 资源文档。例如,如果是 Tomcat,那么您可以找到它here。如果你正在运行一个客户端应用程序——我会高度质疑连接池的价值——那么你需要寻找一个可以利用 MySQL 提供的连接池数据源的连接池框架,例如C3P0.

您发布的代码的另一个问题是PooledConnection#getConnection() 将返回底层 连接,因此不是 池连接。调用 close 不会将连接返回到池,而只是真正关闭它。池必须每次都创建一个新连接。

然后是线程安全故事,这取决于所讨论的真实连接池框架。 C3P0多年来已经证明了它的健壮性,你不用担心,只要你按照标准的习语写JDBC代码,即使用JDBC接口并获取在尽可能短的范围内关闭所有资源(ConnectionStatementResultSet)。

【讨论】:

  • 它是一个 RESTlet 独立应用程序......所以没有应用服务器或 JNDI
  • C3P0 对于可以放入一个类文件的东西来说非常大,如果你使用 PooledConnection 来完成任务。
  • 奇怪的答案。 “数据源需要由任何容器管理” - 不,没有数据源需要由任何容器管理。可以,但没必要。仅仅为了有一个连接池而引入一个容器是不合理的。要手动添加池,我建议用户使用 Apache Commons DBCP(就像 Tomcat 本身所做的那样),或者尝试使用 Tomcat 的 JDBC 池(他们在版本 7 中实现的更快的池,作为 Commons DBCP 的替代品)。
  • @mvmn:“无论 您在哪个容器中运行应用程序”。通俗的说,就是servlet容器/webserver/应用服务器(Tomcat、Glassfish、JBoss AS、WebSphere AS等)。
  • @BalusC:我所说的没有任何改变——没有需要有一个容器来池化数据源。不需要,好吗?实际使用什么容器并不重要——无论是 Servlet Container 还是其他容器,都没有必要将独立应用程序转换为 webapp,或者添加类似 Spring 的东西,只是为了拥有池化 DataSource。 “使用 C3P0”比实际的“答案”更好。国际海事组织。
猜你喜欢
  • 2013-07-13
  • 2016-04-11
  • 2016-01-24
  • 2014-05-15
  • 2010-12-31
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多