資料庫連線池的理解

lusklusklusk發表於2017-02-16
瞭解連線池之前,我們先了解SESSIONS引數的解釋
SESSIONS specifies the maximum number of sessions that can be created in the system.
Because every login requires a session, this parameter effectively determines the
maximum number of concurrent users in the system. You should always set this
parameter explicitly to a value equivalent to your estimate of the maximum number of
concurrent users, plus the number of background processes, plus approximately 10%
for recursive sessions.

連線,是應用程式與資料庫互動的一種方式。為什麼“資料庫連線很昂貴“,下面透過例項解釋它究竟是什麼。
下面是MySQL資料庫建立連線的的一段程式碼:
[java] view plaincopyprint?
String connUrl ="jdbc:mysql://your.database.domain/yourDBname";  
Class.forName("com.mysql.jdbc.Driver");  
Connection con =DriverManager.getConnection (connUrl);  
當我們建立了一個Connection物件,它在內部都執行了什麼:
1.“DriverManager”檢查並註冊驅動程式; 
2.“com.mysql.jdbc.Driver”就是我們註冊了的驅動程式,它會在驅動程式類中呼叫“connect(url…)”方法。 
3.com.mysql.jdbc.Driver的connect方法根據我們請求的“connUrl”,建立一個“Socket連線”,連線到IP為“your.database.domain”,預設埠3306的資料庫。 
4.建立的Socket連線將被用來查詢我們指定的資料庫,並最終讓程式返回得到一個結果。 
簡單的獲取一個連線,系統卻要在背後做很多消耗資源的事情,大多時候,建立連線的時間比執行sql語句的時間還要長。


使用者每次請求都需要向資料庫獲得連結,而資料庫建立連線通常需要消耗相對較大的資源,建立時間也較長,每次都得花費0.05s~1s的時間。這個時間對於一次或幾次資料庫操作,或許感覺不出系統有多大的開銷。可是對於現在的web應用,尤其是大型電子商務網站,同時有幾百人甚至幾千人線上是很正常的事。假設網站一天10萬訪問量,資料庫伺服器就需要建立10萬次連線,極大的浪費資料庫的資源,並且極易造成資料庫伺服器記憶體溢位、拓機。在這種情況下,頻繁的進行資料庫連線操作勢必佔用很多的系統資源,網站的響應速度必定下降,嚴重的甚至會造成伺服器的崩潰。不是危言聳聽,這就是制約某些電子商務網站發展的技術瓶頸問題。其次,對於每一次資料庫連線,使用完後都得斷開。否則,如果程式出現異常而未能關閉,將會導致資料庫系統中的記憶體洩漏,最終將不得不重啟資料庫。還有,這種開發不能控制被建立的連線物件數,系統資源會被毫無顧及的分配出去,如連線過多,也可能導致記憶體洩漏,伺服器崩潰。

透過以上描述可以理解,“資料庫連線”是一種稀缺的資源,那怎麼辦呢?可不可以這樣,我們查詢完資料庫後,不關閉連線,而是暫時存放起來,當別人使用時,把這個連線給他們使用。就避免了一次建立資料庫連線和斷開的操作時間消耗。提高了連線的複用度,從而降低建立新連線的開銷,同時還可以加快使用者的訪問速度。對了,這就產生了連線池的概念,資料庫連線池的基本思想就是為資料庫連線建立一個“緩衝池”。預先在緩衝池中放入一定數量的連線,當需要建立資料庫連線時,只需從“緩衝池”中取出一個,使用完畢之後再放回去。我們可以透過設定連線池最大連線數來防止系統無盡的與資料庫連線。

當連線池裡的連線數足夠時,它負責分配連線,允許應用程式重複使用一個現有的資料庫連線,而不是重新建立一個,當連線池裡的連線數不足時,它負責建立新的連線並放回連線池,當連線池裡的連線數很多且都沒有被使用時,它負責釋放這些連線


