JDBC的连接池选项:DBCP与C3P0

时间:2009-02-06 14:57:19

标签: java jdbc connection-pooling c3p0 apache-commons-dbcp

可用于Java / JDBC的最佳连接池库是什么?

我正在考虑两个主要候选人(免费/开源):

我在博客和其他论坛上看过很多关于它们的内容,但无法做出决定。

这两个是否有任何相关的替代方案?

16 个答案:

答案 0 :(得分:177)

DBCP已过期而非生产等级。一段时间后,我们对两者进行了内部分析,创建了一个测试夹具,对两者产生负载和并发性,以评估它们在现实生活条件下的适用性。

DBCP始终如一地在我们的测试应用程序中生成异常,并努力达到C3P0能够处理的性能水平,没有任何例外。

C3P0还可以在恢复时稳健地处理数据库断开连接和透明重新连接,而如果链接从其下方取出,则DBCP永远不会恢复连接。更糟糕的是DBCP将Connection对象返回到底层传输已经破坏的应用程序。

从那时起,我们在4个主要的重载消费者网络应用程序中使用了C3P0,并且从未回头。

更新:事实证明,经过多年坐在架子上,Apache Commons民众已经采取了DBCP out of dormancy,现在又是一个积极开发的项目。因此我原来的帖子可能已经过时了。

话虽这么说,我还没有体验过这个新升级的库的性能,也没有听说它在任何最近的应用程序框架中都是事实上的。

答案 1 :(得分:173)

我邀请您试用BoneCP - 它是免费的,开源的,并且比可用的替代品更快(参见基准测试部分)。

免责声明:我是作者所以你可以说我有偏见: - )

更新:截至2010年3月,仍然比新重写的Apache DBCP(“tomcat jdbc”)池快35%左右。请参阅基准测试部分中的动态基准测试链接。

更新#2:(2013年12月)经过4年的顶峰,现在有一个更快的竞争对手:https://github.com/brettwooldridge/HikariCP

更新#3:(2014年9月)此时请考虑将BoneCP 弃用,建议切换到HikariCP

更新#4 :( 2015年4月) - 我不再拥有域名jolbox.com,但新所有者保留了旧内容,所以要小心。

答案 2 :(得分:16)

当连接超时时我遇到了DBCP问题所以我试用了c3p0。我打算将其发布到生产中,然后开始进行性能测试。我发现c3p0的表现非常糟糕。我无法将其配置为表现良好。我发现它的速度是DBCP的两倍。

然后我尝试了Tomcat connection pooling

这是c3p0的两倍,修复了我在DBCP中遇到的其他问题。我花了很多时间调查和测试3个池。如果要部署到Tomcat,我的建议是使用新的Tomcat JDBC池。

答案 3 :(得分:14)

对于DBCP的自动重新连接问题,有没有尝试过使用以下2个配置参数?

validationQuery="Some Query"

testOnBorrow=true

答案 4 :(得分:12)

现在已经在生产中使用DBCP几年了。它是稳定的,幸存数据库服务器重启。只需正确配置它。它只需要指定一些参数,所以不要太懒惰。以下是我们的系统生产代码的片段,其中列出了我们明确设置的参数:

DriverAdapterCPDS driverAdapterCPDS = new DriverAdapterCPDS();
driverAdapterCPDS.setUrl(dataSourceProperties.getProperty("url"));
driverAdapterCPDS.setUser(dataSourceProperties.getProperty("username"));
driverAdapterCPDS.setPassword(dataSourceProperties.getProperty("password"));
driverAdapterCPDS.setDriver(dataSourceProperties.getProperty("driverClass"));

driverAdapterCPDS.setMaxActive(Integer.valueOf(dataSourceProperties.getProperty("maxActive")));
driverAdapterCPDS.setMaxIdle(Integer.valueOf(dataSourceProperties.getProperty("maxIdle")));
driverAdapterCPDS.setPoolPreparedStatements(Boolean.valueOf(dataSourceProperties.getProperty("poolPreparedStatements")));

SharedPoolDataSource poolDataSource = new SharedPoolDataSource();
poolDataSource.setConnectionPoolDataSource(driverAdapterCPDS);
poolDataSource.setMaxWait(Integer.valueOf(dataSourceProperties.getProperty("maxWait")));
poolDataSource.setDefaultTransactionIsolation(Integer.valueOf(dataSourceProperties.getProperty("defaultTransactionIsolation")));
poolDataSource.setDefaultReadOnly(Boolean.valueOf(dataSourceProperties.getProperty("defaultReadOnly")));
poolDataSource.setTestOnBorrow(Boolean.valueOf(dataSourceProperties.getProperty("testOnBorrow")));
poolDataSource.setValidationQuery("SELECT 0");

答案 5 :(得分:11)

另一种选择是HikariCP

以下是比较benchmark

答案 6 :(得分:8)

以下是一些文章显示DBCP的性能明显高于C3P0或Proxool。另外根据我自己的经验,c3p0确实有一些很好的功能,比如预处理语句池,比DBCP更可配置,但DBCP在我使用它的任何环境中都明显更快。

