张家港网站定制,wordpress 顶部美化,企业宣传视频模板素材,免费网页空间代码加入redis缓存 1. 缓存菜品1.1 问题说明1.2 实现思路1.3 代码开发1.4 功能测试 2. 缓存套餐2.1 Spring Cache2.1.1 介绍2.1.2 常用注解2.1.3 入门案例 2.2 具体实现思路2.3 代码开发 1. 缓存菜品
1.1 问题说明
用户端小程序展示的菜品数据都是通过查询数据库获得#xff0c;… 加入redis缓存 1. 缓存菜品1.1 问题说明1.2 实现思路1.3 代码开发1.4 功能测试 2. 缓存套餐2.1 Spring Cache2.1.1 介绍2.1.2 常用注解2.1.3 入门案例 2.2 具体实现思路2.3 代码开发 1. 缓存菜品
1.1 问题说明
用户端小程序展示的菜品数据都是通过查询数据库获得如果用户端访问量比较大数据库访问压力随之增大。 结果系统响应慢、用户体验差
1.2 实现思路
通过Redis来缓存菜品数据减少数据库查询操作。 缓存逻辑分析
每个分类下的菜品保存一份缓存数据数据库中菜品数据有变更时清理缓存数据
1.3 代码开发
修改用户端接口 DishController 的 list 方法加入缓存处理逻辑 Autowiredprivate RedisTemplate redisTemplate;/*** 根据分类id查询菜品** param categoryId* return*/GetMapping(/list)ApiOperation(根据分类id查询菜品)public ResultListDishVO list(Long categoryId) {//构造redis中的key规则dish_分类idString key dish_ categoryId;//查询redis中是否存在菜品数据ListDishVO list (ListDishVO) redisTemplate.opsForValue().get(key);if(list ! null list.size() 0){//如果存在直接返回无须查询数据库return Result.success(list);}Dish dish new Dish();dish.setCategoryId(categoryId);dish.setStatus(StatusConstant.ENABLE);//查询起售中的菜品//如果不存在查询数据库将查询到的数据放入redis中list dishService.listWithFlavor(dish);redisTemplate.opsForValue().set(key, list);return Result.success(list);}为了保证数据库和Redis中的数据保持一致修改管理端接口 DishController 的相关方法加入清理缓存逻辑。
需要改造的方法
新增菜品修改菜品批量删除菜品起售、停售菜品
抽取清理缓存的方法
在管理端DishController中添加 Autowiredprivate RedisTemplate redisTemplate;/*** 清理缓存数据* param pattern*/private void cleanCache(String pattern){Set keys redisTemplate.keys(pattern);redisTemplate.delete(keys);}调用清理缓存的方法保证数据一致性
1). 新增菜品优化 /*** 新增菜品** param dishDTO* return*/PostMappingApiOperation(新增菜品)public Result save(RequestBody DishDTO dishDTO) {log.info(新增菜品{}, dishDTO);dishService.saveWithFlavor(dishDTO);//清理缓存数据String key dish_ dishDTO.getCategoryId();cleanCache(key);return Result.success();}2). 菜品批量删除优化 /*** 菜品批量删除** param ids* return*/DeleteMappingApiOperation(菜品批量删除)public Result delete(RequestParam ListLong ids) {log.info(菜品批量删除{}, ids);dishService.deleteBatch(ids);//将所有的菜品缓存数据清理掉所有以dish_开头的keycleanCache(dish_*);return Result.success();}3). 修改菜品优化 /*** 修改菜品** param dishDTO* return*/PutMappingApiOperation(修改菜品)public Result update(RequestBody DishDTO dishDTO) {log.info(修改菜品{}, dishDTO);dishService.updateWithFlavor(dishDTO);//将所有的菜品缓存数据清理掉所有以dish_开头的keycleanCache(dish_*);return Result.success();}4). 菜品起售停售优化 /*** 菜品起售停售** param status* param id* return*/PostMapping(/status/{status})ApiOperation(菜品起售停售)public ResultString startOrStop(PathVariable Integer status, Long id) {dishService.startOrStop(status, id);//将所有的菜品缓存数据清理掉所有以dish_开头的keycleanCache(dish_*);return Result.success();}1.4 功能测试
1). 加入缓存
当第一次查询某个分类的菜品时会从数据为中进行查询同时将查询的结果存储到Redis中在后绪的访问若查询相同分类的菜品时直接从Redis缓存中查询不再查询数据库。 查看控制台sql有查询语句说明是从数据库中进行查询查看Redis中的缓存数据说明缓存成功再次访问控制台没有sql说明是从缓存中查询。
2). 修改操作
当在后台修改菜品数据时为了保证Redis缓存中的数据和数据库中的数据时刻保持一致当修改后需要清空对应的缓存数据。用户再次访问时还是先从数据库中查询同时再把查询的结果存储到Redis中这样就能保证缓存和数据库的数据保持一致。
**进入后台**修改任意一个菜品当前分类的菜品数据已在Redis中缓存。修改完成后查看Redis中的缓存数据发现没有说明修改时已清空缓存。用户再次访问同一个菜品分类时需要先查询数据库再把结果同步到Redis中保证了两者数据一致性。
2. 缓存套餐
2.1 Spring Cache
2.1.1 介绍
Spring Cache 是一个框架实现了基于注解的缓存功能只需要简单地加一个注解就能实现缓存功能。
Spring Cache 提供了一层抽象底层可以切换不同的缓存实现例如
EHCacheCaffeineRedis(常用)
起步依赖
dependencygroupIdorg.springframework.boot/groupIdartifactIdspring-boot-starter-cache/artifactId version2.7.3/version
/dependency2.1.2 常用注解
在SpringCache中提供了很多缓存操作的注解常见的是以下的几个
注解说明EnableCaching开启缓存注解功能通常加在启动类上Cacheable在方法执行前先查询缓存中是否有数据如果有数据则直接返回缓存数据如果没有缓存数据调用方法并将方法返回值放到缓存中CachePut将方法的返回值放到缓存中CacheEvict将一条或多条数据从缓存中删除
在spring boot项目中使用缓存技术只需在项目中导入相关缓存技术的依赖包并在启动类上使用EnableCaching开启缓存支持即可。
例如使用Redis作为缓存技术只需要导入Spring data Redis的maven坐标即可。
2.1.3 入门案例
引导类上加EnableCaching:
Slf4j
SpringBootApplication
EnableCaching//开启缓存注解功能
public class CacheDemoApplication {public static void main(String[] args) {SpringApplication.run(CacheDemoApplication.class,args);log.info(项目启动成功...);}
}2). CachePut注解
CachePut 说明
作用: 将方法返回值放入缓存
value: 缓存的名称, 每个缓存名称下面可以有很多key
key: 缓存的key ---------- 支持Spring的表达式语言SPEL语法
在save方法上加注解CachePut
当前UserController的save方法是用来保存用户信息的我们希望在该用户信息保存到数据库的同时也往缓存中缓存一份数据我们可以在save方法上加上注解 CachePut用法如下 /*** CachePut将方法返回值放入缓存* value缓存的名称每个缓存名称下面可以有多个key* key缓存的key*/PostMappingCachePut(value userCache, key #user.id)//key的生成userCache::1public User save(RequestBody User user){userMapper.insert(user);return user;}说明key的写法如下
#user.id : #user指的是方法形参的名称, id指的是user的id属性 , 也就是使用user的id属性作为key ;
#result.id : #result代表方法返回值该表达式 代表以返回对象的id属性作为key
#p0.id#p0指的是方法中的第一个参数id指的是第一个参数的id属性,也就是使用第一个参数的id属性作为key ;
#a0.id#a0指的是方法中的第一个参数id指的是第一个参数的id属性,也就是使用第一个参数的id属性作为key ;
#root.args[0].id:#root.args[0]指的是方法中的第一个参数id指的是第一个参数的id属性,也就是使用第一个参数的id属性作为key ;
3). Cacheable注解
Cacheable 说明:
作用: 在方法执行前spring先查看缓存中是否有数据如果有数据则直接返回缓存数据若没有数据调用方法并将方法返回值放到缓存中
value: 缓存的名称每个缓存名称下面可以有多个key
key: 缓存的key ---------- 支持Spring的表达式语言SPEL语法
在getById上加注解Cacheable /*** Cacheable在方法执行前spring先查看缓存中是否有数据如果有数据则直接返回缓存数据若没有数据 *调用方法并将方法返回值放到缓存中* value缓存的名称每个缓存名称下面可以有多个key* key缓存的key*/GetMappingCacheable(cacheNames userCache,key#id)public User getById(Long id){User user userMapper.getById(id);return user;}4). CacheEvict注解
CacheEvict 说明
作用: 清理指定缓存
value: 缓存的名称每个缓存名称下面可以有多个key
key: 缓存的key ---------- 支持Spring的表达式语言SPEL语法
在 delete 方法上加注解CacheEvict DeleteMappingCacheEvict(cacheNames userCache,key #id)//删除某个key对应的缓存数据public void deleteById(Long id){userMapper.deleteById(id);}DeleteMapping(/delAll)CacheEvict(cacheNames userCache,allEntries true)//删除userCache下所有的缓存数据public void deleteAll(){userMapper.deleteAll();}2.2 具体实现思路
实现步骤
1). 导入Spring Cache和Redis相关maven坐标
2). 在启动类上加入EnableCaching注解开启缓存注解功能
3). 在用户端接口SetmealController的 list 方法上加入Cacheable注解
4). 在管理端接口SetmealController的 save、delete、update、startOrStop等方法上加入CacheEvict注解
2.3 代码开发
按照上述实现步骤
1). 导入Spring Cache和Redis相关maven坐标(已实现)
dependencygroupIdorg.springframework.boot/groupIdartifactIdspring-boot-starter-data-redis/artifactId
/dependencydependencygroupIdorg.springframework.boot/groupIdartifactIdspring-boot-starter-cache/artifactId
/dependency2). 在启动类上加入EnableCaching注解开启缓存注解功能
package com.sky;SpringBootApplication
EnableTransactionManagement //开启注解方式的事务管理
Slf4j
EnableCaching
public class SkyApplication {public static void main(String[] args) {SpringApplication.run(SkyApplication.class, args);log.info(server started);}
}3). 在用户端接口SetmealController的 list 方法上加入Cacheable注解 /*** 条件查询** param categoryId* return*/GetMapping(/list)ApiOperation(根据分类id查询套餐)Cacheable(cacheNames setmealCache,key #categoryId) //key: setmealCache::100public ResultListSetmeal list(Long categoryId) {Setmeal setmeal new Setmeal();setmeal.setCategoryId(categoryId);setmeal.setStatus(StatusConstant.ENABLE);ListSetmeal list setmealService.list(setmeal);return Result.success(list);}4). 在管理端接口SetmealController的 save、delete、update、startOrStop等方法上加入CacheEvict注解 /*** 新增套餐** param setmealDTO* return*/PostMappingApiOperation(新增套餐)CacheEvict(cacheNames setmealCache,key #setmealDTO.categoryId)//key: setmealCache::100public Result save(RequestBody SetmealDTO setmealDTO) {setmealService.saveWithDish(setmealDTO);return Result.success();}/*** 批量删除套餐** param ids* return*/DeleteMappingApiOperation(批量删除套餐)CacheEvict(cacheNames setmealCache,allEntries true)public Result delete(RequestParam ListLong ids) {setmealService.deleteBatch(ids);return Result.success();}/*** 修改套餐** param setmealDTO* return*/PutMappingApiOperation(修改套餐)CacheEvict(cacheNames setmealCache,allEntries true)public Result update(RequestBody SetmealDTO setmealDTO) {setmealService.update(setmealDTO);return Result.success();}/*** 套餐起售停售** param status* param id* return*/PostMapping(/status/{status})ApiOperation(套餐起售停售)CacheEvict(cacheNames setmealCache,allEntries true)public Result startOrStop(PathVariable Integer status, Long id) {setmealService.startOrStop(status, id);return Result.success();}后记 美好的一天到此结束下次继续努力欲知后续请看下回分解写作不易感谢大家的支持