1. 程式人生 > >【大話存儲II】學習筆記(15章),NoSQL

【大話存儲II】學習筆記(15章),NoSQL

cnblogs 高並發 屏蔽 圖片 一定的 mon 是把 類型 擴容

互聯網運營商(NSP)的數據中心是數據最集中的地方,也正是因為海量的數據存儲與訪問,傳統的存儲架構已經無法滿足了現有的需求。

比如每秒幾十萬次的隨機IOPS、每秒10GB的流量,一般都需要使用高端存儲,當然價格將不便宜。而且擴展性不好,擴容成本高。

業務的不斷增加,導致互聯網運營商逐步使用分布式系統來構建底層文件系統及數據庫,比如Google的GFS+Bigtable

我們先來看一下為了應對大並發、大流量下,架構的逐步的變化,最後引入NoSQL。

傳統數據庫架構的演進

使用緩存技術

隨著訪問量的上升,流量的增加,使用MySQL的架構的網站在數據庫上出現了性能問題。

要應對傳統的MySQL性能不足的問題,最容易想到的就是加緩存

。如果只是使用文件緩存,由於多臺Web服務器通過文件緩存不能共享,所以性能並沒有那麽顯著的提升。

那麽,我們能不能把緩存單獨抽取出來,形成一個緩存服務器,使用這臺服務器的大內存來進行緩存,而且這個緩存服務器還可以分布式部署,既保證了共享,又保證了性能。

最典型的代表就是Memcached緩存服務器,我們可以使用一致性Hash算法來進行多臺服務器的擴展。
詳細可見另一篇文章Memcached集群?

MySQL的主從讀寫分離

使用緩存服務器只能算是權宜之計,訪問量繼續上漲的話,數據庫還是會有瓶頸。因為互聯網應用主要還在於,既然讀壓力這麽大,我們能不能使用集群來負載分擔呢。

但是數據庫因為需要保證它的原子性、一致性等,不能簡單的使用多臺服務器並發訪問這種架構。

我們可以進行讀寫分離,將數據庫分為Master和Slave兩種角色,Master主要用於寫,Slave主要用於讀,而且Slave可以多臺來負載均衡。

這樣就可以提高讀寫性能和讀庫的可擴展性。具體可以參考數據庫(七),讀寫分離到CQRS。

分表分庫

使用 Memcached高速緩存和MySQL主從復制,可以緩解讀壓力,但是寫壓力怎麽辦?

最開始MySQL使用MyISAM引擎,它是使用表鎖的,高並發有嚴重的鎖問題。於是MySQL使用InnoDB引擎代替它。

同時我們還可以進行分表分庫來緩解寫壓力:

有兩種方式:

  • 水平切:一張表,水平切分為多張表,每個節點存儲一張子表,同時保留有另外兩個副本。所以每張子表都包含原表所有的列。

  • 垂直切分:也就是把一張表豎直的切分,原來的列拆分開,相當於把數據打散,可以獲得超高的隨機查詢性能。

水平切分不需要人參與,盲切分即可。
而垂直切分相當於基於業務層面的切分,具有一定的人為介入度。

MySQL的問題

上面講到了MySQL在應對大流量大並發的情況下做的努力,底層架構可謂是越來越復雜,相應的,上層的應用也會越來越復雜。雖然有些公司開發了中間件層來屏蔽開發的復雜性,但是避免不了架構的復雜。

那麽之前的方法主要的缺點在於:

  • 不夠靈活:表結構更改困難,關系型數據庫的表結構在一開始的時候就確定好了,很難更改。

  • 擴展性的問題還是沒有解決,MySQL推出的集群解決方案,只能保證可靠性,無法保證性能。

  • MySQL經常需要存放大文本字段,導致數據庫恢復的時候特別慢。

技術分享圖片

所以關系型數據庫很強大,但是不代表它能應付所有的應用環境,如果我們想要保證良好的擴展性、靈活性,可能需要對原有的功能做一些取舍。

下面我們將介紹一下CAP理論,它會從理論的角度告訴我們魚和熊掌不可兼得