dbcp和c3p0之间的区别?绝对没有! (一个酒井开发者博客)  <击> http://blogs.nyu.edu/blogs/nrm216/sakaidelic/2007/12/difference_between_dbcp_and_c3.html

参见博客文章评论中的JavaTech文章“连接池摊牌”。

答案 7 :(得分:7)

this article中提到了另一种替代方法Proxool。

您或许可以找出Hibernate为其默认连接池实现捆绑c3p0的原因?

答案 8 :(得分:7)

不幸的是它们都已过时了。 DBCP最近有所更新,另外两个是2-3岁,有许多突出的错误。

答案 9 :(得分:7)

如果配置正确,Dbcp已准备就绪。

例如,它在商业网站上使用,每天350000访客,并且有200个连接池。

如果您正确配置它,它可以很好地处理超时。

版本2正在进行中,并且它有一个背景,因为很多,它使它可靠 生产问题已得到解决。

我们将它用于我们的批处理服务器解决方案,它已经运行了数百个批次,可以在数据库中运行数百万行。

tomcat jdbc pool运行的性能测试表明它的性能优于cp30。

答案 10 :(得分:4)

刚刚用DBCP浪费了一天半的时间。即使我使用的是最新的DBCP版本,我也遇到了与j pimmel完全相同的问题。我根本不推荐使用DBCP,特别是当数据库消失时,它无法将连接从池中抛出,当数据库恢复时无法重新连接,并且无法动态地将连接对象添加回池中(它永远挂起)一个后JDBCconnect I / O套接字读取)

我现在正在切换到C3P0。我在以前的项目中使用它,它的工作和表现就像一个魅力。

答案 11 :(得分:4)

当我们使用mutithreading项目时,c3p0很好。在我们的项目中,我们使用DBCP同时使用多个线程执行,如果我们使用更多的线程执行,我们就会得到连接超时。所以我们选择了c3p0配置。

答案 12 :(得分:3)

一个易于使用的好选择是DBPool

“基于Java的数据库连接池实用程序,支持基于时间的到期,语句缓存,连接验证以及使用池管理器轻松配置。”

http://www.snaq.net/java/DBPool/

答案 13 :(得分:3)

我们遇到了需要引入连接池的情况,我们面前有4个选项。

  • DBCP2
  • C3P0
  • Tomcat JDBC
  • HikariCP

我们根据我们的标准进行了一些测试和比较,并决定选择HikariCP。 阅读this article,解释了我们选择HikariCP的原因。

答案 14 :(得分:1)

要以最佳方式实施C3P0,然后check this answer

C3P0

对于企业应用程序,C3P0是最佳方法。 C3P0是一个易于使用的库,用于通过JNDI可绑定的数据源(包括实现连接和语句池的数据源)增强传统的(基于DriverManager的)JDBC驱动程序,如jdbc3规范和jdbc2 std扩展所述。 C3P0还可以稳健地处理数据库断开连接和恢复时的透明重新连接,而如果从其下方拔出了链接,则DBCP不会恢复连接。

因此,这就是c3p0和其他连接池也准备了语句高速缓存的原因-它允许应用程序代码避免处理所有这些问题。语句通常保存在一些有限的LRU池中,因此常见语句会重用PreparedStatement实例。

更糟糕的是,DBCP仍将连接对象返回到基础传输中断的应用程序。 c3p0的一个常见用例是替换Apache Tomcat附带的标准DBCP连接池。通常,程序员会遇到这样的情况,即连接未在DBCP连接池中正确回收,并且在这种情况下c3p0是有价值的替代品。

在当前更新中,C3P0具有一些出色的功能。那些在下面:

ComboPooledDataSource dataSource = new ComboPooledDataSource();
dataSource.setMinPoolSize();
dataSource.setMaxPoolSize();
dataSource.setMaxIdleTime();
dataSource.setMaxStatements();
dataSource.setMaxStatementsPerConnection();
dataSource.setMaxIdleTimeExcessConnections();

此处,最大和最小 poolsize 定义了连接范围,这意味着此应用程序将进行最小和最大连接的方式。 MaxIdleTime()定义何时释放空闲连接。

DBCP

这种方法也不错,但是有一些缺点,例如连接超时和连接重新实现。 当我们使用多线程项目时,C3P0很好。在我们的项目中,通过使用DBCP同时使用了多个线程执行,然后,如果使用更多的线程执行,则连接超时。因此,我们进行了c3p0配置。 我根本不建议使用DBCP,尤其是当数据库消失时,它会把连接从池中抛出,如果DB回来时它无法重新连接,并且无法将连接对象动态地添加回池中(这种情况会永远挂起) JDBCconnect后的I / O套接字读取)

谢谢:)

答案 15 :(得分:0)

我的推荐是

光>德鲁伊> UCP> c3p0> DBCP

它基于我的测试-20190202,在我的本地测试环境中(docker / pool中的4GB mac / mysql minSize = 1,maxSize = 8),hikari可以服务1024个线程x 1024次以获取连接,平均时间每个线程完成的时间为1或2百万秒,而c3p0只能服务256个线程x 1024次,每个线程的平均时间已经为2100万秒。 (512个线程失败)。