緩衝穿透,緩衝穿透緩衝雪崩
所謂緩衝,就是在邏輯代碼和資料庫之間插入那麼一層緩衝層,查詢等操作可以在緩衝層解決,不用再去資料庫操作,以達到緩解資料庫壓力和增加查詢效率的那麼一個緩衝層。從這個角度來看,對於緩衝穿透,字面理解就是將這個緩衝層打透,我每次都能直達資料庫,你得緩衝層不起什麼效果,就是這麼一個概念。
網上也有對這個概念的各種解釋,我簡要提取整理一下就是: 查詢一個一定不存在的資料,由於緩衝是不命中,資料庫也不存在並且資料庫不存在時不會寫入緩衝,導致這個資料每次請求都要到資料庫去查詢,失去了緩衝的意義。 這種情況如果少了還可以,如果並發量達到一個高度,可能會給資料庫造成很大壓力,甚至宕機。 當然,有了問題我們就得有解決的方案,目前比較成熟的解決方案主要是兩種:一是空值緩衝,二是設定過濾器。簡單介紹一下這兩種方案。
-
- 空值緩衝:當我們去查詢一個快取資料,這個資料查不到,就去資料庫查詢,再查不到,如果直接報錯返回,下次再查,還是這麼個迴圈。比如電商平台,我們查詢一個商家推薦商品,當前要是沒有推薦,我們每次去查詢該商家的推薦商品,都要去資料庫查詢。設想一下,如果我們第一次在資料庫查詢完沒有查到資料,就在緩衝中緩衝該商家的推薦商品是空,那麼下一次我們再查詢的時候,是不是就可以直接到緩衝層就可以知道該商家沒有推薦商品,而不用去查詢資料庫了。所謂的空值緩衝,就是這樣一個邏輯,將第一次查出來的空值,設定在緩衝中,以達到緩解資料庫壓力的問題。
- 設定過濾器,一般是使用一個bitmap(也可以使用一個set集合),將可查的資料放入這個集合當中。再拿商家推薦例子吧,我將有推薦的商家id都放入這個一個集合當中,每次查詢的時候都去這個集合過濾一遍,只有合格的資料,我才去緩衝查,不合格的,我就預設他是null就可以了。
當然過濾方案不止這一種啊,比如像我們要是緩衝ip資訊,這個欄位是有規則的啊,我們可以根據ip規則進行過濾再去查詢,防止惡意攻擊等等。
對於這兩種解決方案,普遍使用的都是第一種,對比來說,第一種和第二種,對資料即時變化要求是不一樣的,空值過濾適用於資料變化頻率較高也可以,而你寫死的set集合,對於變化頻率較高的資料,顯然是不擅長的。而對於維護成本來將,第一種的代碼維護成本也是簡單暴力,第二種則略顯複雜。 寫到這裡,就多扯兩句,關於緩衝存在的問題,還有緩衝失效和緩衝雪崩等問題。緩衝失效,很多情況,一個是緩衝時間到了,失效了,其次還有伺服器關了,沒有作用了。關於緩衝雪崩,這個肯定算是事故了,比如緩衝宕機了,或者緩衝大面積的失效,引起一段時間大量資料直接存取資料庫,造成極大的壓力,這種情況就叫緩衝雪崩。但是目前為止,好像還沒有什麼好的緩衝雪崩的解決方案,只能預防為主。預防措施主要有1.使用鎖或者隊列來空值資料庫訪問量,2.使用不失效緩衝(長短兩個緩衝)和設定緩衝時間均勻分布,3.不要同一時間很多緩衝都失效等。