再没有引入其他缓存组件的情况下,SpringBoot默认加载SimpleCacheConfiguration进行自动配置
- SimpleCacheConfiguration源码,主要就是注册一个ConcruentMap缓存管理器组件
- 看ConcurrentMapCacheManager源码
该缓存管理器就是通过ConcurrentMap管理缓存,key存储缓存名,value对应一个缓存对象
新建一个缓存则必须经过这个方法,createConcurrentMapCache,源码如下,可以看出为我们创建的缓存组件是ConcurrentMapCache形式 - 继续追溯ConcurrentMapCache源码
ConcurrentMapCache定义了一个全局常量ConcurrentMap,存储我们需要缓存的东西
key值由我们自定义(或者生成器生成),value值就是具体方法的返回值(需要缓存的对象信息)
然后就像常规的Map操作,里面定义了get,put等方法
- 默认情况下,若不指定key值(或者不指定KeyGenerator),默认使用SimpleKeyGenerator生成key
看这两段源码,就可以知道,SimpleKeyGenerator生成key的规则
- 方法没有参数,返回一个空的SimpleKey,还是来到第二张图的方法中(只不过是空数组)
- 方法一个参数,返回该参数
- 方法多个参数,一个长度大于1的数组,经过处理然后生成一个Hashcode(自我理解)
-
上面基本就是SpringBoot原生缓存,SimpleCacheConfiguration的工作原理
-
常用注解
- 注解@Cacheable
@Cacheable 在方法执行之前,判断缓存中是否有值,有则不执行方法了 通过 key=“” 指定存储缓存的时候的key值 通过 keyGenerator=“” 指定存储缓存的时候的key的生成策略(两者选一)
- 注解@CachePut
@CachePut 方法先执行,再将方法的返回结果放到缓存中(方法没出异常) 通过 key=“” 指定存储缓存的时候的key值 通过 keyGenerator=“” 指定存储缓存的时候的key的生成策略(两者选一)
- 注解@CacheEvict
@CacheEvict 默认在方法执行之后(方法没出异常),清除指定缓存(根据key匹配) 通过 key=“” 指定存储缓存的时候的key值 通过 keyGenerator=“” 指定存储缓存的时候的key的生成策略(两者选一) 通过 allEntries=true清除所有缓存(匹配所有的key) 通过 beforeInvocation=true可以指定在方法之前执行清除缓存
还有一些其他属性,像condition指定条件等
示例代码/** * 根据id获取employee * @Cacheable 在方法执行之前判断,缓存中是否有值,有则不执行方法了 */ @Cacheable(value = HELLO_SERVICES) public Employee getEmp(Integer empId) { getLog().error("查询来了。。"); Example example = new Example(Employee.class); example.createCriteria().andEqualTo(Employee.EMPLOYEE_ID, empId); List<Employee> employees = helloMapper.selectByExample(example); if (CollectionUtils.isEmpty(employees)) { return null; } else { return employees.get(0); } } /** * 更新employee * @CachePut 方法先执行,再将方法的返回结果放到缓存中(方法没出异常) key:#employee.employeeId 取参数对象属性值 */ @CachePut(value = HELLO_SERVICES, key = "#employee.employeeId") public Employee update(Employee employee) { getLog().error("更新来了。。"); helloMapper.updateByPrimaryKeySelective(employee); return employee; } /** * 模拟删除,清空所有缓存 * @CacheEvict 默认在方法执行之后(方法没出异常),清除指定缓存 * @param id * @return Integer */ @CacheEvict(value = HELLO_SERVICES, key = "#id") public Integer delete(Integer id) { getLog().error("删除来了。。"); return id; }
over,五月再见,时间过得真快!!!