当前位置:   article > 正文

简单的使用Redis写入和查询数据_redis computeifabsent

redis computeifabsent

我们以将字典数据写入Redis中,并查询数据为例

1、查询字典数据并写入Redis中

  1. @Resource
  2. private TestMapper testMapper;
  3. @Resource
  4. ShardingRedisUtil shardingRedisUtil;
  5. @Override
  6. public void testSetRedis() {
  7. // 获取所有字典信息
  8. List<TbSysDictInfo> list = testMapper.selectAll();
  9. // 根据字典类型分组
  10. Map<String, List<TbSysDictInfo>> distMap = list.stream()
  11. .collect(Collectors.groupingBy(TbSysDictInfo::getTypeCode));
  12. // 将数据写入redis
  13. shardingRedisUtil.hMSet(Dictconstants.DICT_RESULT, distMap);
  14. }

Dictconstants方法

  1. public class Dictconstants {
  2. /**
  3. * 字典结果属性
  4. */
  5. public static final String DICT_RESULT = "dict_result_";
  6. }

2、根据字典类型从Redis中查询数据

  1. @Override
  2. public List<TbSysDictInfo> testGetRedis(String type) {
  3. // 根据字典类型获取列表
  4. Map<String, List<TbSysDictInfo>> distMap = shardingRedisUtil.hMGet(new TypeReference<List<TbSysDictInfo>>() {
  5. }, Dictconstants.DICT_RESULT, type);
  6. if (distMap.get(type)!=null){
  7. return distMap.get(type);
  8. }else {
  9. return new ArrayList<>();
  10. }
  11. }

3、RedisUtil工具类 ShardingRedisUtil 

