我想知道如何正确确定c3p0 max_statements使用的值。我已经经历了一些缓存死锁,这似乎指向我基于所有SO Q& A I读过的max_statements配置。
我正在使用mysql,当我进行一些多线程我有4个活动线程时,就会发生死锁。
我的配置
<property name="hibernate.connection.provider_class">org.hibernate.service.jdbc.connections.internal.C3P0ConnectionProvider</property>
<property name="hibernate.c3p0.min_size">10</property>
<property name="hibernate.c3p0.max_statements">50</property>
<property name="hibernate.c3p0.max_size">50</property>
<property name="hibernate.c3p0.idle_test_period">1800</property>
<property name="hibernate.c3p0.timeout">3600</property>
例外
[WARN] async.ThreadPoolAsynchronousRunner com.mchange.v2.async.ThreadPoolAsynchronousRunner$DeadlockDetector@72df1587 -- APPARENT DEADLOCK!!! Complete Status:
Managed Threads: 3
Active Threads: 3
Active Tasks:
com.mchange.v2.c3p0.stmt.GooGooStatementCache$StatementDestructionManager$1UncheckedStatementCloseTask@e877a61
on thread: C3P0PooledConnectionPoolManager[identityToken->1hge0wd9a1o1iea71i8u346|1a799bb]-HelperThread-#2
com.mchange.v2.c3p0.stmt.GooGooStatementCache$StatementDestructionManager$1UncheckedStatementCloseTask@109b1150
on thread: C3P0PooledConnectionPoolManager[identityToken->1hge0wd9a1o1iea71i8u346|1a799bb]-HelperThread-#0
com.mchange.v2.c3p0.stmt.GooGooStatementCache$StatementDestructionManager$1UncheckedStatementCloseTask@3eb42946
on thread: C3P0PooledConnectionPoolManager[identityToken->1hge0wd9a1o1iea71i8u346|1a799bb]-HelperThread-#1
Pending Tasks:
com.mchange.v2.c3p0.stmt.GooGooStatementCache$1StmtAcquireTask@52729f95
Pool thread stack traces:
Thread[C3P0PooledConnectionPoolManager[identityToken->1hge0wd9a1o1iea71i8u346|1a799bb]-HelperThread-#0,5,main]
com.mysql.jdbc.PreparedStatement.realClose(PreparedStatement.java:2765)
com.mysql.jdbc.StatementImpl.close(StatementImpl.java:541)
com.mchange.v1.db.sql.StatementUtils.attemptClose(StatementUtils.java:53)
com.mchange.v2.c3p0.stmt.GooGooStatementCache$StatementDestructionManager$1UncheckedStatementCloseTask.run(GooGooStatementCache.java:938)
com.mchange.v2.async.ThreadPoolAsynchronousRunner$PoolThread.run(ThreadPoolAsynchronousRunner.java:648)
Thread[C3P0PooledConnectionPoolManager[identityToken->1hge0wd9a1o1iea71i8u346|1a799bb]-HelperThread-#1,5,main]
com.mysql.jdbc.PreparedStatement.realClose(PreparedStatement.java:2765)
com.mysql.jdbc.StatementImpl.close(StatementImpl.java:541)
com.mchange.v1.db.sql.StatementUtils.attemptClose(StatementUtils.java:53)
com.mchange.v2.c3p0.stmt.GooGooStatementCache$StatementDestructionManager$1UncheckedStatementCloseTask.run(GooGooStatementCache.java:938)
com.mchange.v2.async.ThreadPoolAsynchronousRunner$PoolThread.run(ThreadPoolAsynchronousRunner.java:648)
Thread[C3P0PooledConnectionPoolManager[identityToken->1hge0wd9a1o1iea71i8u346|1a799bb]-HelperThread-#2,5,main]
com.mysql.jdbc.PreparedStatement.realClose(PreparedStatement.java:2765)
com.mysql.jdbc.StatementImpl.close(StatementImpl.java:541)
com.mchange.v1.db.sql.StatementUtils.attemptClose(StatementUtils.java:53)
com.mchange.v2.c3p0.stmt.GooGooStatementCache$StatementDestructionManager$1UncheckedStatementCloseTask.run(GooGooStatementCache.java:938)
com.mchange.v2.async.ThreadPoolAsynchronousRunner$PoolThread.run(ThreadPoolAsynchronousRunner.java:648)
所以我的问题是如何确定这些值应该是什么。我确定必须在没有猜测的情况下做到这一点。
我读过的文章
should i activate c3p0 statement pooling?
How to trace and prevent the deadlock appeared in c3po which is running in seperate processes?
答案 0 :(得分:4)
要解决与Oracle / jTDS / mySQL下的Statement缓存相关的死锁,请确保您使用的是最近的c3p0(0.9.5.1是当前版本),请参阅statementCacheNumDeferredCloseThreads和Configuring Statement Pooling
TL; DR set config param
<property name="hibernate.c3p0.statementCacheNumDeferredCloseThreads">1</property>
max_statements
的确切值只是偶然与此问题相关联。如果max_statements
太小,您将不必要地翻译语句,并且在一些驱动程序中与PreparedStatement.close()
的脆弱性相关的此问题将更频繁地出现。
但是,对于hibernate.c3p0.max_statements
50的池,maxPoolSize
的值太小。即使在修复死锁问题之后,通过语句转换也会减少或消除语句缓存的任何性能优势。要计算hibernate.c3p0.max_statements
(映射到c3p0.maxStatements
)的良好值,请计算应用程序中经常使用 的不同PreparedStatements的数量,并将其乘以{{1} (或者在你的情况下maxPoolSize
)。或者,只需将hibernate.c3p0.max_size
设置为应用程序频繁使用的不同PreparedStatements的数量。
请参阅maxStatements,maxStatementsPerConnection和Configuring Statement Pooling。