計(jì)算機(jī)領(lǐng)域多處地方用到緩存,比如說(shuō)為了緩解CPU和內(nèi)存之間的速度不匹配問(wèn)題,我們往往通過(guò)增加一級(jí)、二級(jí)、三級(jí)緩存,CPU先從緩存中取指令,如果取不到,再?gòu)膬?nèi)存中取,并更新緩存,同時(shí),根據(jù)程序的局部性原理,使得大部分情況下緩存都會(huì)命中。
創(chuàng)新互聯(lián)云計(jì)算的互聯(lián)網(wǎng)服務(wù)提供商,擁有超過(guò)13年的服務(wù)器租用、大邑服務(wù)器托管、云服務(wù)器、網(wǎng)站空間、網(wǎng)站系統(tǒng)開發(fā)經(jīng)驗(yàn),已先后獲得國(guó)家工業(yè)和信息化部頒發(fā)的互聯(lián)網(wǎng)數(shù)據(jù)中心業(yè)務(wù)許可證。專業(yè)提供云主機(jī)、網(wǎng)站空間、國(guó)際域名空間、VPS主機(jī)、云服務(wù)器、香港云服務(wù)器、免備案服務(wù)器等。
目前,Web應(yīng)用的核心數(shù)據(jù)通常存放在數(shù)據(jù)庫(kù)中,比如說(shuō)用戶信息、訂單信息、交易信息等,同時(shí),數(shù)據(jù)庫(kù)和編程語(yǔ)言是無(wú)關(guān)的,通過(guò)SQL交互,Java、Php等語(yǔ)言寫的程序需要訪問(wèn)數(shù)據(jù)庫(kù),執(zhí)行業(yè)務(wù)邏輯,展示結(jié)果給用戶。但是數(shù)據(jù)庫(kù)有一定的局限性,譬如:1.數(shù)據(jù)庫(kù)連接是非常 "昂貴 "的資源,為了復(fù)用這些資源,目前采用連接池技術(shù),2. 連接池的連接數(shù)是有限的,如果用戶過(guò)多,勢(shì)必要等待,3. 讀寫數(shù)據(jù)時(shí)需要加鎖。
通過(guò)上述介紹,我們知道一個(gè)大型系統(tǒng)中數(shù)據(jù)庫(kù)往往會(huì)成為瓶頸,我們不能每次訪問(wèn)都訪問(wèn)數(shù)據(jù)庫(kù),尤其是在多用戶,大并發(fā)的情況下。面對(duì)這種情況,我們通常采用何種方法呢?在計(jì)算機(jī)行業(yè)中的所有問(wèn)題,都可以通過(guò)增加一個(gè)抽象層來(lái)解決。那么,針對(duì)數(shù)據(jù)庫(kù)這個(gè)瓶頸,我們可以在應(yīng)用層和數(shù)據(jù)庫(kù)層增加一層,即緩存層。
如果你是某某大型公司的首席架構(gòu)師,現(xiàn)在公司需要自研一套緩存系統(tǒng),你應(yīng)該怎么設(shè)計(jì)呢?我想在設(shè)計(jì)之前應(yīng)該想好以下幾個(gè)問(wèn)題:
目前常見的數(shù)據(jù)格式有序列化對(duì)象、XML、JSON、字符串(key,value)和基本的數(shù)據(jù)結(jié)構(gòu),其中針對(duì)Java語(yǔ)言的序列化對(duì)象有序列化和反序列化,而Google研發(fā)的protobuf是和語(yǔ)言無(wú)關(guān)的,比如說(shuō)Python將某對(duì)象序列化,Java能將這個(gè)對(duì)象進(jìn)行反序列化。
考慮到公司有很多后端小組,并且使用不同的編程語(yǔ)言,這就要求我們自研的緩存系統(tǒng)應(yīng)該和編程語(yǔ)言無(wú)關(guān),基于此,我們需要制定一套協(xié)議來(lái)支持各種語(yǔ)言??蛻舳巳绾问褂眠@套協(xié)議?最常見的就是客戶端/服務(wù)器模型。首先,服務(wù)器監(jiān)聽請(qǐng)求;接著,客戶端發(fā)送請(qǐng)求,獲得響應(yīng),其中客戶端發(fā)送的請(qǐng)求就是協(xié)議;最后,基于Socket通信。比如說(shuō):set 'name' 'mukedada'
、get name
。
緩存服務(wù)器端在啟動(dòng)的時(shí)候,應(yīng)該設(shè)置緩存大小,當(dāng)緩存被沾滿時(shí),采用LRU算法。
對(duì)于大型應(yīng)用服務(wù)器,單機(jī)的緩存服務(wù)器是支撐不了的。那么,就需要對(duì)緩存服務(wù)器進(jìn)行水平擴(kuò)展(即增刪服務(wù)器,當(dāng)活動(dòng)結(jié)束后,就需要考慮刪減服務(wù)器),那么用什么算法讓數(shù)據(jù)相對(duì)平均的分配到每臺(tái)服務(wù)器?同時(shí),這個(gè)算法應(yīng)該放在客戶端還是服務(wù)端呢?
它的典型應(yīng)用是Memcached,Memcached使用的是一致性Hash算法,在介紹它之前,我們先來(lái)看一下余數(shù)算法。對(duì)于用戶要存儲(chǔ)的(key,value),計(jì)算key的整數(shù)哈希值,然后對(duì)服務(wù)器的數(shù)目求余,這樣來(lái)確定存儲(chǔ)服務(wù)器。這個(gè)方法存在一個(gè)致命的問(wèn)題:當(dāng)服務(wù)器個(gè)數(shù)發(fā)送變化時(shí),余數(shù)會(huì)發(fā)生變化,這樣一來(lái)需要重新到數(shù)據(jù)庫(kù)獲取數(shù)據(jù)。
為了加深大家的理解,舉個(gè)具體的實(shí)例:假設(shè)有3臺(tái)服務(wù)器0、1、2,key1、key2的hash值分別是100,99,對(duì)應(yīng)的余數(shù)分別是1和0,也就是說(shuō)它們分別存放于編號(hào)為1和0的服務(wù)器中,現(xiàn)在如果增加一臺(tái)服務(wù)器3,那么它們的余數(shù)也會(huì)隨之發(fā)生變化,100%4 = 0,99%4 = 3,但是它們?cè)?、3號(hào)服務(wù)器卻找不到對(duì)應(yīng)的數(shù)據(jù)。
為了解決余數(shù)算法存在的問(wèn)題,我們的先輩們提出了分布式一致性hash算法。它思路就是當(dāng)服務(wù)器個(gè)數(shù)發(fā)生變化時(shí),盡可能的減少影響。譬如:當(dāng)我們新增node5,只影響局部范圍內(nèi)的key,而余數(shù)算法則影響全局。
但是它也存在分布不均勻的問(wèn)題,導(dǎo)致有的服務(wù)器上緩存的數(shù)據(jù)多,有的少。一種方法就是虛擬節(jié)點(diǎn),也就是說(shuō)讓一個(gè)服務(wù)器化身為多個(gè)虛擬節(jié)點(diǎn),分布到環(huán)上。Memcache采用的就是這種方法。
另一種方法就是Hash槽。Redis采用的就是這種方法,在介紹路由實(shí)現(xiàn)時(shí)會(huì)詳細(xì)介紹該方法。
代理實(shí)現(xiàn)
代理程序放在服務(wù)器端,它的典型案例有Twemproxy和Codis。它的基本思想:應(yīng)用程序向Proxy發(fā)送請(qǐng)求,Proxy通過(guò)一定算法計(jì)算得到數(shù)據(jù)應(yīng)該從哪個(gè)節(jié)點(diǎn)獲取,并且返回響應(yīng)給客戶端。為了防止Proxy出現(xiàn)單點(diǎn)故障,可以通過(guò)集群等方式實(shí)現(xiàn)Proxy高可用。
CRC16(key)%16384
求余,最終會(huì)落到0~16383這個(gè)區(qū)間的槽中。但是,每當(dāng)新增一個(gè)節(jié)點(diǎn)時(shí),需要從原先的每個(gè)節(jié)點(diǎn)中獲取hash槽,這時(shí)需要涉及數(shù)據(jù)遷移的過(guò)程。如果在數(shù)據(jù)遷移的過(guò)程中有一個(gè)用戶請(qǐng)求,這個(gè)時(shí)候該怎么辦?目前一種解決方法是讓node1和node4的持有相同的槽,但是設(shè)置不同的狀態(tài),例如node1的槽的狀態(tài)設(shè)置為正在遷移,而node4的狀態(tài)是正在導(dǎo)入,首先將請(qǐng)求交給node1,如果node1中有數(shù)據(jù)則直接返回,如果沒有則交給ndoe4。如下圖所示。
同時(shí),我們注意到node1、node2等存在單點(diǎn)故障,為增加可用性,我們對(duì)每個(gè)node使用主從模式。數(shù)據(jù)首先寫入到master節(jié)點(diǎn),之后有兩種方式,方式一,直接將結(jié)果返回給客戶端,然后將master節(jié)點(diǎn)數(shù)據(jù)同步到slave從節(jié)點(diǎn)中,這樣做的好處就是響應(yīng)周期短,缺點(diǎn)是可能存在數(shù)據(jù)不一致的情況,即master節(jié)點(diǎn)將結(jié)果返回給客戶端之后,還沒來(lái)得及將數(shù)據(jù)同步到slave節(jié)點(diǎn)中就發(fā)生故障,那么這部分?jǐn)?shù)據(jù)就會(huì)丟失。方式二,數(shù)據(jù)寫入到master節(jié)點(diǎn)之后,需要將數(shù)據(jù)同步到slave節(jié)點(diǎn)成功之后,再將結(jié)果返回給客戶端,這種方式保證了數(shù)據(jù)強(qiáng)一致性,但是用戶需要更長(zhǎng)的時(shí)間來(lái)等待。
用戶每次訪問(wèn)緩存都沒有命中,導(dǎo)致每次請(qǐng)求都要訪問(wèn)數(shù)據(jù)庫(kù),這就是緩存擊穿問(wèn)題,出現(xiàn)這種情況導(dǎo)致緩存沒起效果,反而增加了系統(tǒng)消耗。針對(duì)這個(gè)問(wèn)題,一般諸如雙十一等活動(dòng)都會(huì)在活動(dòng)開始之前將用戶信息預(yù)先存放到緩存中。
另外有需要云服務(wù)器可以了解下創(chuàng)新互聯(lián)scvps.cn,海內(nèi)外云服務(wù)器15元起步,三天無(wú)理由+7*72小時(shí)售后在線,公司持有idc許可證,提供“云服務(wù)器、裸金屬服務(wù)器、高防服務(wù)器、香港服務(wù)器、美國(guó)服務(wù)器、虛擬主機(jī)、免備案服務(wù)器”等云主機(jī)租用服務(wù)以及企業(yè)上云的綜合解決方案,具有“安全穩(wěn)定、簡(jiǎn)單易用、服務(wù)可用性高、性價(jià)比高”等特點(diǎn)與優(yōu)勢(shì),專為企業(yè)上云打造定制,能夠滿足用戶豐富、多元化的應(yīng)用場(chǎng)景需求。
網(wǎng)頁(yè)名稱:漫談Web緩存架構(gòu)-創(chuàng)新互聯(lián)
網(wǎng)站URL:http://jinyejixie.com/article44/gijee.html
成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供移動(dòng)網(wǎng)站建設(shè)、定制網(wǎng)站、網(wǎng)站收錄、建站公司、App開發(fā)、品牌網(wǎng)站制作
聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶投稿、用戶轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請(qǐng)盡快告知,我們將會(huì)在第一時(shí)間刪除。文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如需處理請(qǐng)聯(lián)系客服。電話:028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時(shí)需注明來(lái)源: 創(chuàng)新互聯(lián)
猜你還喜歡下面的內(nèi)容