场景

ruoyi-vue前后端分离项目使用的是redis缓存,现在要把redis缓存,改为本地缓存,即内存中存储,不使用redis了。

思路

开发一个本地缓存的工具类来替代 RedisCache类,然后把涉及的地方改一下即可

开始改造

由于ruoyi中使用redis的地方较多,所以需要仔细改造

1、首先去掉redis的maven依赖

注意:是去掉,不是加上

 <!-- redis 缓存操作 -->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-data-redis</artifactId>
        </dependency>

2、开发一个本地缓存工具类,类似于redis

开发本地缓存类Localcache.java,放在ruoyi-common工程中

package com.ruoyi.common.core.cache;

import java.util.ArrayList;
import java.util.Collection;
import java.util.List;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.TimeUnit;

import javax.annotation.PostConstruct;

import org.springframework.stereotype.Component;

import com.github.benmanes.caffeine.cache.Cache;
import com.github.benmanes.caffeine.cache.Caffeine;




/**
 * 本地缓存方式
 *
 */
@SuppressWarnings(value = { "unchecked" })
@Component
public class Localcache {

	private Map<String,Object> persistentCache;
	
	/**
	 * token认证cache - 会自动过期的map
	 */
	private Cache<String, Object> tokenCache;
	
	/**
	 * 防止重复提交
	 */
	private Cache<String, Object> repeatSubmitCache;
	
	/**
	 * 验证码服务
	 */
	private Cache<String, Object> captchaCache;
	
	@PostConstruct
	public void init() {
		
		persistentCache = new ConcurrentHashMap<String, Object>(1024);
		
		tokenCache = Caffeine.newBuilder()
        .expireAfterWrite(30, TimeUnit.MINUTES)		//30分钟
        .initialCapacity(100)
        .maximumSize(10000)
        .build();
		
		
		repeatSubmitCache = Caffeine.newBuilder()
		        .expireAfterWrite(10, TimeUnit.SECONDS)		//10秒
		        .initialCapacity(100)
		        .maximumSize(10000)
		        .build();
		
		captchaCache = Caffeine.newBuilder()
		        .expireAfterWrite(2, TimeUnit.MINUTES)		//2分钟
		        .initialCapacity(100)
		        .maximumSize(10000)
		        .build();
	}
	
	/**
	 * Get方法, 转换结果类型并屏蔽异常, 仅返回Null.
	 */
	public <T> T get(String key) {
		try {
			Object obj = persistentCache.get(key);
			
			if( null == obj ) {
				obj = tokenCache.getIfPresent(key);
			}
			
			if( null == obj ) {
				obj = captchaCache.getIfPresent(key);
			}
			
			if( null == obj ) {
				obj = repeatSubmitCache.getIfPresent(key);
			}
			
			return (T) obj;
		} catch (RuntimeException e) {
			
			return (T)null;
		}
	}
	
	public List<String> keys(String key){
		List<String> keyList = new ArrayList<String>();
		List<String> keys = new ArrayList<String>(persistentCache.keySet());
		for(int i=0;i<keys.size();i++){
			if(keys.get(i).startsWith(key)){
				keyList.add(keys.get(i));
			}
		}
		return keyList;
	}

	/**
	 * 异步Set方法, 不考虑执行结果.
	 * @param key
	 * @param value
	 * @param expiredTime	单位:秒
	 */
	public void set(String key, Object value, int expiredTime ) {
		if( 0 == expiredTime ) {
			persistentCache.put(key,value);
		}else if( expiredTime <= 60 ) {		//TTL少于1分钟
			repeatSubmitCache.put(key, value);
		}else if( expiredTime <= 300 ) {	//TTL少于5分钟
			captchaCache.put(key, value);
		}else {
			tokenCache.put(key, value);
		}
	}
	
	
	/**
	 * 持久化保存
	 * @param key
	 * @param value
	 */
	public void set(String key, Object value) {
		try {
			this.set(key, value, 0 );
		} catch (Exception e) {
			
		}
	}

	/**
	 * 异步 Delete方法, 不考虑执行结果.
	 */
	public void delete(final String key) {
		persistentCache.remove(key);
		captchaCache.invalidate(key);
		tokenCache.invalidate(key);
		//防止重复提交和token过期,不存在删除的方法
	}
	
	public void delete(final Collection<String> keys) {
		for( String key : keys ) {
			delete(key);
		}
	}
	
}

3、接下来就把所有使用到RedisCache的地方,改成Localcache 就可以了,由于代码篇幅较长,在此,就不演示了,

Logo

快速构建 Web 应用程序

更多推荐