使用StringRedisTemplate,键和值都需要是String类型,由Redis提供的String类型序列化器
使用RedisTemplate,键和值都是Object类型,由JDK提供的序列化器(使用Redis可视化工具查看会乱码)
使用自定义RedisTemplate
创建RedisTemplate配置类
注入引用RedisTemplate<>泛型用自己定义的
Serviceimpl中使用:先查询缓存中是否有数据---->没有就创建对象然后放到缓存里------->有就直接Return回去一个需要的对象
缓存一致性问题:修改数据库同时修改缓存:在修改数据的Service中注入RedisTemplate------>完成数据库操作后添加删除缓存方法RedisTemplate.remove(key);
1.自定义RedisTemplate
本项目使用Reids保存缓存数据,因此我们需要使用RedisTemplate进行读写操作。前文提到过,Spring-data-redis
提供了StringRedisTemplate
和RedisTemplate<Object,Object>
两个实例,但是两个实例均不满足我们当前的需求,所以我们需要自定义RedisTemplate。
在common模块中创建com.atguigu.lease.common.redis.RedisConfiguration
类,内容如下
@Configuration
public class RedisConfiguration {
@Bean
public RedisTemplate<String, Object> stringObjectRedisTemplate(RedisConnectionFactory redisConnectionFactory) {
//新建一个Template
RedisTemplate<String, Object> template = new RedisTemplate<>();
//创建一个ConnectionFactory
template.setConnectionFactory(redisConnectionFactory);
//设置key和value的序列化器
template.setKeySerializer(RedisSerializer.string());
template.setValueSerializer(RedisSerializer.java());
return template;
}
}
2.编写缓存逻辑
修改web-app模块中的com.atguigu.lease.web.app.service.impl.RoomInfoServiceImpl
中的getDetailById
方法,如下
@Override
public RoomDetailVo getDetailById(Long id) {
//定义key
String key = RedisConstant.APP_ROOM_PREFIX+id;
//先去查询缓存是否有这个key
RoomDetailVo redisRoomDetailVo = (RoomDetailVo)redisTemplate.opsForValue().get(key);
//查到了直接返回Return出去,没查到就新建插入
if(redisRoomDetailVo==null){
//1.查询房间信息
RoomInfo roomInfo = roomInfoMapper.selectById(id);
if (roomInfo == null) {
return null;
}
//2.查询图片
List<GraphVo> graphVoList = graphInfoMapper.selectListByItemTypeAndId(ItemType.ROOM, id);
//3.查询租期
List<LeaseTerm> leaseTermList = leaseTermMapper.selectListByRoomId(id);
//4.查询配套
List<FacilityInfo> facilityInfoList = facilityInfoMapper.selectListByRoomId(id);
//5.查询标签
List<LabelInfo> labelInfoList = labelInfoMapper.selectListByRoomId(id);
//6.查询支付方式
List<PaymentType> paymentTypeList = paymentTypeMapper.selectListByRoomId(id);
//7.查询基本属性
List<AttrValueVo> attrValueVoList = attrValueMapper.selectListByRoomId(id);
//8.查询杂费信息
List<FeeValueVo> feeValueVoList = feeValueMapper.selectListByApartmentId(roomInfo.getApartmentId());
//9.查询公寓信息
ApartmentItemVo apartmentItemVo = apartmentInfoService.selectApartmentItemVoById(roomInfo.getApartmentId());
redisRoomDetailVo = new RoomDetailVo();
BeanUtils.copyProperties(roomInfo, redisRoomDetailVo);
redisRoomDetailVo.setApartmentItemVo(apartmentItemVo);
redisRoomDetailVo.setGraphVoList(graphVoList);
redisRoomDetailVo.setAttrValueVoList(attrValueVoList);
redisRoomDetailVo.setFacilityInfoList(facilityInfoList);
redisRoomDetailVo.setLabelInfoList(labelInfoList);
redisRoomDetailVo.setPaymentTypeList(paymentTypeList);
redisRoomDetailVo.setFeeValueVoList(feeValueVoList);
redisRoomDetailVo.setLeaseTermList(leaseTermList);
//新建完成后就缓存到Redis中
redisTemplate.opsForValue().set(key, redisRoomDetailVo);
}
//保存浏览历史
browsingHistoryService.saveHistory(LoginUserHolder.getLoginUser().getUserId(),id);
return redisRoomDetailVo;
}
3.编写删除缓存逻辑
为保证缓存数据的一致性,在房间信息发生变化时,需要删除相关缓存。
修改web-admin模块中的com.atguigu.lease.web.admin.service.impl.RoomInfoServiceImpl
中的saveOrUpdateRoom
方法,如下
@Override
public void saveOrUpdateRoom(RoomSubmitVo roomSubmitVo) {
boolean isUpdate = roomSubmitVo.getId() != null;
super.saveOrUpdate(roomSubmitVo);
//若为更新操作,则先删除与Room相关的各项信息列表
if (isUpdate) {
//1.删除原有graphInfoList
......
//2.删除原有roomAttrValueList
......
//3.删除原有roomFacilityList
......
//4.删除原有roomLabelList
......
//5.删除原有paymentTypeList
......
//6.删除原有leaseTermList
......
//只在更新时操作数据库时,删除RedisRoom的缓存
String key= RedisConstant.APP_ROOM_PREFIX+roomSubmitVo.getId();
redisTemplate.delete(key);
}
//1.保存新的graphInfoList
......
//2.保存新的roomAttrValueList
......
//3.保存新的facilityInfoList
......
//4.保存新的labelInfoList
......
//5.保存新的paymentTypeList
......
//6.保存新的leaseTermList
......
}
修改web-admin模块中的com.atguigu.lease.web.admin.service.impl.RoomInfoServiceImpl
中的removeRoomById
方法,如下
@Override
public void removeRoomById(Long id) {
//1.删除RoomInfo
......
//2.删除graphInfoList
......
//3.删除attrValueList
......
//4.删除facilityInfoList
......
//5.删除labelInfoList
......
//6.删除paymentTypeList
......
//7.删除leaseTermList
......
//删除缓存
String key=RedisConstant.APP_ROOM_PREFIX+id;
redisTemplate.delete(key);
}
推荐阅读: