Redis 黑马点评day02 商户查询缓存
1.Redis 缓存功能
Redis 是一个高性能的键值存储系统,通常用作缓存、消息队列或数据库。在缓存场景中,Redis 将数据存储在内存中,以提供极高的读写速度。以下是 Redis 缓存的一些关键特点:
高性能:数据存储在内存中,读写速度极快。
支持多种数据结构:字符串、哈希、列表、集合、有序集合、范围查询、位图、超日志等。
持久化支持:虽然 Redis 主要用于内存存储,但它也提供了多种持久化机制,如 RDB 和 AOF。
易于使用:提供了丰富的客户端库,支持多种编程语言。
2.商铺缓存

/*** 根据id查询商铺信息* @param id 商铺id* @return 商铺详情数据*/@GetMapping("/{id}")public Result queryShopById(@PathVariable("id") Long id) {return shopService.queryById(id);}
//impl
@Service
public class ShopServiceImpl extends ServiceImpl<ShopMapper, Shop> implements IShopService {@Resourceprivate StringRedisTemplate stringRedisTemplate;@Overridepublic Result queryById(Long id){String key = CACHE_SHOP_KEY+id;//1.redis查商铺缓存String shopJson = stringRedisTemplate.opsForValue().get(key);//2.判断是否存在if(StrUtil.isNotBlank(shopJson)) {//3.存在返回Shop shop = JSONUtil.toBean(shopJson,Shop.class);return Result.ok(shop);}//4.不存在根据id查询数据库Shop shop = getById(id);//5.不存在返回错误if(shop == null){return Result.fail("店铺不存在");}//6.存在写入redisstringRedisTemplate.opsForValue().set(key,JSONUtil.toJsonStr(shop));;//7.返回return Result.ok(shop);}3.店铺缓存菜单

Controller
@RestController
@RequestMapping("/shop-type")
public class ShopTypeController {@Resourceprivate IShopTypeService typeService;@GetMapping("list")public Result queryTypeList() {
// List<ShopType> typeList = typeService
// .query().orderByAsc("sort").list();return typeService.showlist();}
}Impl
package com.hmdp.service.impl;import cn.hutool.core.util.StrUtil;
import com.hmdp.dto.Result;
import com.hmdp.entity.ShopType;
import cn.hutool.json.JSONUtil;
import com.hmdp.mapper.ShopTypeMapper;
import com.hmdp.service.IShopTypeService;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.stereotype.Service;import javax.annotation.Resource;
import java.util.List;/*** <p>* 服务实现类* </p>** @author 虎哥* @since 2021-12-22*/
@Service
public class ShopTypeServiceImpl extends ServiceImpl<ShopTypeMapper, ShopType> implements IShopTypeService {@Resourceprivate StringRedisTemplate stringRedisTemplate;@Overridepublic Result showlist() {//从redis查找String key = "cache:shop:type";String shopType = stringRedisTemplate.opsForValue().get(key);//如果不为空返回if(StrUtil.isNotBlank(shopType)){List<ShopType> shopTypeList = JSONUtil.toList(shopType,ShopType.class);return Result.ok(shopTypeList);}//如果为空,从数据库查找List<ShopType> ShopTypes = query().orderByAsc("sort").list();//如果数据库没有,报错if(ShopTypes.isEmpty()){return Result.fail("没有数据");}//缓存到redisstringRedisTemplate.opsForValue().set(key,JSONUtil.toJsonStr(ShopTypes));return Result.ok(ShopTypes);}
}
4.缓存更新策略





queryById
//6.存在写入redisstringRedisTemplate.opsForValue().set(key,JSONUtil.toJsonStr(shop),CACHE_SHOP_TTL,TimeUnit.MINUTES);update
@Override@Transactionalpublic Result update(Shop shop) {Long id = shop.getId();if(id == null){return Result.fail("店铺id不能为空");}//1.更新数据库updateById(shop);//2.删除缓存stringRedisTemplate.delete(CACHE_SHOP_KEY+shop.getId());//3.返回return Result.ok();}5.缓存穿透



@Overridepublic Result queryById(Long id){String key = CACHE_SHOP_KEY+id;//1.redis查商铺缓存String shopJson = stringRedisTemplate.opsForValue().get(key);//2.判断是否存在if(StrUtil.isNotBlank(shopJson)) {//3.存在返回Shop shop = JSONUtil.toBean(shopJson,Shop.class);return Result.ok(shop);}//判断是否为空值if(shopJson != null){return Result.fail("店铺不存在");}//4.不存在根据id查询数据库Shop shop = getById(id);//5.不存在返回错误if(shop == null){//空值写入redisstringRedisTemplate.opsForValue().set(key,"",CACHE_NULL_TTL,TimeUnit.MINUTES);//返回错误信息return Result.fail("店铺不存在");}//6.存在写入redisstringRedisTemplate.opsForValue().set(key,JSONUtil.toJsonStr(shop),CACHE_SHOP_TTL,TimeUnit.MINUTES);//7.返回return Result.ok(shop);}