package com.ard.common.core.redis; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Qualifier; import org.springframework.data.redis.core.Cursor; import org.springframework.data.redis.core.RedisCallback; import org.springframework.data.redis.core.RedisTemplate; import org.springframework.data.redis.core.ScanOptions; import org.springframework.stereotype.Component; import org.springframework.util.CollectionUtils; import java.nio.charset.StandardCharsets; import java.util.*; import java.util.concurrent.TimeUnit; /** * @author sean * @version 1.0 * @date 2022/4/19 */ @Component public class RedisOpsUtils { private static RedisTemplate redisTemplate; @Autowired public void setRedisTemplate(@Qualifier("redisTemplate") RedisTemplate redisTemplate) { RedisOpsUtils.redisTemplate = redisTemplate; } /** * HSET * @param key * @param field * @param value */ public static void hashSet(String key, String field, Object value) { redisTemplate.opsForHash().put(key, field, value); } /** * HGET * @param key * @param field * @return */ public static Object hashGet(String key, String field) { return redisTemplate.opsForHash().get(key, field); } /** * HKEYS * @param key * @return */ public static Set hashKeys(String key) { return redisTemplate.opsForHash().keys(key); } /** * HEXISTS * @param key * @param field * @return */ public static boolean hashCheck(String key, String field) { return redisTemplate.opsForHash().hasKey(key, field); } /** * HDEL * @param key * @param fields * @return */ public static boolean hashDel(String key, Object[] fields) { return redisTemplate.opsForHash().delete(key, fields) > 0; } /** * HLEN * @param key * @return */ public static long hashLen(String key) { return redisTemplate.opsForHash().size(key); } /** * EXPIRE * @param key * @param timeout * @return */ public static boolean expireKey(String key, long timeout) { return redisTemplate.expire(key, timeout, TimeUnit.SECONDS); } /** * SET * @param key * @param value */ public static void set(String key, Object value) { redisTemplate.opsForValue().set(key, value); } /** * GET * @param key * @return */ public static Object get(String key) { return redisTemplate.opsForValue().get(key); } /** * SETEX * @param key * @param value * @param expire */ public static void setWithExpire(String key, Object value, long expire) { redisTemplate.opsForValue().set(key, value, expire, TimeUnit.SECONDS); } /** * TTL * @param key * @return */ public static long getExpire(String key) { return redisTemplate.getExpire(key, TimeUnit.SECONDS); } /** * EXISTS * @param key * @return */ public static boolean checkExist(String key) { return redisTemplate.hasKey(key); } /** * DEL * @param key * @return */ public static boolean del(String key) { return RedisOpsUtils.checkExist(key) && redisTemplate.delete(key); } /** * KEYS * @param pattern * @return */ public static Set getAllKeys(Object pattern) { return redisTemplate.keys(pattern); } /** * RPUSH * @param key * @param value */ public static void listRPush(String key, Object... value) { if (value.length == 0) { return; } for (Object val : value) { redisTemplate.opsForList().rightPush(key, val); } } /** * LRANGE * @param key * @param start * @param end * @return */ public static List listGet(String key, long start, long end) { return redisTemplate.opsForList().range(key, start, end); } /** * LRANGE * @param key * @return */ public static List listGetAll(String key) { return redisTemplate.opsForList().range(key, 0, -1); } /** * LLen * @param key * @return */ public static Long listLen(String key) { return redisTemplate.opsForList().size(key); } /** * ZADD * @param key * @param value * @param score */ public static Boolean zAdd(String key, Object value, double score) { return redisTemplate.opsForZSet().add(key, value, score); } /** * ZREM * @param key * @param value */ public static Boolean zRemove(String key, Object... value) { return redisTemplate.opsForZSet().remove(key, value) > 0; } /** * ZRANGE * @param key * @param start * @param end * @return */ public static Set zRange(String key, long start, long end) { return redisTemplate.opsForZSet().range(key, start, end); } /** * ZRANGE * @param key * @return */ public static Object zGetMin(String key) { Set objects = zRange(key, 0, 0); if (CollectionUtils.isEmpty(objects)) { return null; } return objects.iterator().next(); } /** * ZSCORE * @param key * @param value * @return */ public static Double zScore(String key, Object value) { return redisTemplate.opsForZSet().score(key, value); } /** * ZINCRBY * @param key * @param value * @param delta */ public static Double zIncrement(String key, Object value, double delta) { return redisTemplate.opsForZSet().incrementScore(key, value, delta); } /** * 批量读取所有相关键值对 * @return 完整键 -> 值的映射 */ public static Map getAllData(String keyPrefix) { Map resultMap = new HashMap<>(); // 1. 用SCAN命令匹配前缀,获取所有相关键 List keys = redisTemplate.execute((RedisCallback>) connection -> { List keyList = new ArrayList<>(); // 构造匹配模式:前缀 + "*" ScanOptions options = ScanOptions.scanOptions() .match(keyPrefix) // 匹配所有带前缀的键 .count(100) // 每次迭代最多返回100个键(可根据实际调整) .build(); // try-with-resources自动关闭Cursor,避免资源泄漏 try (Cursor cursor = connection.scan(options)) { while (cursor.hasNext()) { byte[] keyBytes = cursor.next(); String key = new String(keyBytes, StandardCharsets.UTF_8); keyList.add(key); } } catch (Exception e) { throw new RuntimeException("Redis SCAN命令执行失败", e); } return keyList; }); // 2. 批量获取值(减少网络请求) if (!CollectionUtils.isEmpty(keys)) { List values = redisTemplate.opsForValue().multiGet(keys); // 3. 组装键值对 for (int i = 0; i < keys.size(); i++) { Object key = keys.get(i); Object value = values.get(i); if (value != null) { resultMap.put(key, value); } } } return resultMap; } }