SpringBoot自定义缓存

Posted 帅东

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了SpringBoot自定义缓存相关的知识,希望对你有一定的参考价值。

上一篇文章说了默认的缓存实际上是:ConcurrentMap,有很多功能都没有,比如:定期删除、容量上线、容量不够的策略(LRU、LFU)等等。

自定义缓存步骤

1. 定义一个属于自己的Cache,需要实现org.springframework.cache.Cache

public class MyCache implements Cache 
    private MyLinkedHashMap<String> myMap = new MyLinkedHashMap<>(2, 1, true);
    private String name;

    @Override
    public String getName() 
        return name;
    

    public void setName(String name) 
        this.name = name;
    

    @Override
    public Object getNativeCache() 
        return myMap;
    

    @Override
    public ValueWrapper get(Object key) 
        String value = myMap.get(key);
        return value == null ? null : () -> value;
    

    @Override
    public <T> T get(Object key, Class<T> type) 
        Object value = myMap.get(key);
        if (value != null && type != null && !type.isInstance(value)) 
            throw new IllegalStateException(
                    "Cached value is not of required type [" + type.getName() + "]: " + value);
        
        return (T) value;
    

    @Override
    public <T> T get(Object key, Callable<T> valueLoader) 
        return Optional.ofNullable((T) myMap.get(key)).orElseGet(() -> 
            try 
                return valueLoader.call();
             catch (Exception e) 
                throw new RuntimeException(e);
            
        );
    

    @Override
    public void put(Object key, Object value) 
        myMap.put((String) key, (String) value);
    

    @Override
    public ValueWrapper putIfAbsent(Object key, Object value) 
        return () -> Optional.ofNullable((Object) myMap.get(key)).orElse(value);
    

    @Override
    public void evict(Object key) 
    

    @Override
    public boolean evictIfPresent(Object key) 
        return false;
    

    @Override
    public void clear() 
        myMap.clear();
    

    @Override
    public boolean invalidate() 
        return false;
    


2. 重写缓存底层数据结构(当然也可以用Java自带的数据结构,比如:HashMap、LinkedHashMap、ConcurrentMap等)

public class MyLinkedHashMap<T> extends LinkedHashMap<String, T> 
    private int capacity;

    @Override
    protected boolean removeEldestEntry(Map.Entry eldest) 
        return size() > capacity;
    

    public MyLinkedHashMap(int initialCapacity, float loadFactor, boolean accessOrder) 
        //可选参数accessOrder 设置为true 即可实现LRU逻辑
        super(initialCapacity, loadFactor, accessOrder);
        this.capacity = initialCapacity;
    

3. 注入到SimpleCacheManager

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:cache="http://www.springframework.org/schema/cache"
       xsi:schemaLocation="http://www.springframework.org/schema/beans
           http://www.springframework.org/schema/beans/spring-beans.xsd
           http://www.springframework.org/schema/cache
           http://www.springframework.org/schema/cache/spring-cache.xsd">

    <cache:annotation-driven/>

    <bean id="cacheManager" class="org.springframework.cache.support.SimpleCacheManager">
        <property name="caches">
            <set>
                <!-- 自定义cache -->
                <bean class="com.dong.springuseehcacheredis.cache.MyCache">
                    <property name="name" value="帅东自定义cache"/>
                </bean>
            </set>
        </property>
    </bean>
</beans>

GitHub代码

https://github.com/shuaidongshuai/spring-use-ehcache-redis

以上是关于SpringBoot自定义缓存的主要内容,如果未能解决你的问题,请参考以下文章

SpringBoot自定义缓存

SpringBoot自定义缓存

SpringBoot自定义缓存

SpringBoot2.x整合Redis缓存自定义序列化

VSCode自定义代码片段——CSS选择器

SpringBoot2.3.0自定义RedisCacheManager并对缓存Jackson序列化