如果應用沒有出現明顯的高峰,但是發現v$session來自同一臺機器的同一個程式的狀態為INACTIVE的連線非常多,就要考慮該伺服器上的程式的連線池配置了
select count(ss.SID),ss.machine,ss.status,ss.TERMINAL,ss.PROGRAM,ss.USERNAME,ss.CLIENT_IDENTIFIER 
from v$session ss group by ss.machine,ss.status,ss.TERMINAL,ss.PROGRAM,ss.USERNAME,ss.CLIENT_IDENTIFIER having count(ss.SID)>10






現實中在程式中配置的連線池例子
<!--連線池 -->
<bean id="dataSourceDmt" class="com.alibaba.druid.pool.DruidDataSource" init-method="init" destroy-method="close"> 
<!-- 基本屬性 url、user、password -->
<property name="driverClassName" value="oracle.jdbc.driver.OracleDriver" />
<property name="url" value="jdbc:oracle:thin:@192.168.1.1:1521:DB" />
<property name="username" value="user" />
<property name="password" value="passwd" />
<!--配置初始化大小、最小、最大 -->
<property name="initialSize" value="2" />
<property name="minIdle" value="2" />
<property name="maxActive" value="100" /> 
<!-- 配置獲取連線等待超時的時間(1分鐘) -->
<property name="maxWait" value="60000" /> 
<!-- 配置間隔多久才進行一次檢測,檢測需要關閉的空閒連線,單位是毫秒(1分鐘) -->
<property name="timeBetweenEvictionRunsMillis" value="60000" /> 
<!-- 配置一個連線在池中最小生存的時間(連線保持空閒而不被驅逐的最長時間),單位是毫秒(5分鐘) -->
<property name="minEvictableIdleTimeMillis" value="300000" />
</bean>




最小的空閒連線數
上述案例配置值為2,就是池子裡永遠都會有2個連線,不管是否需要和資料庫進行資料互動,當程式開始向DB建立第1個對話時,直接就會去使用這個空閒連線,建立第2個會話時也會使用空閒連線,當建立第3個會話時就會新建一個連線

初始連線數
程式啟動後就自動建立和DB的會話數,該值過大,則程式啟動慢,上述案例配置值為2


最大的活動連線數
程式可以和DB建立的最大會話數,上述案例配置值為100

程式如果沒有配置這些,則最小空閒連線數0、初始連線數0、最大活動會話連線數不受限制


上述配置案例,當建立第3個會話時就會新建一個連線,並把這個連線放到連線池裡面。依次類推,池子裡最多有100個連線,當和DB的連線結束時,池子裡的連線狀態變成空閒,1分鐘後程式會自動清除空閒連線,使池子裡保持只有2個空閒連線,所以不會出 現某個時刻併發量100後,池子裡永遠保持100個連線數,程式會清理掉空閒連線的。程式連線池裡的連線就是表示已經和DB建立的連線,連線池裡面是10,就是已經建立了10個連線,當然也不會一直在池子裡放10個空閒連線,這樣100套應用連線同一DB,每個應用都這樣的話 ,資料庫就是1000個連線


如何確保連線池中的最小連線數呢?有動態和靜態兩種策略。動態即每隔一定時間就對連線池進行檢測,如果發現連線數量小於最小連線數,則補充相應數量的新連線,以保證連線池的正常運轉。靜態是發現空閒連線不夠時再去檢查。

對資料庫而言兩點
1.頻繁的進行資料庫連線操作勢必佔用資料庫伺服器很多的系統資源
2.如果程式出現異常而未能關閉,將會導致資料庫系統中的記憶體洩漏,最終將不得不重啟資料庫。

當客戶請求資料庫連線時,首先檢視應用程式的連線池中是否有空閒連線,如果存在空閒連線,則將連線分配給客戶使用;如果沒有空閒連線,則轉到資料庫,資料庫檢視當前所開的連線數是否已經達到最大連線數,例如如果沒有達到就重新建立一個請求的客戶;如果達到,就按設定的最大等待時間進行等待,如果超出最大等待時間,則丟擲異常給客戶。


對應用程式而言
1.較小的連線池,啟動快
2.較多的連線池,啟動慢

來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/30126024/viewspace-2133637/,如需轉載,請註明出處,否則將追究法律責任。

相關文章