直播間原始碼,透過Redis實現資料快取

雲豹科技曉彤發表於2021-07-28

需求說明

在直播間原始碼中,使用者檢視直播列表,這個列表資料具有時時性,並且是強熱點資料,也就是說每時每刻都可能會有新的直播。這些資料如果每次都去資料庫讀取肯定是不可取的,所以這可以考慮使用redis來實現。

使用redis有序集合來儲存直播列表

思路簡介 

由於每時每刻都有可能會有新的資料進入到sortedset中,所以使用redis的有序集合進行儲存。直播間原始碼之所以使用有序集合是考慮到翻頁的時候不要有重複資料,如果需求允許重複資料的出現,則可以使用先進先出佇列queue。

直播間原始碼重複資料出現原因:假如使用者當前再看第一頁的資料,此時又有兩條新資料插入到sortedSet中,那麼如果用zrevrange(key, pageSize*pageNum, pageSize*(pageNum+1)進行取值,就會出現2條重複資料了

每生成一條資料,將其新增到redis有序集合中,根據ID(如果id是數值型的)或者時間戳(這個要進行處理,後面會講)進行排序。取的時候透過以下方法進行取值。

Set<String> zrevrangeByScore(final String key, final double max, final double min, final int offset, final int count)
1
假如每頁5條資料:
第一頁:jedisCluster.zrevrangeByScore(key , Double.MAX_VALUE , 0, 0 , 5)
記錄第一頁中後一條資料的score是M
第二頁:jedisCluster.zrevrangeByScore(key , M , 0 ,1, 5)
以此類推。

我這裡使用的jedisCluster客戶端

如何保證sortedSet集合數量

假如只快取100條資料,每頁10條顯示。直播間原始碼可以採取緩衝區策略,就像redis中儲存字串時使用的SDS動態字串。我們可以每次在儲存的時候檢測set的大小zcard,如果zcard超過了120(允許多快取20個,這樣可以減少擷取set的操作次數,提高效率),則可以使用以下命令進行擷取至100:

jedisCluster.zremrangeByRank(key, 0, jedisCluster.zcard(key)-100)
1

併發安全

上面的策略存在直播間原始碼併發安全問題,它包含兩步:
1. 插入資料到set中。
2. 查詢sortedSet大小,判斷是否大於120
3. 如果大於120,則進行zremrangeByRank操作。

如果在直播間原始碼高併發的環境中很容易多次執行zremrangeByRank。

解決辦法:
使用lua指令碼,將上面操作寫到lua指令碼中。在lua指令碼中執行的操作是原子性的,是執行緒安全的。不過要注意redis在執行lua指令碼時是不可以處理其他請求的

翻頁超過了快取大小

這種情況的話就可以考慮到直播間原始碼資料庫中查詢,或者走搜尋引擎,畢竟使用者看的最多的還是前幾頁的資料。具體要快取多少資料要根據實際業務進行計算.
————————————————
宣告:本文由雲豹科技轉發自 快樂崇拜234部落格,如有侵權請聯絡作者刪除


來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/70002045/viewspace-2783879/,如需轉載,請註明出處,否則將追究法律責任。

相關文章