談談系統中的緩存預熱-@PostConstruct

說起緩存,相信大家都不陌生,下面我們先看這張圖
在這裏插入圖片描述
上圖是一個最簡單的應用系統業務流轉模型,當一個客戶端連接到server時,需要做數據訪問,在server中會判斷是否已經在緩存中,如果在則直接在緩存中拿出數據返回,由於緩存是在內存中的(比如redis,mongo,sping-cache等),不用大批量的跟數據庫進行交互,避免了大量io操作,大大提高效率。

下面,我們來考慮一個問題,可以設想下如下場景:
當應用啓動起來的瞬間,n(非常大)個用戶訪問儘量,都訪問同一波熱點數據,這種情況很可能導致,數據庫承受不了大量io導致數據庫瞬間癱瘓。

爲了避免這個情況,出現了緩存預熱這個解決方案,當然實現方式有很多中,核心思想都是在應用啓動的過程中將數據寫進緩存系統中,從而使使用過程中可以直接提高系統的緩存命中率(當然不可能將所有的數據全部寫進緩存中),減少數據庫jdbc操作。

下面主要來說說使用@PostConstruct來實現我們的緩存預熱。
從Java EE5規範開始,Servlet中增加了兩個影響Servlet生命週期的註解,@PostConstruct和@PreDestroy,這兩個註解被用來修飾一個非靜態的void()方法。

在spring的bean生命週期中,被@PostConstruct的方法會在實例初始化完成後執行,做一個生命週期的回掉。

redis連接篇:https://blog.csdn.net/baomw/article/details/89186501

我們先假設,數據庫中某張表的前4000個使熱點數據,然後我們在容器啓動的時候將這4000條數據緩存到redis中去。
dao類代碼如下:

   @Select("select id,tel from tel order by id asc limit 4000")
    public List<HashMap> getList();

service類測試代碼如下:

 @Autowired
    private TelDao telDao;

    @Autowired
    private StringRedisTemplate redisTemplate;

    @PostConstruct
    public void init(){
        List<HashMap> list = telDao.getList();

        for (HashMap map:list){
            //操作string
            redisTemplate.opsForValue().set(map.get("id").toString(),map.get("tel").toString());
            System.out.println(map.get("id").toString()+"----"+redisTemplate.opsForValue().get(map.get("id").toString()));
        }

    }

在spring容器啓動的時候初始化redis緩存,如下圖可以看到緩存數據都被加載到redis中去了。
在這裏插入圖片描述
在這裏插入圖片描述
我們連接redis-cli,keys *發現數據確實都被緩存到redis中去了。

如此一個簡單的緩存預熱已經完成了。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章