close

其實當我們的完成上一篇的架構之後,整個大架構已經慢慢的趨向完整,不過我們發現,當我們Server機器越加越多的時候,資料庫卻是仍只有一台,此時我們的服務上限變成是由資料庫來決定,端看資料庫能多快回應我們的要求,來決定我們服務的上限。

很明顯的,這是一個問題,但是這個問題要如何改善呢?即然伺服器可以分流,那資料庫能不能也做分流呢?如果可以的話,對程式面來說,又需要做什麼變更呢?

我們先以分流的方式來檢討一下,我們預計資料庫的分流應該達到什麼樣的目的:

  1. 能夠有多台資料庫同時供應服務。

  2. 每個連線來要求資料時,不管被導到那一台資料庫,都能取得相同的資料。

看起來問題比較大的是第二點,我們的多台資料庫必須能夠自動同步資料才行;即然如此,我們回到資料庫程式來看看它本身有什麼功能能達到自動同步這個要求:

  1. 異地備援:能夠自動的將資料備份到不同機器。

  2. 叢集:能夠自動的同步資料到叢集中的機器。

因為我們還需要考慮第一點-能夠有多台資料庫同時供應服務,所以看起來「叢集」是比較適合目前的狀況,所以下方我們來討論資料庫的叢集。

資料庫叢集(Cluster)

之前有談過伺服器的叢集,它能夠將多台伺服器「連在一起」,並共享彼此的Session;資料庫的叢集也是一樣,是透過資料庫本身的設定,將多台資料庫「連在一起」,並「自動」同步資料。

至於該如何設定叢集,則要視讀者使用的資料庫為何,並上網查找相關的設定方式;筆者將如何設定MariaDB的Cluster方式另寫一篇,讀者可以參考。

當我們假定我們設定完成的資料庫叢集,是一個Active-Active架構(A-A架構,代表任何一台均可接受連線服務),所以會需要一台Load Balance來判斷那一台伺服器比較空閒,所以Cluster後的架構如下圖:

大架構-負載平衝+Memcached+NFS+資料庫分流.png

 

資料庫Cluster與程式

當架設好資料庫的Cluster後,一樣,重回到程式的角度,來查看程式是否要變更;不過在談論之前,必須先瞭解,Cluster的自動同步功能,是針對所有在Cluster中的機器,也就是說,只要其有一台的資料變更,另外二台就會同步相關資料;可是有些資料必需要唯一,或者有些資料的存入會有順序,或者我們在不同的資料庫上,針對同一筆資料做修改,像這些狀況,如果同時有二台資庫可供寫入時,難道不會有問題嗎?答案是會的,或者是說,無法保證不會出問題。

為了避免這類問題,我們應該做的事情是:確保寫入都會被導到同一台機器,而讀取則導到任意一台機器即可。而如何才能達到這個要求呢?有二種方式:

  1. 由Load Balance來判斷寫入與讀取,來判斷導向的機器。

  2. 由程式控管,切分寫入與讀取使用的連線不同;讀取連線到Load Balance,而寫入則連線到特定機器,或是有提供Failover(容錯移轉)的機器上。(之後會談到MariaDB的Cluster設定如何切分讀取與寫入,並設定容錯移轉。)

第一種的由Load Balance來判斷,這種方式比較特殊,等同Load Balance還必須去判斷SQL語法,所以一般是由Load Balance的軟體來處理,並且只針對特定的資料庫,據筆者所知,目前Postgresql中的軟體pgpool-II可以達到這件事,詳細可參考(http://www.pgpool.net/docs/latest/pgpool-en.html#stream)。

至於第二種方式,是比較一般的方式,透過連到Load Balance的Port不同,來導向到對應的機器,不過這種方式跟第一種方式比起來,以一個程式設計師來說,當然比較喜歡第一種方式,因為程式不需要做任何變更;但是第二種方式的話,程式需要:

  • 切分Write、Read的Connection。

  • 針對所有與SQL有關的Method,確認要呼叫的Connection。

這不是一件小事,但是目前沒有更好的方法了,筆者之後如果有空會再補一篇,在JAVA中如何切分Read與Writer的Connection的方法。

arrow
arrow

    JAVA Programmer 發表在 痞客邦 留言(0) 人氣()