caffeine 一级缓存

caffeine 比较redis 优势

Redis 这种 NoSql 作为缓存组件,它能够很好的作为分布式缓存组件提供多个服务间的缓存,但是 Redis 这种还是需要网络开销,增加时耗。本地缓存是直接从本地内存中读取,没有网络开销,例如秒杀系统或者数据量小的缓存等,比远程缓存更合适.

Caffeine 是基于 JAVA 8 的高性能缓存库。并且在 spring5 (springboot 2.x) 后,spring 官方放弃了 Guava,而使用了性能更优秀的 Caffeine 作为默认缓存组件。

springboot 使用caffeine作为一级缓存,redis作为 二级缓存,流程图
示例
java 复制代码
		<!-- 一级缓存,效率:caffeine > guava > redis -->
        <dependency>
            <groupId>com.github.ben-manes.caffeine</groupId>
            <artifactId>caffeine</artifactId>
            <version>2.8.0</version>
        </dependency>
java 复制代码
配置类
import com.github.benmanes.caffeine.cache.Cache;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import java.util.concurrent.TimeUnit;

@Configuration
public class Caffeine {
    @Bean
    public Cache<String, Object> caffeineCache() {
        return com.github.benmanes.caffeine.cache.Caffeine.newBuilder()
                // 设置每个key的过期时间
                .expireAfterWrite(60, TimeUnit.SECONDS)
                // 初始的缓存空间大小(键值对的数量,而不是内存大小)
                .initialCapacity(100)
                // 缓存的最大条数
                .maximumSize(1000)
                .build();
    }
}
java 复制代码
工具类
import com.github.benmanes.caffeine.cache.Cache;
import jakarta.annotation.Resource;
import org.springframework.stereotype.Component;
import org.springframework.util.ObjectUtils;

@Component
public class CaffeineUtils<T> {

    @Resource
    Cache<String, Object> caffeineCache;


    // 添加缓存
    public void put(String key, Object value){
        // 添加一级缓存
        caffeineCache.put(key,value);

    }
    // 获取数据
    public T get(String key){
        T info = (T) caffeineCache.asMap().get(key);
        return info;
    }


    // 判断缓存是否存在
    public boolean exist(String key){
        Object ifPresent = caffeineCache.getIfPresent(key);
        // 非空 true
        return !ObjectUtils.isEmpty(ifPresent);
    }

    // 移除数据
    public void remove(String key){
        caffeineCache.asMap().remove(key);
    }
}
java 复制代码
使用

import jakarta.annotation.Resource;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import java.util.HashMap;
import java.util.Map;

@RestController
public class FirstCacheController {
    @Resource
    CaffeineUtils firstAndSecondCache;
    @Resource
    private RedisTemplate<String, Object> redisTemplate;

    // 添加缓存
    @RequestMapping("addCache")
    public void addFirstCache(String key){
        Map<String,Object> map = new HashMap<>();
        map.put("a","1");
        // 一级缓存
        firstAndSecondCache.put(key,map);
        // 二级缓存
        redisTemplate.opsForHash().putAll(key, map);
    }

    // 缓存是否存在
    @RequestMapping("existFirstCache")
    public void existFirstCache(String key){
        System.out.println(firstAndSecondCache.exist(key));
    }

    // 获取缓存数据
    @RequestMapping("getFirstCache")
    public Object getFirstCache(String key){
        Object o;
        //1. 一级缓存存在,返回数据
        if(firstAndSecondCache.exist(key)){
             o = firstAndSecondCache.get(key);
             return o;
        }
        //2. 一级缓存不存在,判断二级缓存是否存在
        if(redisTemplate.hasKey(key)){
            // 二级缓存数据存在
            o = redisTemplate.opsForHash().entries(key);
            // 将二级缓存数据同步给一级缓存
            firstAndSecondCache.put(key,o);
            return o;
        }
        //3. 一级缓存不存在,二级缓存也不存在
        //3.1 数据源 Mysql 中取数据 ,此处模拟。
        if(true){
            Map<String,Object> map = new HashMap<>();
            map.put("a",2);
            o = map;
            //3.2 将数据缓到 二级缓存 AND 一级缓存
            redisTemplate.opsForHash().putAll(key, map);
            firstAndSecondCache.put(key,map);

        }
        return o;
    }
    
    //移除缓存
    @RequestMapping("deleteFirstCache")
    public void deleteFirstCache(String key){
        firstAndSecondCache.remove(key);
        redisTemplate.delete(key);
    }
}
相关推荐
Zfox_5 小时前
Redis:Hash数据类型
服务器·数据库·redis·缓存·微服务·哈希算法
呼拉拉呼拉5 小时前
Redis内存淘汰策略
redis·缓存
咖啡啡不加糖9 小时前
Redis大key产生、排查与优化实践
java·数据库·redis·后端·缓存
肥仔哥哥193010 小时前
springCloud2025+springBoot3.5.0+Nacos集成redis从nacos拉配置起服务
redis·缓存·最新boot3集成
呼拉拉呼拉12 小时前
Redis故障转移
数据库·redis·缓存·高可用架构
篱笆院的狗16 小时前
如何使用 Redis 快速实现布隆过滤器?
数据库·redis·缓存
Alla T17 小时前
【前端】缓存相关
前端·缓存
chen.@-@21 小时前
后端下载限速(redis记录实时并发,bucket4j动态限速)
数据库·redis·缓存
吾日三省吾码1 天前
Spring 团队详解:AOT 缓存实践、JSpecify 空指针安全与支持策略升级
java·spring·缓存
不凡的凡1 天前
鸿蒙图片缓存(一)
缓存