c3p0連接池的配置方式

c3p0的配置方式分爲三種,分別是
1.setters一個個地設置各個配置項
2.類路徑下提供一個c3p0.properties文件
3.類路徑下提供一個c3p0-config.xml文件

1.setters一個個地設置各個配置項
這種方式最繁瑣,形式一般是這樣:

01 Properties props = new Properties();
02 InputStream in = ConnectionManager.class.getResourceAsStream("/c3p0.properties");
03 props.load(in);
04 in.close();
05  
06 ComboPooledDataSource cpds = new ComboPooledDataSource();
07 cpds.setDriverClass(props.getProperty("driverClass"));
08 cpds.setJdbcUrl(props.getProperty("jdbcUrl"));
09 cpds.setUser(props.getProperty("user"));
10 cpds.setPassword(props.getProperty("password"));

因爲繁瑣,所以很不適合採用,於是文檔提供了另外另種方式。

2. 類路徑下提供一個c3p0.properties文件 
文件的命名必須是c3p0.properties,裏面配置項的格式爲:

1 c3p0.driverClass=com.mysql.jdbc.Driver
2 c3p0.jdbcUrl=jdbc:mysql://localhost:3306/jdbc
3 c3p0.user=root
4 c3p0.password=java

上面只提供了最基本的配置項,其他配置項參照 文檔配置,記得是c3p0.後面加屬性名就是了,最後初始化數據源的方式就是這樣簡單: 
1 private static ComboPooledDataSource ds = new ComboPooledDataSource();
2      
3 public static Connection getConnection() {
4     try {
5         return ds.getConnection();
6     catch (SQLException e) {
7         throw new RuntimeException(e);
8     }
9 }

3.類路徑下提供一個c3p0-config.xml文件  
這種方式使用方式與第二種差不多,但是有更多的優點 
(1).更直觀明顯,很類似hibernate和spring的配置 
(2).可以爲多個數據源服務,提供default-config和named-config兩種配置方式 
下面是一個配置模板: 
01 <c3p0-config>
02   <default-config>  
03     <property name="user">root</property>
04     <property name="password">java</property>
05     <property name="driverClass">com.mysql.jdbc.Driver</property>
06     <property name="jdbcUrl">jdbc:mysql://localhost:3306/jdbc</property>
07      
08     <property name="initialPoolSize">10</property>
09     <property name="maxIdleTime">30</property>
10     <property name="maxPoolSize">100</property>
11     <property name="minPoolSize">10</property>
12   </default-config>
13    
14   <named-config name="myApp">
15     <property name="user">root</property>
16     <property name="password">java</property>
17     <property name="driverClass">com.mysql.jdbc.Driver</property>
18     <property name="jdbcUrl">jdbc:mysql://localhost:3306/jdbc</property>
19      
20     <property name="initialPoolSize">10</property>
21     <property name="maxIdleTime">30</property>
22     <property name="maxPoolSize">100</property>
23     <property name="minPoolSize">10</property>
24   </named-config>
25 </c3p0-config>

如果要使用default-config則初始化數據源的方式與第二種一樣,如果要使用named-config裏面配置初始化數據源,則只要使用一個帶參數的ComboPooledDataSource構造器就可以了 
1 private static ComboPooledDataSource ds = new ComboPooledDataSource("myApp");

下面整理一下從文檔和網上學習到的c3p0配置的理解 (user,password,driverClass,jdbcUrl沒有說的必要) 

1.基本配置項

01 acquireIncrement
02 default : 3
03 連接池在無空閒連接可用時一次性創建的新數據庫連接數
04  
05 initialPoolSize
06 default : 3
07 連接池初始化時創建的連接數
08  
09 maxPoolSize
10 default : 15
11 連接池中擁有的最大連接數,如果獲得新連接時會使連接總數超過這個值則不會再獲取新連接,而是等待
12 其他連接釋放,所以這個值有可能會設計地很大
13  
14 maxIdleTime
15 default : 0 單位 s
16 連接的最大空閒時間,如果超過這個時間,某個數據庫連接還沒有被使用,則會斷開掉這個連接
17 如果爲0,則永遠不會斷開連接
18  
19 minPoolSize
20 default : 3
21 連接池保持的最小連接數,後面的maxIdleTimeExcessConnections跟這個配合使用來減輕連接池的負載

2.管理連接池的大小和連接的生存時間

01 maxConnectionAge
02 default : 0 單位 s
03 配置連接的生存時間,超過這個時間的連接將由連接池自動斷開丟棄掉。當然正在使用的連接不會馬上斷開,而是等待
04 它close再斷開。配置爲0的時候則不會對連接的生存時間進行限制。
05  
06 maxIdleTimeExcessConnections
07 default : 0 單位 s
08 這個配置主要是爲了減輕連接池的負載,比如連接池中連接數因爲某次數據訪問高峯導致創建了很多數據連接
09 但是後面的時間段需要的數據庫連接數很少,則此時連接池完全沒有必要維護那麼多的連接,所以有必要將
10 斷開丟棄掉一些連接來減輕負載,必須小於maxIdleTime。配置不爲0,則會將連接池中的連接數量保持到minPoolSize。
11 爲0則不處理。

maxIdleTime也可以歸屬到這一類,前面已經寫出來了。

3.配置連接測試:因爲連接池中的數據庫連接很有可能是維持數小時的連接,很有可能因爲數據庫服務器的問題,網絡問題等導致實際連接已經無效,但是連接池裏面的連接還是有效的,如果此時獲得連接肯定會發生異常,所以有必要通過測試連接來確認連接的有效性。
下面的前三項用來配置如何對連接進行測試,後三項配置對連接進行測試的時機。

01 automaticTestTable
02 default : null
03 用來配置測試連接的一種方式。配置一個表名,連接池根據這個表名創建一個空表,
04 並且用自己的測試sql語句在這個空表上測試數據庫連接
05 這個表只能由c3p0來使用,用戶不能操作,同時用戶配置的preferredTestQuery 將會被忽略。
06  
07 preferredTestQuery
08 default : null
09 用來配置測試連接的另一種方式。與上面的automaticTestTable二者只能選一。
10 如果要用它測試連接,千萬不要設爲null,否則測試過程會很耗時,同時要保證sql語句中的表在數據庫中一定存在。
11  
12 connectionTesterClassName
13 default :  com.mchange.v2.c3p0.impl.DefaultConnectionTester
14 連接池用來支持automaticTestTable和preferredTestQuery測試的類,必須是全類名,就像默認的那樣,
15 可以通過實現UnifiedConnectionTester接口或者繼承AbstractConnectionTester來定製自己的測試方法
16  
17 idleConnectionTestPeriod
18 default : 0
19 用來配置測試空閒連接的間隔時間。測試方式還是上面的兩種之一,可以用來解決MySQL8小時斷開連接的問題。因爲它
20 保證連接池會每隔一定時間對空閒連接進行一次測試,從而保證有效的空閒連接能每隔一定時間訪問一次數據庫,將於MySQL
21 8小時無會話的狀態打破。爲0則不測試。
22  
23 testConnectionOnCheckin
24 default : false
25 如果爲true,則在close的時候測試連接的有效性。爲了提高測試性能,可以與idleConnectionTestPeriod搭配使用,
26 配置preferredTestQuery或automaticTestTable也可以加快測試速度。
27  
28 testConnectionOnCheckout
29 default : false
30 性能消耗大。如果爲true,在每次getConnection的時候都會測試,爲了提高性能,
31 可以與idleConnectionTestPeriod搭配使用,
32 配置preferredTestQuery或automaticTestTable也可以加快測試速度。

4.配置PreparedStatement緩存 
01 maxStatements
02 default : 0
03 連接池爲數據源緩存的PreparedStatement的總數。由於PreparedStatement屬於單個Connection,所以
04 這個數量應該根據應用中平均連接數乘以每個連接的平均PreparedStatement來計算。爲0的時候不緩存,
05 同時maxStatementsPerConnection的配置無效。
06  
07 maxStatementsPerConnection
08 default : 0
09 連接池爲數據源單個Connection緩存的PreparedStatement數,這個配置比maxStatements更有意義,因爲
10 它緩存的服務對象是單個數據連接,如果設置的好,肯定是可以提高性能的。爲0的時候不緩存。

5.重連相關配置 
01 acquireRetryAttempts
02 default : 30
03 連接池在獲得新連接失敗時重試的次數,如果小於等於0則無限重試直至連接獲得成功
04  
05 acquireRetryDelay
06 default : 1000 單位ms
07 連接池在獲得新連接時的間隔時間
08  
09 breakAfterAcquireFailure
10 default : false
11 如果爲true,則當連接獲取失敗時自動關閉數據源,除非重新啓動應用程序。所以一般不用。

個人覺得上述三個沒有更改的必要,但可以將acquireRetryDelay配置地更短一些

6.定製管理Connection的生命週期

1 connectionCustomizerClassName
2 default : null
3 用來定製Connection的管理,比如在Connection acquire 的時候設定Connection的隔離級別,或者在
4 Connection丟棄的時候進行資源關閉,就可以通過繼承一個AbstractConnectionCustomizer來實現相關
5 方法,配置的時候使用全類名。有點類似監聽器的作用。

例如: 
01 import java.sql.Connection;
02 import com.mchange.v2.c3p0.AbstractConnectionCustomizer;
03  
04 public class ConnectionCustomizer extends AbstractConnectionCustomizer{
05  
06     @Override
07     public void onAcquire(Connection c, String parentDataSourceIdentityToken)
08             throws Exception {
09         System.out.println("acquire : " + c);
10     }
11     @Override
12     public void onCheckIn(Connection c, String parentDataSourceIdentityToken)
13             throws Exception {
14         System.out.println("checkin : " + c);
15     }
16     @Override
17     public void onCheckOut(Connection c, String parentDataSourceIdentityToken)
18             throws Exception {
19         System.out.println("checkout : " + c);
20     }
21     @Override
22     public void onDestroy(Connection c, String parentDataSourceIdentityToken)
23             throws Exception {
24         System.out.println("destroy : " + c);
25     }
26 }

1 <property name="connectionCustomizerClassName">liuyun.zhuge.db.ConnectionCustomizer</property>

7.配置未提交的事務處理 
1 autoCommitOnClose
2 default : false
3 連接池在回收數據庫連接時是否自動提交事務
4 如果爲false,則會回滾未提交的事務
5 如果爲true,則會自動提交事務
6  
7 forceIgnoreUnresolvedTransactions
8 default : false
9 這個配置強烈不建議爲true。

一般來說事務當然由自己關閉了,爲什麼要讓連接池來處理這種不細心問題呢?

8.配置debug和回收Connection

01 unreturnedConnectionTimeout
02 default : 0 單位 s
03 爲0的時候要求所有的Connection在應用程序中必須關閉。如果不爲0,則強制在設定的時間到達後回收
04 Connection,所以必須小心設置,保證在回收之前所有數據庫操作都能夠完成。這種限制減少Connection未關閉
05 情況的不是很適用。爲0不對connection進行回收,即使它並沒有關閉。
06  
07 debugUnreturnedConnectionStackTraces
08 default : false
09 如果爲true並且unreturnedConnectionTimeout設爲大於0的值,當所有被getConnection出去的連接
10 unreturnedConnectionTimeout時間到的時候,就會打印出堆棧信息。只能在debug模式下適用,因爲
11 打印堆棧信息會減慢getConnection的速度

同第七項一樣的,連接用完當然得close了,不要通過unreturnedConnectionTimeout讓連接池來回收未關閉的連接。

9.其他配置項:因爲有些配置項幾乎沒有自己配置的必要,使用默認值就好,所以沒有再寫出來

1 checkoutTimeout
2 default : 0
3 配置當連接池所有連接用完時應用程序getConnection的等待時間。爲0則無限等待直至有其他連接釋放
4 或者創建新的連接,不爲0則當時間到的時候如果仍沒有獲得連接,則會拋出SQLException
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章