CAP理論

所謂CAP(Consistency , Availability , Partition Tolerance)理論,指的是一致性、性能、擴展性無法完全兼顧。也就是,我們想要良好的擴展性,則就無法像傳統關系型數據那樣能保證強一致性。

到底要不要保證強一致性,主要看客戶的業務是否需要強一致性呢?

比如DNS解析,更換主機之後暫時不能全網刷新,這種短暫的不一致是可以接受的。

不過也不是完全不能保證一致性,我們有個模型叫NWR模型,可以在一致性和性能上實現平衡。

  • N表示數據塊的副本數,

  • W表示寫入幾份就返回成功。

  • R表示為了保證讀一致,客戶端需要從保存副本的N個節點中的幾個同時讀出數據。

比如N=3,W=1,也就是保存3副本,寫入1份數據就返回成功。

  • 如果R=1,當寫入一份數據並返回成功以後開始讀,因為同時只讀一份數據,則既可能從未更新的兩份數據中讀,又可能從剛剛更新的數據中讀,所以有可能讀到未更新的版本。

  • 如果R=2,同樣也不能保證一定讀到最新更新的版本。

  • 如果R=3,則一定可以保證讀到的3份數據有一份是最新的,只需要看誰的時間戳更晚就行。

如果W=2,就必須同步寫成功2個副本才返回後成功,讀的時候,只需要讀2份就能保證最新了。

總結一下,只要$W+R>N$,就可以保證讀一致。

技術分享圖片

NoSQL

弱一致性的數據庫集群一般都不支持事務,同時也不支持關聯查詢,為什麽呢?因為關聯查詢需要其他節點提供數據分片,也就是說一次查詢需要調動其他的節點,這樣並發性能將會非常差。

這種去掉關聯性,只能保證弱一致性的輕量級的分布式數據庫系統,就屬於 NoSQL系統

NoSQL被我們用得最多的當數key-value存儲,當然還有其他的文檔型的、列存儲、圖型數據庫、xml數據庫等。

NoSQL分類

我們對現有的NoSQL進行簡單的分類。

類型 部分代表 特點
列存儲 Hbase 方便做數據壓縮,對針對某一列或者某幾列的查詢有非常大的IO優勢。
文檔存儲 MongoDB JSON。因為存儲的內容是一個文檔,所以可以對某些字段建立索引
key-value存儲 Redis/Memcache 可以通過key快速查詢到其value
圖存儲 Neo4J 如要存儲的是圖形關系,使用這種方式最好。
對象存儲 db4o/Versant 通過對象的方式存取數據。
xml數據庫 Berkeley DB XML 支持XML的內部查詢語法,比如Xpath。

技術分享圖片

優勢

  • 更加的靈活

    關系型數據庫需要事先設定要數據字段,而NoSQL存儲方式是鍵值對、列存儲等,更加的靈活,特別適合處理非結構化、半結構化得的數據。

  • 易擴展:去掉了關系數據庫的關系型特性,數據無關系,更易於擴展。

  • 高性能:因為NoSQL去掉了關系性,數據庫結構簡單,性能自然更高。

  • 高可用:大多數NoSQL數據支持自動復制,可以可以在不太影響性能的情況下,方便的實現高可用架構。

  • 自動分片:

    關系型數據因為是結構化的,所以一般來說都是垂直擴展,也就意味著單臺服務器需要持有整個數據庫,擴展性自然不好。

    NoSQL一般都支持自動分片,也就是會自動向多臺服務器上分發數據,這一切是對應用透明的。

缺點

了解了優點我們也需要了解NoSQL的缺點。

NoSQL相對於關系型數據庫,放棄了很多功能,比如事務、一致性等,而且目前來說還不夠成熟,同時很多NoSQL不提供SQL支持。

所以最好的方法是了解那些場景適合NoSQL,然後與萬能的關系型數據庫結合來使用
技術分享圖片

一些涉及到K-V的存儲、用戶密碼存儲、Session會話存儲等,可以使用NoSQL

【大話存儲II】學習筆記(15章),NoSQL