設定JDBC資料庫連線池
前言
JDBC作為J2EE的規範之一,它定義了連線資料庫的介面,封裝了連線資料庫的細節問題,給開發人員極大的方便。開發人員只需要實現這些介面,就可以連線不同的資料庫,不需要針對不同資料庫寫不同的連線程式碼。
JDBC連線資料庫
JDBC連線資料庫,簡單來說有下面四個步驟:
1、載入資料庫驅動
2、建立連線
3、訪問資料庫
4、關閉資料庫連線
當然,JDBC連線資料庫沒有這麼簡單,它還包括Statement物件的建立,如果需要,還會建立ResultSet物件,關閉連線的時候,也要相應的先關閉其他物件,如《
連線池
資料庫連線池又稱Resource Pool,基本思想是為資料庫連線建立一個緩衝池,當建立連線池時,預先在連線池中配置一些數量的連線,當需要建立資料庫連線時,就在連線池中取出連線,用完之後再放進去,否則當使用連線數超過最大連線數,接著再請求連線時,就會出現Timeout異常。當需要建立的連線數超過連線池中預先放入的連線,再建立新的連線。當然,連線池可以設定它的最大連線數,以及初始化時的連線數。
JDBC並未提供連線池的方法,我們可以採用Tomcat,對連線池的一些引數進行設定。我們可以通過進入Tomcat的管理介面進行設定,或者直接設定Tomcat的server.xml檔案,因為管理介面設定完成後,同樣也會寫入server.xml檔案中。如果採用xml檔案直接配置,就需要把下面的程式碼放入server.xml檔案中,然後修改相應的引數就可以了。設定連線池的時候,有幾個固定的引數:
<Resource name="jdbc/drp" type="javax.sql.DataSource" maxActive="4" maxIdle="2" username="drp1" maxWait="5000" driverClassName="oracle.jdbc.driver.OracleDriver" password="123456" url="jdbc:oracle:thin:@localhost:1521:orcl"/>
driverClassName:表示資料庫驅動,上面程式碼中是Oracle驅動,如果是Mysql資料庫,只需改成Mysql的驅動類就好了
url:資料庫路徑,如果是連線伺服器的資料庫,只需要將localhost改成伺服器IP地址就OK了
username:username是資料庫的使用者名稱
password:是該使用者的密碼
maxActive:最大的可用的連線數量
maxIdle:初始化時,連線池中的空閒連線數
maxWait:最長等待時間,如果超過這個時間沒有獲得連線(單位為ms),則提示Timeout
name:是隨便起的名字
type:指的是實現的javax.sql.DataSource的介面,是JDBC提供的
配置完成之後,該連線池就對Tomcat伺服器下的所有程式起作用。如果想讓該連線池設定只對某一個應用程式起作用,只需要將上述程式碼拷貝到tomcat/conf路徑下的context.xml檔案中,然後將該檔案剪下到應用程式的WebRoot/META-INF路徑下即可。
當需要建立連線池時,直接去連線池中取就好了:
Connection conn = null;
try {
Context ctx = new InitialContext();
//通過JNDI查詢DataSource
DataSource ds = (DataSource)ctx.lookup("java:comp/env/jdbc/drp");
conn = ds.getConnection();
}catch(Exception e) {
e.printStackTrace();
throw new ApplicationException("系統錯誤,請聯絡系統管理員");
}
return conn;
執行緒併發問題
資料庫連線池並不是執行緒安全的,所以我們可以在建立Connection時可以採用synchronized關鍵字來保證執行緒同步,也可以採用ThreadLocal進行管理。當一個方法需要建立資料庫連線時,可以先判斷它所在的執行緒是否已經綁定了一個Connection,如果已經綁定了,那就直接用,如果沒有,就建立一個Connection物件,放到ThreadLocal中,以備後面的方法使用。
private static ThreadLocal<Connection> connectionHolder = new ThreadLocal<Connection>();
/**
* 得到Connection
* @return
*/
public static Connection getConnection() {
Connection conn = connectionHolder.get();
//如果在當前執行緒中沒有繫結相應的Connection
if (conn == null) {
//建立一個新連線
conn = DbUtil.getConnection();
//將連線放入ThreadLocal
connectionHolder.set(conn);
}
return conn;
}
當然,關閉連線時,也需要把Connection從ThreadLocal中移除出去:
public static void closeConnection() {
Connection conn = connectionHolder.get();
if (conn != null) {
try {
conn.close();
//從ThreadLocal中清除Connection
connectionHolder.remove();
} catch (SQLException e) {
e.printStackTrace();
}
}
}
總結
JDBC作為一個規範,它將連線資料庫的細節封裝了起來,提供給我們各種介面,只要去實現這些介面,就可以實現資料庫的連線。JDBC連線資料庫有固定的步驟,而每建立一個連線都需要執行這個過程,對於訪問人數較多的網站來說,如果不對資料庫連線進行限制的話,系統會一直建立連線,這樣就會造成資料庫的記憶體洩露,對資料安全造成問題,所以就採用了連線池技術做改善,在連線池中限制最大連線數,只允許程式建立一定量的連線,用完之後就一定要放回連線池。即使這樣,也會出現多執行緒併發問題,對於執行緒同步,可以採用synchronized關鍵字,也可以使用ThreadLocal來解決。