这个工具类功能很强大,大家可以自行挖掘

  1. import com.fasterxml.jackson.core.type.TypeReference;
  2. import com.fasterxml.jackson.databind.ObjectMapper;
  3. import org.apache.commons.lang3.StringUtils;
  4. import org.apache.commons.lang3.exception.ExceptionUtils;
  5. import org.slf4j.Logger;
  6. import org.slf4j.LoggerFactory;
  7. import org.springframework.data.redis.core.Cursor;
  8. import org.springframework.data.redis.core.RedisTemplate;
  9. import org.springframework.data.redis.core.ScanOptions;
  10. import org.springframework.stereotype.Component;
  11. import org.springframework.util.CollectionUtils;
  12. import javax.annotation.Resource;
  13. import java.util.*;
  14. import java.util.concurrent.CompletableFuture;
  15. import java.util.concurrent.ConcurrentHashMap;
  16. import java.util.concurrent.TimeUnit;
  17. import java.util.stream.Collectors;
  18. @Component
  19. public class ShardingRedisUtil {
  20. Logger logger = LoggerFactory.getLogger(this.getClass());
  21. @Resource
  22. private RedisTemplate<String, Object> redisTemplate;
  23. private static final int SHARDING_COUNT = 100; //分片数
  24. private static final int SCAN_COUNT = 1000; //扫描分批数
  25. private ObjectMapper objectMapper = new ObjectMapper();
  26. public void hMSet(String key, Map<String, ? extends Object> map) {
  27. hMSet(key, map, SHARDING_COUNT);
  28. }
  29. public <T> Map<String, T> hMGet(TypeReference<T> typeReference, String key, String... field) {
  30. return hMGet(typeReference, SHARDING_COUNT, key, field);
  31. }
  32. public <T> Map<String, T> hMGet(TypeReference<T> typeReference, String key, List<String> fields) {
  33. if (CollectionUtils.isEmpty(fields)) {
  34. return null;
  35. }
  36. return hMGet(typeReference, key, fields.toArray(new String[1]));
  37. }
  38. public long hDel(String key, String... field) {
  39. return hDel(SHARDING_COUNT, key, field);
  40. }
  41. public void hMSet(String key, Map<String, ? extends Object> map, int shardingCount) {
  42. if (!CollectionUtils.isEmpty(map)) {
  43. Map<String, Map<String, Object>> tmpMap = new HashMap<>();
  44. for (Map.Entry<String, ? extends Object> entry : map.entrySet()) {
  45. String tmpKey = entry.getKey();
  46. Object tmpValue = entry.getValue();
  47. int num = Math.abs(tmpKey.hashCode() % shardingCount);
  48. String hashKey = String.format("%s$%s", key, num);
  49. tmpMap.computeIfAbsent(hashKey, k -> new HashMap<>()).put(tmpKey, tmpValue);
  50. }
  51. for (Map.Entry<String, Map<String, Object>> entry : tmpMap.entrySet()) {
  52. redisTemplate.opsForHash().putAll(entry.getKey(), entry.getValue());
  53. }
  54. }
  55. }
  56. public void hMSetToOneGroup(String key, Map<String, Object> map) {
  57. if (!CollectionUtils.isEmpty(map)) {
  58. redisTemplate.opsForHash().putAll(key, map);
  59. }
  60. }
  61. public <T> Map<String, T> hMGetfromOneGroup(TypeReference<T> typeReference, String key, String... field) {
  62. Map<String, T> resultMap = new HashMap<>();
  63. if (field != null) {
  64. List<Object> objects = redisTemplate.opsForHash().multiGet(key, Arrays.asList(field));
  65. List<String> fieldList = new ArrayList<>();
  66. Collections.addAll(fieldList, field);
  67. for (int i = 0; i < fieldList.size(); i++) {
  68. Object o = objects.get(i);
  69. resultMap.put(fieldList.get(i), o != null ? objectMapper.convertValue(o, typeReference) : null);
  70. }
  71. }
  72. return resultMap;
  73. }
  74. public <T> Map<String, T> hMGet(TypeReference<T> typeReference, int shardingCount, String key, String... field) {
  75. Map<String, T> resultMap = new HashMap<>();
  76. if (field != null) {
  77. for (Map.Entry<String, List<String>> entry : separateToMap(shardingCount, key, field).entrySet()) {
  78. List<String> fieldList = entry.getValue();
  79. List<Object> objects = redisTemplate.opsForHash().multiGet(entry.getKey(), new ArrayList<>(fieldList));
  80. for (int i = 0; i < fieldList.size(); i++) {
  81. Object o = objects.get(i);
  82. resultMap.put(fieldList.get(i), o != null ? objectMapper.convertValue(o, typeReference) : null);
  83. }
  84. }
  85. }
  86. return resultMap;
  87. }
  88. /**
  89. * 扫描key前缀,获取key的所有redis缓存
  90. *
  91. * @param keyPattern
  92. * @param <T>
  93. * @return
  94. */
  95. public <T> Map<String, T> hMGet(TypeReference<T> typeReference, String keyPattern) {
  96. return hMGet(typeReference, SHARDING_COUNT, keyPattern);
  97. }
  98. /**
  99. * 扫描key前缀,获取key的所有redis缓存
  100. *
  101. * @param keyPattern
  102. * @param <T>
  103. * @return
  104. */
  105. public <T> Map<String, T> hMGet(TypeReference<T> typeReference, int shardingCount, String keyPattern) {
  106. Map<String, T> resultMap = new HashMap<>();
  107. if (StringUtils.isNoneBlank(keyPattern)) {
  108. try {
  109. for (int num = 0; num < shardingCount; num++) {
  110. String hashKey = String.format("%s$%s", keyPattern, num);
  111. // Cursor<Map.Entry<Object, Object>> cursor = redisTemplate.opsForHash().scan(hashKey, ScanOptions.scanOptions().count(SCAN_COUNT).build());
  112. // while (cursor.hasNext()) {
  113. // Map.Entry<Object, Object> next = cursor.next();
  114. // Object field = next.getKey();
  115. // Object value = next.getValue();
  116. // if (field != null && value != null) {
  117. // resultMap.put(field.toString(), objectMapper.convertValue(value, typeReference));
  118. // }
  119. // }
  120. // cursor.close();
  121. resultMap.putAll(hMGetTargetKey(typeReference,hashKey));
  122. }
  123. } catch (Exception e) {
  124. logger.error("扫描redis获取hashKey所有缓存异常", e);
  125. }
  126. }
  127. return resultMap;
  128. }
  129. /**
  130. * 扫描key前缀,获取key的所有redis缓存
  131. *
  132. * @param key
  133. * @param <T>
  134. * @return
  135. */
  136. public <T> Map<String, T> hMGetTargetKey(TypeReference<T> typeReference, String key) {
  137. Map<String, T> resultMap = new HashMap<>();
  138. if (StringUtils.isNoneBlank(key)) {
  139. try {
  140. Cursor<Map.Entry<Object, Object>> cursor = redisTemplate.opsForHash().scan(key, ScanOptions.scanOptions().count(SCAN_COUNT).build());
  141. while (cursor.hasNext()) {
  142. Map.Entry<Object, Object> next = cursor.next();
  143. Object field = next.getKey();
  144. Object value = next.getValue();
  145. if (field != null && value != null) {
  146. resultMap.put(field.toString(), objectMapper.convertValue(value, typeReference));
  147. }
  148. }
  149. cursor.close();
  150. } catch (Exception e) {
  151. logger.error("扫描redis获取hashKey所有缓存异常", e);
  152. }
  153. }
  154. return resultMap;
  155. }
  156. public Long hDel(int shardingCount, String key, String... field) {
  157. long count = 0;
  158. if (field != null) {
  159. for (Map.Entry<String, List<String>> entry : separateToMap(shardingCount, key, field).entrySet()) {
  160. count += redisTemplate.opsForHash().delete(entry.getKey(), entry.getValue().toArray());
  161. }
  162. }
  163. return count;
  164. }
  165. private Map<String, List<String>> separateToMap(int shardingCount, String key, String[] field) {
  166. Map<String, List<String>> tmpMap = new HashMap<>();
  167. for (String s : field) {
  168. if (StringUtils.isNotBlank(s)) {
  169. int num = Math.abs(s.hashCode() % shardingCount);
  170. String hashKey = String.format("%s$%s", key, num);
  171. tmpMap.computeIfAbsent(hashKey, k -> new ArrayList<>()).add(s);
  172. }
  173. }
  174. return tmpMap;
  175. }
  176. public void listSet(String key, List list) {
  177. if (!CollectionUtils.isEmpty(list)) {
  178. redisTemplate.opsForList().rightPushAll(key, list);
  179. }
  180. }
  181. public long listSize(String key) {
  182. return redisTemplate.opsForList().size(key);
  183. }
  184. public <T> Map<String, List<T>> listGet(String prefix, TypeReference<T> typeReference) {
  185. Map<String, List<T>> result = new ConcurrentHashMap<>();
  186. Set<String> setKeys = redisTemplate.keys(prefix + "*");
  187. setKeys.parallelStream().forEach(hashKey -> {
  188. try {
  189. List<T> list = listGet(typeReference, hashKey);
  190. result.put(hashKey, list);
  191. } catch (Exception e) {
  192. logger.error("获取hashKey为" + hashKey + "的redis缓存列表失败", e);
  193. }
  194. });
  195. return result;
  196. }
  197. public <T> List<T> listGet(TypeReference<T> typeReference, String key) {
  198. List<T> resultList = new LinkedList<>();
  199. long size = redisTemplate.opsForList().size(key);
  200. for (int index = 0; index < size; index = index + 1000) {
  201. List<Object> objList = new ArrayList<>();
  202. try {
  203. objList = redisTemplate.opsForList().range(key, index, 1000);
  204. objList.forEach(obj->{
  205. resultList.add(objectMapper.convertValue(obj, typeReference));
  206. });
  207. } catch (Exception e) {
  208. logger.error(ExceptionUtils.getStackTrace(e));
  209. }
  210. }
  211. return resultList;
  212. }
  213. public void listDeleteOneList(String key) {
  214. deleteKey(key);
  215. }
  216. public Long listDel(String key, long count, Object value) {
  217. return redisTemplate.opsForList().remove(key, count, value);
  218. }
  219. public boolean deleteKey(String key) {
  220. return redisTemplate.delete(key);
  221. }
  222. public Set<String> getKeys(String pattern) {
  223. return getKeys(pattern, 10, TimeUnit.SECONDS);
  224. }
  225. public Set<String> getKeys(String pattern, int timeout, TimeUnit timeUnit) {
  226. Set<String> keys = new HashSet<>();
  227. CompletableFuture<Set<String>> getRedisKeysFuture = CompletableFuture.supplyAsync(() -> {
  228. try {
  229. return redisTemplate.keys(pattern);
  230. } catch (Exception e) {
  231. logger.error("获取redis中包含{}的key失败:", pattern, e);
  232. return null;
  233. }
  234. }).whenComplete((result, ex) -> {
  235. if (result != null) {
  236. keys.addAll(result);
  237. }
  238. });
  239. try {
  240. getRedisKeysFuture.get(timeout, timeUnit);
  241. } catch (Exception e) {
  242. logger.error("获取redis中包含{}的key超时:", pattern, e);
  243. }
  244. return keys;
  245. }
  246. public void strSet(String key, String value) {
  247. redisTemplate.opsForValue().set(key, value);
  248. }
  249. public void strSet(String key, String value, long timeout, TimeUnit timeUnit) {
  250. redisTemplate.opsForValue().set(key, value, timeout, timeUnit);
  251. }
  252. public String strGet(String key) {
  253. Object object = redisTemplate.opsForValue().get(key);
  254. if (object != null) {
  255. return object.toString();
  256. }
  257. return null;
  258. }
  259. public void expire(String key, long timeout, TimeUnit unit) {
  260. redisTemplate.expire(key, timeout, unit);
  261. }
  262. public void hLSetToOneGroup(String key, List<Object> list) {
  263. if (!CollectionUtils.isEmpty(list)) {
  264. redisTemplate.opsForList().leftPushAll(key, list);
  265. }
  266. }
  267. public <T> List<T> hLGetFromOneGroup(TypeReference<T> typeReference, String key) {
  268. List<T> result = new ArrayList<>();
  269. if (StringUtils.isNotBlank(key)) {
  270. long size = Optional.ofNullable(redisTemplate.opsForList().size(key)).orElse(0L);
  271. List<Object> objects = redisTemplate.opsForList().range(key, 0, size);
  272. if (!CollectionUtils.isEmpty(objects)) {
  273. for (Object o : objects) {
  274. result.add(o != null ? objectMapper.convertValue(o, typeReference) : null);
  275. }
  276. }
  277. }
  278. return result;
  279. }
  280. public void setTypeAdd(String key, Object value) {
  281. redisTemplate.opsForSet().add(key, value);
  282. }
  283. public void setTypeAddAll(String key, Set<Object> value) {
  284. redisTemplate.opsForSet().add(key, value.toArray(new Object[1]));
  285. }
  286. public Set setTypeGet(String key) {
  287. return redisTemplate.opsForSet().members(key);
  288. }
  289. public boolean setTypeContain(String key, String value) {
  290. return redisTemplate.opsForSet().isMember(key, value);
  291. }
  292. }

