Spring 配置Redies缓存@Cacheable注解与 @CacheEvict注解
1.properties文件指定Redis连接IP与密码
# Redis IP
redis.host=127.0.0.1
redis.port=6379
#Redis PassWord
redis.password=123
redis.timeOut=10000
# \u5BC6\u7801\u7559\u7A7A\u5F88\u6709\u5FC5\u8981(\u8FD9\u4E2A\u8BBE\u7F6E\u4E0D\u7528\u4F7F\u7528\uFF09
redis.pass=
redis.maxTotal=200
redis.maxIdle=50
redis.minIdle=8
redis.maxWaitMillis=10000
redis.testOnBorrow=true
redis.testOnReturn=true
redis.testWhileIdle=true
redis.timeBetweenEvictionRunsMillis=30000
redis.numTestsPerEvictionRun=10
redis.minEvictableIdleTimeMillis=60000
# Redis DB(0-15)
redis.database=14
2.在applicationContext.xml文件添加节点:
<import resource="spring-redis.xml"/> <!-- 启动缓存 --> <cache:annotation-driven />
3.新建spring-redis.xml 文件
<?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:context="http://www.springframework.org/schema/context" xmlns:mvc="http://www.springframework.org/schema/mvc" xmlns:aop="http://www.springframework.org/schema/aop" xmlns:tx="http://www.springframework.org/schema/tx" xmlns:p="http://www.springframework.org/schema/p" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.3.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.3.xsd http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc-4.3.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-4.3.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-4.3.xsd" default-lazy-init="true" > <!--redis配置 --> <bean name="jedisPoolConfig" class="redis.clients.jedis.JedisPoolConfig" lazy-init="true"> <property name="maxTotal" value="${redis.maxTotal}"/> <property name="maxIdle" value="${redis.maxIdle}"/> <property name="minIdle" value="${redis.minIdle}"/> <property name="maxWaitMillis" value="${redis.maxWaitMillis}"/> <property name="testOnBorrow" value="${redis.testOnBorrow}"/> <property name="testOnReturn" value="${redis.testOnReturn}"/> <property name="testWhileIdle" value="${redis.testWhileIdle}"/> <property name="timeBetweenEvictionRunsMillis" value="${redis.timeBetweenEvictionRunsMillis}"/> <property name="numTestsPerEvictionRun" value="${redis.numTestsPerEvictionRun}"/> <property name="minEvictableIdleTimeMillis" value="${redis.minEvictableIdleTimeMillis}"/> </bean> <!-- Jedis ConnectionFactory 数据库连接配置--> <bean id="jedisConnectionFactory" class="org.springframework.data.redis.connection.jedis.JedisConnectionFactory"> <property name="hostName" value="${redis.host}" /> <property name="port" value="${redis.port}" /> <property name="password" value="${redis.password}" /> <property name="database" value="${redis.database}" /> <property name="poolConfig" ref="jedisPoolConfig" /> </bean> <!-- StringRedisTemplate 序列化方式 --> <bean id="redisTemplate" class="org.springframework.data.redis.core.StringRedisTemplate" p:connection-factory-ref="jedisConnectionFactory" > <!--以String类型的方式 序列化 时间:2020年2月13日17:29:41 作者:陈翔宇 start --> <property name="keySerializer"> <bean class="org.springframework.data.redis.serializer.StringRedisSerializer" /> </property> <property name="valueSerializer"> <bean class="org.springframework.data.redis.serializer.JdkSerializationRedisSerializer" /> </property> <property name="hashKeySerializer"> <bean class="org.springframework.data.redis.serializer.StringRedisSerializer" /> </property> <property name="hashValueSerializer"> <bean class="org.springframework.data.redis.serializer.JdkSerializationRedisSerializer" /> </property> <!--以String类型的方式 序列化 时间:2020年2月13日17:29:41 作者:陈翔宇 end --> </bean> <!-- 设置Cookie domain 和 名称 --> <bean id="defaultCookieSerializer" class="com.kintech.web.CookieSerializer"> <property name="domainName" value="${sysHost}"/> <property name="cookieName" value="MYJSESSIONID"/> <!--<property name="domainNamePattern" value="^.+?\\.(\\w+\\.[a-z]+)$"/>--> </bean> <!-- 将session放入redis --> <bean id="redisHttpSessionConfiguration" class="org.springframework.session.data.redis.config.annotation.web.http.RedisHttpSessionConfiguration"> <!--session 自动超时时间--> <property name="maxInactiveIntervalInSeconds" value="7200" /> <property name="cookieSerializer" ref="defaultCookieSerializer"/> <!-- session 创建/失效监听器 start --> <property name="httpSessionListeners"> <list> <bean class="com.kintech.webSYS.listener.RedisSessionListener" /> </list> </property> <!-- session 创建/失效监听器 --> </bean> <!--@Cacheable使用Redis缓存 : spring自己的缓存管理器,这里定义了缓存位置名称 ,即注解中的value --> <bean id="cacheManager" class="org.springframework.cache.support.SimpleCacheManager"> <property name="caches"> <set> <bean class="org.springframework.data.redis.cache.RedisCache"> <constructor-arg name="redisOperations" ref="redisTemplate"></constructor-arg> <constructor-arg name="name" value="menuAllList"></constructor-arg> <constructor-arg name="prefix" value="dbSYS:"></constructor-arg> <constructor-arg name="expiration" value="7200"></constructor-arg> </bean> <!-- 如果有多个缓存在这里添加多个bean menuAllList为缓存变量名称--> </set> </property> </bean> </beans>
4.@Cacheable注解时会报错说没有key报错java.lang.ClassCastException: org.springframework.cache.interceptor.SimpleKey cannot be cast to java.lang.String,解决办法:新建文件RedisConfig.java 文件,内容如下:
@Configuration @EnableCaching public class RedisConfig extends CachingConfigurerSupport { @Override @Bean public KeyGenerator keyGenerator() { return (target, method, params) -> { StringBuilder sb = new StringBuilder(); sb.append(target.getClass().getName()); sb.append(method.getName()); for (Object obj : params) { sb.append(obj.toString()); } return sb.toString(); }; } }
5.新建一个interface CacheService.java
public interface CacheService { List<SysMenu> findMenuAllList();//获取并缓存 menuAllList void clearMenuAllList();//清除menuAllList }
6.新建class CacheServiceImpl.java
/** * 缓存类 * 该类针对一个数据表缓存只有二个方法,即一个获取缓存,一个清空缓存, * 获取所有缓存方法名规则 findXXXAllList() * 一个清空缓存方法名规则 clearXXXAllList() ,请在修改或新增该缓存表的Controller里调用一下该方法 * 如有其他需要用的缓存的逻辑请放到该表的ServiceImple里面实现,方法名规则:findXXXFromCache() */ @Service("cacheService") public class CacheServiceImpl implements CacheService { @Autowired SysMenuService sysMenuService; /** * 获取所有数据并存入缓存中 * @return */ @Override @Cacheable(value="menuAllList") public List<SysMenu> findMenuAllList() { return sysMenuService.findAllList(); } /** * 清空缓存数据 (在修改或新增该表的数据时(如Controller里调用一下该方法)) * @return */ @Override @CacheEvict(value="menuAllList",allEntries=true) public void clearMenuAllList(){} }
7.在Service使用缓存
@Autowired
CacheService cacheService;
/** * 从缓存中根据Url 查数据 * @param MenuUrl * @return */ @Override public SysMenu findByMenuUrlFromCache(String MenuUrl) { List<SysMenu> listAll=cacheService.findMenuAllList(); List<SysMenu> filterList = listAll.stream().filter(item -> item.getMenuUrl().equals(MenuUrl)).collect(Collectors.toList()); if(filterList!=null && filterList.size()>0){ return filterList.get(0); }else{ return null; } }
调用以后用Redis Desktop Manager查看数据已缓存起来
也可以直接在别的地方用缓存
@Autowired
CacheService cacheService;
List<SysMenu> listAll=cacheService.findMenuAllList();
欢迎加入JAVA技术交流QQ群:179945282
欢迎加入ASP.NET(C#)交流QQ群:17534377