亚洲全黄无码一级在线看_国产剧情久久久性色_无码av一区二区三区无码_亚洲成a×人片在线观看

當(dāng)前位置: 首頁(yè) > 科技新聞 >

看了這篇Redis,我以大溫州私家偵探專生的身份,

時(shí)間:2019-11-29 10:10來(lái)源:網(wǎng)絡(luò)整理 瀏覽:
前幾天講了Redis的面試知識(shí)點(diǎn),當(dāng)然那只是一部分,我相信各位在面試,或者實(shí)際開發(fā)過(guò)程中對(duì)緩存雪崩,穿透,擊穿也不陌生吧,就算沒(méi)遇到過(guò)但是你

前幾天講了Redis的面試知識(shí)點(diǎn),當(dāng)然那只是一部分,我相信各位在面試,或者實(shí)際開發(fā)過(guò)程中對(duì)緩存雪崩,穿透,擊穿也不陌生吧,就算沒(méi)遇到過(guò)但是你肯定聽(tīng)過(guò),那三者到底有什么區(qū)別,我們又應(yīng)該怎么去防止這樣的情況發(fā)生呢,我們有請(qǐng)受害者。

面試開始

一個(gè)大腹便便,穿著格子襯衣的中年男子,拿著一個(gè)滿是劃痕的mac向你走來(lái),看著快禿頂?shù)念^發(fā),心想著肯定是尼瑪頂級(jí)架構(gòu)師吧!但是我們腹有詩(shī)書氣自華,虛都不虛。

小伙子我看你的簡(jiǎn)歷上寫到了Redis,那么我們直接開門見(jiàn)山,直接懟常見(jiàn)的幾個(gè)大問(wèn)題,Redis雪崩了解么?

帥氣迷人的面試官您好,我了解的,目前電商首頁(yè)以及熱點(diǎn)數(shù)據(jù)都會(huì)去做緩存 ,一般緩存都是定時(shí)任務(wù)去刷新,或者是查不到之后去更新的,定時(shí)任務(wù)刷新就有一個(gè)問(wèn)題。

舉個(gè)簡(jiǎn)單的例子:如果所有首頁(yè)的Key失效時(shí)間都是12小時(shí),中午12點(diǎn)刷新的,我零點(diǎn)有個(gè)秒殺活動(dòng)大量用戶涌入,假設(shè)當(dāng)時(shí)每秒 6000 個(gè)請(qǐng)求,本來(lái)緩存在可以扛住每秒 5000 個(gè)請(qǐng)求,但是緩存當(dāng)時(shí)所有的Key都失效了。此時(shí) 1 秒 6000 個(gè)請(qǐng)求全部落數(shù)據(jù)庫(kù),數(shù)據(jù)庫(kù)必然扛不住,它會(huì)報(bào)一下警,真實(shí)情況可能DBA都沒(méi)反應(yīng)過(guò)來(lái)就直接掛了。此時(shí),如果沒(méi)用什么特別的方案來(lái)處理這個(gè)故障,DBA 很著急,重啟數(shù)據(jù)庫(kù),但是數(shù)據(jù)庫(kù)立馬又被新的流量給打死了。這就是我理解的緩存雪崩。

我刻意看了下我做過(guò)的項(xiàng)目感覺(jué)再吊的都不允許這么大的QPS直接打DB去,不過(guò)沒(méi)慢SQL加上分庫(kù),大表分表可能還還算能頂,但是跟用了Redis的差距還是很大

同一時(shí)間大面積失效,那一瞬間Redis跟沒(méi)有一樣,那這個(gè)數(shù)量級(jí)別的請(qǐng)求直接打到數(shù)據(jù)庫(kù)幾乎是災(zāi)難性的,你想想如果打掛的是一個(gè)用戶服務(wù)的庫(kù),那其他依賴他的庫(kù)所有的接口幾乎都會(huì)報(bào)錯(cuò),如果沒(méi)做熔斷等策略基本上就是瞬間掛一片的節(jié)奏,你怎么重啟用戶都會(huì)把你打掛,等你能重啟的時(shí)候,用戶早就睡覺(jué)去了,并且對(duì)你的產(chǎn)品失去了信心,什么垃圾產(chǎn)品。

面試官摸了摸自己的頭發(fā),嗯還不錯(cuò),那這種情況咋整?你都是怎么去應(yīng)對(duì)的?

處理緩存雪崩簡(jiǎn)單,在批量往Redis存數(shù)據(jù)的時(shí)候,把每個(gè)Key的失效時(shí)間都加個(gè)隨機(jī)值就好了,這樣可以保證數(shù)據(jù)不會(huì)在同一時(shí)間大面積失效,我相信,Redis這點(diǎn)流量還是頂?shù)米〉摹?/p>

setRedis(Key,value,time + Math.random() * 10000);
復(fù)制代碼