4、Redis链接配置工具类

  1. import com.fasterxml.jackson.databind.ObjectMapper;
  2. import org.springframework.beans.factory.annotation.Value;
  3. import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
  4. import org.springframework.context.annotation.Bean;
  5. import org.springframework.context.annotation.Configuration;
  6. import org.springframework.data.redis.connection.RedisConnectionFactory;
  7. import org.springframework.data.redis.core.RedisTemplate;
  8. import org.springframework.data.redis.serializer.Jackson2JsonRedisSerializer;
  9. import org.springframework.data.redis.serializer.StringRedisSerializer;
  10. import redis.clients.jedis.JedisPool;
  11. import redis.clients.jedis.JedisPoolConfig;
  12. @Configuration
  13. @ConditionalOnProperty(name = "spring.redis.host")
  14. public class RedisConfiguration {
  15. @Value("${spring.redis.host}")
  16. private String host ;
  17. @Value("${spring.redis.port}")
  18. private int port ;
  19. @Value("${spring.redis.password}")
  20. private String password ;
  21. @Value("${spring.redis.timeout:3000}")
  22. private int timeout ;
  23. @Value("${redis.jedisPoolConfig.maxActive:300}")
  24. private int maxActive ;
  25. @Value("${redis.jedisPoolConfig.maxIdle:100}")
  26. private int maxIdle ;
  27. @Value("${redis.jedisPoolConfig.minIdle:1}")
  28. private int minIdle ;
  29. @Value("${redis.jedisPoolConfig.maxWait:5000}")
  30. private int maxWait ;
  31. @Value("${spring.redis.database:0}")
  32. private int database;
  33. @Bean
  34. public RedisTemplate<String, Object> redisTemplate(RedisConnectionFactory redisConnectionFactory){
  35. RedisTemplate<String, Object> redisTemplate = new RedisTemplate<>();
  36. redisTemplate.setConnectionFactory(redisConnectionFactory);
  37. Jackson2JsonRedisSerializer<Object> jackson2JsonRedisSerializer = new Jackson2JsonRedisSerializer<>(Object.class);
  38. ObjectMapper objectMapper = new ObjectMapper();
  39. // objectMapper.setVisibility(PropertyAccessor.ALL, JsonAutoDetect.Visibility.ANY);
  40. // objectMapper.enableDefaultTyping(ObjectMapper.DefaultTyping.NON_FINAL);
  41. jackson2JsonRedisSerializer.setObjectMapper(objectMapper);
  42. StringRedisSerializer stringRedisSerializer = new StringRedisSerializer();
  43. redisTemplate.setKeySerializer(stringRedisSerializer);
  44. redisTemplate.setHashKeySerializer(stringRedisSerializer);
  45. redisTemplate.setValueSerializer(jackson2JsonRedisSerializer);
  46. redisTemplate.setHashValueSerializer(jackson2JsonRedisSerializer);
  47. redisTemplate.afterPropertiesSet();
  48. return redisTemplate;
  49. }
  50. @Bean
  51. public JedisPool JedisPoolFactory() {
  52. JedisPoolConfig poolConfig = new JedisPoolConfig();
  53. poolConfig.setMaxTotal(maxActive);
  54. poolConfig.setMaxIdle(maxIdle);
  55. poolConfig.setMinIdle(minIdle);
  56. poolConfig.setMaxWaitMillis( maxWait);
  57. JedisPool jedisPool = new JedisPool(poolConfig,host,port,timeout,password,database);
  58. return jedisPool;
  59. }
  60. }

5、配置文件内容

  1. spring:
  2. redis:
  3. host: localhost
  4. port: 6379
  5. #password:

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/从前慢现在也慢/article/detail/852996?site
推荐阅读
相关标签
  

闽ICP备14008679号