14、SpringBoot整合Redis
14.1、概述
SpringBoot操作数据库:spring-data,jpa,jdbc,mongodb,redis
SpringData也是和SpringBoot齐名的项目!
说明:在SpringBoot2.x之后,原来使用的jedis被替换成了lettuce
jedis:采用的直连,多个线程操作的话,是不安全的,如果想要避免不安全的,使用jedis pool连接池!更像BIO模式
lettuce:采用netty,实例可以在多个线程中进行共享,不存在线程不安全的情况,可以减少线程数据了,更像NIO模式
源码分析:
@AutoConfiguration
@ConditionalOnClass(RedisOperations.class)
@EnableConfigurationProperties(RedisProperties.class) // redis的各种配置
@Import({ LettuceConnectionConfiguration.class, JedisConnectionConfiguration.class })
public class RedisAutoConfiguration {
@Bean
@ConditionalOnMissingBean(name = "redistemplate") // 我们可以自定义一个redistemplate来替换这个默认的
@ConditionalOnSingleCandidate(RedisConnectionFactory.class)
public Redistemplate<Object, Object> redistemplate(RedisConnectionFactory redisConnectionFactory) {
// 默认的Redistemplate没有过多的配置,redis对象都需要序列化
// 两个泛型都是 Object的类型,我们使用的时候需要强转为<String, Object>
Redistemplate<Object, Object> template = new Redistemplate<>();
template.setConnectionFactory(redisConnectionFactory);
return template;
}
@Bean
@ConditionalOnMissingBean // 由于String是Redis中最常用的类型,所以单独提出一个bean
@ConditionalOnSingleCandidate(RedisConnectionFactory.class)
public StringRedistemplate stringRedistemplate(RedisConnectionFactory redisConnectionFactory) {
return new StringRedistemplate(redisConnectionFactory);
}
}
14.2、整合Redis
1、导入依赖
<!-- redis -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>
2、配置连接
# 配置redis host使用ip 或者 localhost
spring.redis.host = 127.0.0.1
spring.redis.port = 6379
3、测试
@SpringBoottest
class Springboot11RedisApplicationTests {
@Autowired
private Redistemplate redistemplate;
@Test
void contextLoads() {
// redistemplate 操作不同的数据类型,api和我们的指令是一样的
// opsForvalue 操作字符串 类似string
// opsForList 操作List 类似List
// opsForset
// opsForHash
// opsForzset
// opsForGeo
// opsForHyperLogLog
//除了基本的操作,我们常用的方法都可以直接通过redistemplate操作,比如事务,和基本的CRUD
//获取redis的连接对象
// RedisConnection connection = redistemplate.getConnectionFactory().getConnection();
// connection.flushDb();
// connection.flushAll();
redistemplate.opsForValue().set("ly", "你好 reids");
System.out.println(redistemplate.opsForValue().get("ly"));
}
}
14.3、RedisConfig配置类
// Redis配置
@Configuration
public class RedisConfig {
//固定模板
@Bean
public Redistemplate<String, Object> redistemplate(RedisConnectionFactory redisConnectionFactory) {
// 为了开发方便,一般使用 <String, Object>
Redistemplate<String, Object> template = new Redistemplate<>();
template.setConnectionFactory(redisConnectionFactory);
// Json的序列化方式
Jackson2JsonRedisSerializer jackson2JsonRedisSerializer = new Jackson2JsonRedisSerializer(Object.class);
ObjectMapper om = new ObjectMapper();
om.setVisibility(PropertyAccessor.ALL, JsonAutoDetect.Visibility.ANY);
om.enableDefaultTyping(ObjectMapper.DefaultTyping.NON_FINAL);
jackson2JsonRedisSerializer.setobjectMapper(om);
// String的序列化
StringRedisSerializer stringRedisSerializer = new StringRedisSerializer();
// key采用String的序列化方式
template.setKeySerializer(stringRedisSerializer);
// hash的key也采用String的序列化方式
template.setHashKeySerializer(stringRedisSerializer);
// value序列化方式采用jackson
template.setValueSerializer(jackson2JsonRedisSerializer);
// hash的value序列化方式采用jackson
template.setHashValueSerializer(jackson2JsonRedisSerializer);
template.afterPropertiesSet();
return template;
}
}
在Redis中,所有的实体化都会序列化,否则会出现问题
@Data
@AllArgsConstructor
@NoArgsConstructor
// 企业开发中,我们所有的pojo都会序列化
public class User implements Serializable {
private String name;
private int age;
}
测试
@SpringBoottest
class Springboot11RedisApplicationTests {
// 默认使用的是jdk序列化,可能会解析不对,所以我们需要使用自定义的序列化,重写Redistemplate方法覆盖原方法
// key 使用String解析,value使用json解析。
@Autowired
@Qualifier("redistemplate")
private Redistemplate redistemplate;
@Test
public void test() {
User user = new User("张三", 13);
// String userjson = new ObjectMapper().writeValueAsstring(user);
redistemplate.opsForValue().set("user", user);
System.out.println(redistemplate.opsForValue().get("user"));
}
}
14.4、RedisUtils工具类
14.4.1、工具类
Redis工具类千篇一律,网上有很多,这就是随便在网上找的一个工具类
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.*;
import org.springframework.stereotype.Component;
import java.util.List;
import java.util.Set;
import java.util.concurrent.TimeUnit;
@Component
public class RedisUtils {
@Autowired
private Redistemplate<String, Object> redistemplate;
private static double size = Math.pow(2, 32);
/**
* 写入缓存
* @param key
* @param offset 位 8Bit=1Byte
* @return
*/
public boolean setBit(String key, long offset, boolean isShow) {
boolean result = false;
try {
ValueOperations<String, Object> operations = redistemplate.opsForValue();
operations.setBit(key, offset, isShow);
result = true;
} catch (Exception e) {
e.printstacktrace();
}
return result;
}
/**
* 写入缓存
*
* @param key
* @param offset
* @return
*/
public boolean getBit(String key, long offset) {
boolean result = false;
try {
ValueOperations<String, Object> operations = redistemplate.opsForValue();
result = operations.getBit(key, offset);
} catch (Exception e) {
e.printstacktrace();
}
return result;
}
/**
* 写入缓存
*
* @param key
* @param value
* @return
*/
public boolean set(final String key, Object value) {
boolean result = false;
try {
ValueOperations<String, Object> operations = redistemplate.opsForValue();
operations.set(key, value);
result = true;
} catch (Exception e) {
e.printstacktrace();
}
return result;
}
/**
* 写入缓存设置失效时间
* @param key
* @param value
* @return
*/
public boolean set(final String key, Object value, Long expireTime) {
boolean result = false;
try {
ValueOperations<String, Object> operations = redistemplate.opsForValue();
operations.set(key, value);
redistemplate.expire(key, expireTime, TimeUnit.SECONDS);
result = true;
} catch (Exception e) {
e.printstacktrace();
}
return result;
}
/**
* 批量删除对应的value
*
* @param keys
*/
public void remove(final String... keys) {
for (String key : keys) {
remove(key);
}
}
/**
* 删除对应的value
*
* @param key
*/
public void remove(final String key) {
if (exists(key)) {
redistemplate.delete(key);
}
}
/**
* 判断缓存中是否有对应的value
*
* @param key
* @return
*/
public boolean exists(final String key) {
return redistemplate.hasKey(key);
}
/**
* 读取缓存
*
* @param key
* @return
*/
public Object get(final String key) {
Object result = null;
ValueOperations<String, Object> operations = redistemplate.opsForValue();
result = operations.get(key);
return result;
}
/**
* 哈希 添加
*
* @param key
* @param hashKey
* @param value
*/
public void hmSet(String key, Object hashKey, Object value) {
HashOperations<String, Object, Object> hash = redistemplate.opsForHash();
hash.put(key, hashKey, value);
}
/**
* 哈希获取数据
*
* @param key
* @param hashKey
* @return
*/
public Object hmGet(String key, Object hashKey) {
HashOperations<String, Object, Object> hash = redistemplate.opsForHash();
return hash.get(key, hashKey);
}
/**
* 列表添加
*
* @param k
* @param v
*/
public void lPush(String k, Object v) {
ListOperations<String, Object> list = redistemplate.opsForList();
list.rightPush(k, v);
}
/**
* 列表获取
*
* @param k
* @param l
* @param l1
* @return
*/
public List<Object> lRange(String k, long l, long l1) {
ListOperations<String, Object> list = redistemplate.opsForList();
return list.range(k, l, l1);
}
/**
* 集合添加
*
* @param key
* @param value
*/
public void add(String key, Object value) {
Setoperations<String, Object> set = redistemplate.opsForSet();
set.add(key, value);
}
/**
* 集合获取
* @param key
* @return
*/
public Set<Object> setMembers(String key) {
Setoperations<String, Object> set = redistemplate.opsForSet();
return set.members(key);
}
/**
* 有序集合添加
* @param key
* @param value
* @param scoure
*/
public void zAdd(String key, Object value, double scoure) {
ZSetoperations<String, Object> zset = redistemplate.opsForZSet();
zset.add(key, value, scoure);
}
/**
* 有序集合获取
* @param key
* @param scoure
* @param scoure1
* @return
*/
public Set<Object> rangeByscore(String key, double scoure, double scoure1) {
ZSetoperations<String, Object> zset = redistemplate.opsForZSet();
redistemplate.opsForValue();
return zset.rangeByscore(key, scoure, scoure1);
}
//第一次加载的时候将数据加载到redis中
public void saveDataToRedis(String name) {
double index = Math.abs(name.hashCode() % size);
long indexLong = new Double(index).longValue();
boolean availableusers = setBit("availableusers", indexLong, true);
}
//第一次加载的时候将数据加载到redis中
public boolean getDataToRedis(String name) {
double index = Math.abs(name.hashCode() % size);
long indexLong = new Double(index).longValue();
return getBit("availableusers", indexLong);
}
/**
* 有序集合获取排名
* @param key 集合名称
* @param value 值
*/
public Long zRank(String key, Object value) {
ZSetoperations<String, Object> zset = redistemplate.opsForZSet();
return zset.rank(key,value);
}
/**
* 有序集合获取排名
* @param key
*/
public Set<ZSetoperations.TypedTuple<Object>> zRankWithscore(String key, long start,long end) {
ZSetoperations<String, Object> zset = redistemplate.opsForZSet();
Set<ZSetoperations.TypedTuple<Object>> ret = zset.rangeWithscores(key,start,end);
return ret;
}
/**
* 有序集合添加
* @param key
* @param value
*/
public Double zSetscore(String key, Object value) {
ZSetoperations<String, Object> zset = redistemplate.opsForZSet();
return zset.score(key,value);
}
/**
* 有序集合添加分数
* @param key
* @param value
* @param scoure
*/
public void incrementscore(String key, Object value, double scoure) {
ZSetoperations<String, Object> zset = redistemplate.opsForZSet();
zset.incrementscore(key, value, scoure);
}
/**
* 有序集合获取排名
* @param key
*/
public Set<ZSetoperations.TypedTuple<Object>> reverseZRankWithscore(String key, long start,long end) {
ZSetoperations<String, Object> zset = redistemplate.opsForZSet();
Set<ZSetoperations.TypedTuple<Object>> ret = zset.reverseRangeByscoreWithscores(key,start,end);
return ret;
}
/**
* 有序集合获取排名
* @param key
*/
public Set<ZSetoperations.TypedTuple<Object>> reverseZRankWithRank(String key, long start, long end) {
ZSetoperations<String, Object> zset = redistemplate.opsForZSet();
Set<ZSetoperations.TypedTuple<Object>> ret = zset.reverseRangeWithscores(key, start, end);
return ret;
}
}
14.4.2、测试
@SpringBoottest
class Springboot11RedisApplicationTests {
// Redis工具类,方便我们之间调用redis,简化操作,不直接使用原生方法
@Autowired
private RedisUtils redisUtils;
@Test
public void test1() {
User user = new User("张三", 13);
//使用redis工具类
redisUtils.set("test", user);
System.out.println(redisUtils.get("test"));
}
}
END
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 [email protected] 举报,一经查实,本站将立刻删除。