Redis實現用戶瀏覽商品的歷史記錄
思路: 用戶每次瀏覽商品時, 向後臺發送請求, 攜帶商品ID, 然後在 Redis中存儲: 用戶ID和瀏覽的商品ID,以時間排序. 來實現存儲用戶瀏覽歷史記錄.
其比較複雜的是redis選用數據結構(有序Set)
// redis存用戶瀏覽記錄,根據瀏覽時間, 只存8條
// redis key上線 2.5億
// key: userId value: skuId
public void addRecentHistory(Long userId, Long skuId) {
ZSetOperations<String, String> zSetOperations = this.redisTemplate.opsForZSet();
// //zset內部是按分數來排序的,這裏用當前時間做分數
zSetOperations.add(KEY_HISTORY + userId, skuId.toString(), System.currentTimeMillis());
// 例子: 只保留5個元素
// //環形結構 -6, -5, -4, -3, -2, -1 (負數索引)
// 0 , 1 , 2 , 3 , 4, 5 (正數索引)
// 只要5個元素, 移除0 ~ -6之間的元素,只保留-1~ -5元素
zSetOperations.removeRange(KEY_HISTORY + userId, 0, -9); // 保留8個skuId
}
// 從redis中拿到對應用戶的SkuId
public List<Long> getRecentHistorySkuId(long userId) {
if (userId <= 0) {
return Collections.emptyList();
}
// 獲取用戶最近瀏覽的SkuId
Set<String> skuIds = this.redisTemplate.opsForZSet().reverseRange(KEY_HISTORY + userId, 0, 7);
List<Long> skuId = new ArrayList<>();
skuIds.forEach(item -> {
skuId.add(Long.valueOf(item));
});
return skuId;
}
這裏有一個removeRange函數, 其目的是爲了保證redis中只存儲8個元素.
如下圖:
右側位redis中索引( 正數索引從0開始表示第一個元素, 負數索引從-1開始表示最後一個元素 ), 因此removeRange(KEY_HISTORY + userId, 0, -6); 這個函數的目的是移除索引0 ~ -6之間的元素, 也就是把value爲1000 這個元素移除掉了.