SpringBoot中操作Redis通过所有可能的key查询存在的key并解析为对象实体的通用方法
场景
SpringBoot中操作Redis的特殊操作-批量查询(通过key的集合批量查杜绝模糊搜索)、查询并解析对象list:
SpringBoot中操作Redis的特殊操作-批量查询(通过key的集合批量查杜绝模糊搜索)、查询并解析对象list_霸道流氓气质的博客-CSDN博客
在上面讲操作redis中特殊操作时,对于通过key的集合批量查询所使用的工具方法,不能实现
通用对象适配,下面进行修改。
应用场景是所有业务数据会存储在mysql数据库中,使用redis作为msyql数据库的缓存。
但是redis中有的数据不一定全覆盖mysql中的数据。
那么在redis中进行缓存时会使用mysql中某个字段作为唯一标识缓存到redis中,将唯一标识作为
redis的key,那么如何通过所有可能的key的集合在redis中批量查询所有存在的key,并将value数据
进行解析为对应的对象。
比如以下两个redis中存储的数据
适用对象1
适用对象2
注:
博客:
霸道流氓气质的博客_CSDN博客-C#,架构之路,SpringBoot领域博主
实现
1、抽离公共操作redis的方法类
package com.badao.demo.utils;import com.alibaba.fastjson.JSON;
import com.badao.demo.constant.RedisConstants;
import com.badao.demo.entity.*;
import com.ruoyi.common.core.domain.reportmanagement.BusCarEcu;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;import java.util.*;
import java.util.stream.Collectors;
import java.util.stream.Stream;/* 公共服务工具类*/
@Component
public class CommonServiceUtils {@Autowiredprivate RedisCache redisCache;/* 通过所有可能的key从redis中获取存在的key* @param allKeys* @return*/public List<Map<String, Object>> getExistKeys(Set<String> allKeys) {try {List<Map<String, Object>> keys = redisCache.getCacheList(allKeys);return keys;}catch (Exception exception){System.out.println("getExistKeys:异常:"+exception);return new ArrayList<>();}}/* 数据转换为实体* @param* @return*/public Stream<Object> convertToDTOs(List<Map<String, Object>> objects) {try {objects.removeAll(Collections.singletonList(null));objects.forEach(car -> {car.remove("@type");if(car.containsKey("params")){car.remove("params");}});Stream<Object> objectStream = JSON.parseArray(JSON.toJSONString(objects), Object.class).stream();return objectStream;}catch (Exception exception){System.out.println("convertToDTOs异常:"+exception.getMessage());return Stream.of();}}
}
一个方法是传递所有可能的key的集合,然后从redis中批量查询。
一个是将查询到的数据移除空数据,这里移除@Type和移除params完全是根据自己业务来写,
在redis中存储时会有这两个字段,所以在映射为实体时需要将其移除掉。
如果自己业务中没有这两个字段,可以不用写这块。
然后返回Object的Stream。
2、在需要调用的地方
@Autowiredprivate CommonServiceUtils commonServiceUtils;
先引入依赖
再获取所有所有可能的key的集合
Set<String> allKeys = signalLightIdList.stream().map(signal -> RedisConstants.SIGNALIGHT_XHD + signal).collect(Collectors.toSet());List<Map<String, Object>> cards = commonServiceUtils.getExistKeys(allKeys);if(cards.size()>0) {Stream<Object> dtosStream = commonServiceUtils.convertToDTOs(cards);List<SignalrightDevsDTO> collect = dtosStream.map(dto -> {BusSignallightControl busSignallightControl = JSONObject.toJavaObject((JSON) dto, BusSignallightControl.class);
如果是映射其他对象也可以通用
Set<String> allKeys = carInfoList.stream().map(carInfoPO -> RedisConstants.CARD_CARD + carInfoPO.getLocationNumber()).collect(Collectors.toSet());List<Map<String, Object>> cards = commonServiceUtils.getExistKeys(allKeys);if(cards.size()>0){Stream<Object> cardDTOStream = commonServiceUtils.convertToDTOs(cards);try {List<CarPositionDTO> carPositionDTOList = cardDTOStream.map(cardDTO -> {CardDTO cardDTOVO = JSONObject.toJavaObject((JSON) cardDTO, CardDTO.class);
一个完整业务示例代码
public List<SignalrightDevsDTO> getSignalrightDevsDtoList(List<Long> signalLightIdList) {Set<String> allKeys = signalLightIdList.stream().map(signal -> RedisConstants.SIGNALIGHT_XHD + signal).collect(Collectors.toSet());List<Map<String, Object>> cards = commonServiceUtils.getExistKeys(allKeys);if(cards.size()>0) {Stream<Object> dtosStream = commonServiceUtils.convertToDTOs(cards);List<SignalrightDevsDTO> collect = dtosStream.map(dto -> {BusSignallightControl busSignallightControl = JSONObject.toJavaObject((JSON) dto, BusSignallightControl.class);return SignalrightDevsDTO.builder().mineCode(mineCode).mineName(mineName).equipmentCode(busSignallightControl.getId().toString()).equipmentName(busSignallightControl.getSignalLightName()).signalState(busSignallightControl.getLightState()).build();}).collect(Collectors.toList());return collect;}else{return null;}}
示例效果