如果Redis是集群部署,將熱點(diǎn)數(shù)據(jù)均勻分布在不同的Redis庫(kù)中也能避免全部失效的問(wèn)題,不過(guò)本渣我在生產(chǎn)環(huán)境中操作集群的時(shí)候,單個(gè)服務(wù)都是對(duì)應(yīng)的單個(gè)Redis分片,是為了方便數(shù)據(jù)的管理,但是也同樣有了可能會(huì)失效這樣的弊端,失效時(shí)間隨機(jī)是個(gè)好策略。

或者設(shè)置熱點(diǎn)數(shù)據(jù)永遠(yuǎn)不過(guò)期,有更新操作就更新緩存就好了(比如運(yùn)維更新了首頁(yè)商品,那你刷下緩存就完事了,不要設(shè)置過(guò)期時(shí)間),電商首頁(yè)的數(shù)據(jù)也可以用這個(gè)操作,保險(xiǎn)。

那你了解緩存穿透和擊穿么,可以說(shuō)說(shuō)他們跟雪崩的區(qū)別么?

嗯,了解,我先說(shuō)一下緩存穿透吧,緩存穿透是指緩存和數(shù)據(jù)庫(kù)中都沒(méi)有的數(shù)據(jù),而用戶不斷發(fā)起請(qǐng)求,我們數(shù)據(jù)庫(kù)的 id 都是1開始自增上去的,如發(fā)起為id值為 -1 的數(shù)據(jù)或 id 為特別大不存在的數(shù)據(jù)。這時(shí)的用戶很可能是攻擊者,攻擊會(huì)導(dǎo)致數(shù)據(jù)庫(kù)壓力過(guò)大,嚴(yán)重會(huì)擊垮數(shù)據(jù)庫(kù)。

小點(diǎn)的單機(jī)系統(tǒng),基本上用postman就能搞死,比如我自己買的阿里云服務(wù)

像這種你如果不對(duì)參數(shù)做校驗(yàn),數(shù)據(jù)庫(kù)id都是大于0的,我一直用小于0的參數(shù)去請(qǐng)求你,每次都能繞開Redis直接打到數(shù)據(jù)庫(kù),數(shù)據(jù)庫(kù)也查不到,每次都這樣,并發(fā)高點(diǎn)就容易崩掉了。

至于緩存擊穿嘛,這個(gè)跟緩存雪崩有點(diǎn)像,但是又有一點(diǎn)不一樣,緩存雪崩是因?yàn)榇竺娣e的緩存失效,打崩了DB,而緩存擊穿不同的是緩存擊穿是指一個(gè)Key非常熱點(diǎn),在不停的扛著大并發(fā),大并發(fā)集中對(duì)這一個(gè)點(diǎn)進(jìn)行訪問(wèn),當(dāng)這個(gè)Key在失效的瞬間,持續(xù)的大并發(fā)就穿破緩存,直接請(qǐng)求數(shù)據(jù)庫(kù),就像在一個(gè)完好無(wú)損的桶上鑿開了一個(gè)洞。

面試官露出欣慰的眼光,那他們分別怎么解決

緩存穿透我會(huì)在接口層增加校驗(yàn),比如用戶鑒權(quán)校驗(yàn),參數(shù)做校驗(yàn),不合法的參數(shù)直接代碼Return,比如:id 做基礎(chǔ)校驗(yàn),id <=0的直接攔截等。

這里我想提的一點(diǎn)就是,我們?cè)陂_發(fā)程序的時(shí)候都要有一顆“不信任”的心,就是不要相信任何調(diào)用方,比如你提供了API接口出去,你有這幾個(gè)參數(shù),那我覺(jué)得作為被調(diào)用方,任何可能的參數(shù)情況都應(yīng)該被考慮到,做校驗(yàn),因?yàn)槟悴幌嘈耪{(diào)用你的人,你不知道他會(huì)傳什么參數(shù)給你。

舉個(gè)簡(jiǎn)單的例子,你這個(gè)接口是分頁(yè)查詢的,但是你沒(méi)對(duì)分頁(yè)參數(shù)的大小做限制,調(diào)用的人萬(wàn)一一口氣查 Integer.MAX_VALUE 一次請(qǐng)求就要你幾秒,多幾個(gè)并發(fā)你不就掛了么?是公司同事調(diào)用還好大不了發(fā)現(xiàn)了改掉,但是如果是黑客或者競(jìng)爭(zhēng)對(duì)手呢?在你雙十一當(dāng)天就調(diào)你這個(gè)接口會(huì)發(fā)生什么,就不用我說(shuō)了吧。

從緩存取不到的數(shù)據(jù),在數(shù)據(jù)庫(kù)中也沒(méi)有取到,這時(shí)也可以將對(duì)應(yīng)Key的Value對(duì)寫為null、位置錯(cuò)誤、稍后重試這樣的值具體取啥問(wèn)產(chǎn)品,或者看具體的場(chǎng)景,緩存有效時(shí)間可以設(shè)置短點(diǎn),如30秒(設(shè)置太長(zhǎng)會(huì)導(dǎo)致正常情況也沒(méi)法使用)。

這樣可以防止攻擊用戶反復(fù)用同一個(gè)id暴力攻擊,但是我們要知道正常用戶是不會(huì)在單秒內(nèi)發(fā)起這么多次請(qǐng)求的,那網(wǎng)關(guān)層Nginx本渣我也記得有配置項(xiàng),可以讓運(yùn)維大大對(duì)單個(gè)IP每秒訪問(wèn)次數(shù)超出閾值的IP都拉黑。

那你還有別的辦法么?

還有我記得Redis還有一個(gè)高級(jí)用法布隆過(guò)濾器(Bloom Filter)這個(gè)也能很好的防止緩存穿透的發(fā)生,他的原理也很簡(jiǎn)單就是利用高效的數(shù)據(jù)結(jié)構(gòu)和算法快速判斷出你這個(gè)Key是否在數(shù)據(jù)庫(kù)中存在,不存在你return就好了,存在你就去查了DB刷新KV再return。

那又有小伙伴說(shuō)了如果黑客有很多個(gè)IP同時(shí)發(fā)起攻擊呢?這點(diǎn)我一直也不是很想得通,但是一般級(jí)別的黑客沒(méi)這么多肉雞,再者正常級(jí)別的Redis集群都能抗住這種級(jí)別的訪問(wèn)的,小公司我想他們不會(huì)感興趣的。把系統(tǒng)的高可用做好了,集群還是很能頂?shù)摹?/p>

緩存擊穿的話,設(shè)置熱點(diǎn)數(shù)據(jù)永遠(yuǎn)不過(guò)期。或者加上互斥鎖就能搞定了
作為暖男,代碼我肯定幫你們準(zhǔn)備好了

面試結(jié)束

嗯嗯還不錯(cuò),三個(gè)點(diǎn)都回答得很好,今天也不早了,面試就先到這里,明天你再過(guò)來(lái)二面我繼續(xù)問(wèn)一下你關(guān)于Redis集群高可用,主從同步,哨兵等知識(shí)點(diǎn)的問(wèn)題。

總結(jié)

我們玩歸玩,鬧歸鬧,別拿面試開玩笑。

本文簡(jiǎn)單的介紹了,Redis雪崩,擊穿,穿透,三者其實(shí)都差不多,但是又有一些區(qū)別,在面試中其實(shí)這是問(wèn)到緩存必問(wèn)的,大家不要把三者搞混了,因?yàn)榫彺嫜┍?、穿透和擊穿,是緩存最大的?wèn)題,要么不出現(xiàn),一旦出現(xiàn)就是致命性的問(wèn)題,所以面試官一定會(huì)問(wèn)你。

大家一定要理解是怎么發(fā)生的,以及是怎么去避免的,發(fā)生之后又怎么去搶救,你可以不是知道很深入,但是你不能一點(diǎn)都不去想,面試有時(shí)候不一定是對(duì)知識(shí)面的拷問(wèn),或許是對(duì)你的態(tài)度的拷問(wèn),如果你思路清晰,然后知其然還知其所以然那就很贊,還知道怎么預(yù)防那來(lái)上班吧。

技術(shù)總結(jié):

一般避免以上情況發(fā)生我們從三個(gè)時(shí)間段去分析下:

事前:Redis 高可用,主從+哨兵,Redis cluster,避免全盤崩潰。事中:本地 ehcache 緩存 + Hystrix 限流+降級(jí),避免** MySQL** 被打死。事后:Redis 持久化 RDB+AOF,一旦重啟,自動(dòng)從磁盤上加載數(shù)據(jù),快速恢復(fù)緩存數(shù)據(jù)。

上面的幾點(diǎn)我會(huì)在吊打系列Redis篇全部講一下這個(gè)月應(yīng)該可以吧Redis更完,限流組件,可以設(shè)置每秒的請(qǐng)求,有多少能通過(guò)組件,剩余的未通過(guò)的請(qǐng)求,怎么辦?走降級(jí)!可以返回一些默認(rèn)的值,或者友情提示,或者空白的值。

好處:

數(shù)據(jù)庫(kù)絕對(duì)不會(huì)死,限流組件確保了每秒只有多少個(gè)請(qǐng)求能通過(guò)。 只要數(shù)據(jù)庫(kù)不死,就是說(shuō),對(duì)用戶來(lái)說(shuō),3/5 的請(qǐng)求都是可以被處理的。 只要有 3/5 的請(qǐng)求可以被處理,就意味著你的系統(tǒng)沒(méi)死,對(duì)用戶來(lái)說(shuō),可能就是點(diǎn)擊幾次刷不出來(lái)頁(yè)面,但是多點(diǎn)幾次,就可以刷出來(lái)一次。

這個(gè)在目前主流的互聯(lián)網(wǎng)大廠里面是最常見(jiàn)的,你是不是好奇,某明星爆出什么事情,你發(fā)現(xiàn)你去微博怎么刷都空白界面,但是有的人又直接進(jìn)了,你多刷幾次也出來(lái)了,現(xiàn)在知道了吧,那是做了降級(jí),犧牲部分用戶的體驗(yàn)換來(lái)服務(wù)器的安全,可還行?

推薦內(nèi)容