SpringData Redis
Spring Data Redis 是 Spring Data 项目的一部分,它为 Java 应用程序提供了一种便捷的方式来与 Redis 数据库进行交互。
Spring Data Redis 提供了对 Redis 的抽象封装,使得开发者能够以面向对象的方式操作 Redis,并简化了 Redis 在 Spring 管理的应用中的集成工作。
其主要特性包括:
- 自动配置:在使用 Spring Boot 时,通过引入
spring-boot-starter-data-redis
启动器,可以快速实现自动配置和连接到 Redis 服务器。 - 模板类:提供了
RedisTemplate
类,这是一个通用的 Redis 操作类,用于执行 Redis 命令以及转换键值对的序列化和反序列化过程。 - Repository 支持:类似于 Spring Data JPA,Spring Data Redis 也支持自定义 Repository 接口,通过继承
CrudRepository
、PagingAndSortingRepository
或自定义方法来简化 CRUD 操作。 - 数据绑定:可以通过注解或元数据映射将 Java 对象与 Redis 中的数据结构(例如 Hash)关联起来,简化复杂类型的操作。
- 事务管理:支持 Redis 事务处理,可以通过编程式或者声明式事务管理来保证数据的一致性。
- 发布订阅(Pub/Sub):提供了对 Redis 发布/订阅功能的支持,方便构建消息驱动的系统。
- 缓存支持:结合 Spring Cache Abstraction,可以利用 Redis 作为分布式缓存解决方案
Spring Data Redis 提供的两个核心API:RedisTemplate 模板类 和 CrudRepository 持久化接口
下面先来介绍 Spring Data Redis 中的 RedisTemplate 的具体用法
一、配置pom.xml
首先创建springboot项目
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
<exclusions>
<exclusion>
<groupId>org.junit.vintage</groupId>
<artifactId>junit-vintage-engine</artifactId>
</exclusion>
</exclusions>
</dependency>
</dependencies>
二、配置 application
spring.redis.host=127.0.0.1
spring.redis.port=6379
spring.redis.password=123456
spring.redis.database=1 # 0~15 默认0
三、DAO RedisTemplate依赖
@Autowired
private RedisTemplate redisTemplate;
public void set(Student student){
//保存基本信息 String 注意:不能使用相同的 name 去redis客户端取值的。
redisTemplate.opsForValue().set("name",student.getName());
}
public void get(String key){
String name = redisTemplate.opsForValue().get("name").toString();
System.out.println(name);
}
四、测试
@SpringBootTest
class DemoApplicationTests {
@Autowired
private StudentDao studentDao;
@Test
void set() {
Student student = new Student();
student.setName("AAAAAAAAAAABBBBBBBBBBB");
studentDao.set(student);
}
@Test
void get(){
studentDao.get(null);
}
}
就此,来测试是否连通 redis 。保存和取值 String 进行测试。
五、保存一个对象
1. 实体类,实现序列化接口
@Data
public class Student implements Serializable {
private String name;
private int age;
}
2.编写DAO
public void set(Student student){
redisTemplate.opsForValue().set("student",student); //存储对象
}
public Student get(String key){
return (Student) redisTemplate.opsForValue().get(key);
}
六、list 类型操作
public void pushlist(){
//获取操作list类型的 工具类
ListOperations<String,String> listOperations = redisTemplate.opsForList();
listOperations.leftPush("words","Sky");
listOperations.leftPush("words","Desk");
listOperations.leftPush("words","Person"); //添加队头
listOperations.rightPush("words","Apple"); //追加队尾
}
public void rangeList(){
ListOperations<String,String> listOperations = redisTemplate.opsForList();
List<String> list = listOperations.range("words", 0, Integer.MAX_VALUE);
System.out.println(list);
}
七、set 类型
public void setadd(){
SetOperations setOperations = redisTemplate.opsForSet();
setOperations.add("myset","A","B","C");
setOperations.add("myset","X","Y","C");
}
public void setmembers(){
SetOperations setOperations = redisTemplate.opsForSet();
Set myset = setOperations.members("myset");
System.out.println(myset);
}
八、zset 类型
public void zsetadd(){
ZSetOperations zSetOperations = redisTemplate.opsForZSet();
//第三个为score 排序依据分数 权重
zSetOperations.add("zset","CCC",5);
zSetOperations.add("zset","DDD",3);
zSetOperations.add("zset","AAA",1);
zSetOperations.add("zset","EEE",2);
zSetOperations.add("zset","BBB",4);
}
public void zsetget(){
ZSetOperations zSetOperations = redisTemplate.opsForZSet();
Set zset = zSetOperations.range("zset", 0, 100);
System.out.println(zset);
}
九、hash 类型
public void hashadd(){
HashOperations hashOperations = redisTemplate.opsForHash();
hashOperations.put("person","sid","1001");
hashOperations.put("person","age","23");
Map<String,String> map = new HashMap<>();
map.put("name","诸葛亮");
map.put("email","zhuge@sina.com");
hashOperations.putAll("person",map);
}
public void hashget(){
HashOperations<String,String,String> hashOperations = redisTemplate.opsForHash();
Map<String,String> map = hashOperations.entries("person");
System.out.println(map);
}
十、序列化乱码问题
使用 RedisTemplate 存取redis的数据时,因为序列化原因,存入的数据看上去乱码,不是原本设置的key。 但是不影响应用程序的存取。但是直接操作redis 查看还是不太方便。下面来解决这个问题
1. 添加 jackson 依赖
因为下面的配置类需要依赖json
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
<version>2.11.0</version>
</dependency>
2. 编写配置类
package com.example.demo;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.serializer.GenericJackson2JsonRedisSerializer;
import org.springframework.data.redis.serializer.StringRedisSerializer;
@Configuration
public class Config {
@Autowired
private RedisTemplate redisTemplate;
@Bean
public RedisTemplate redisTemplateInit() {
//设置序列化Key的实例化对象
redisTemplate.setKeySerializer(new StringRedisSerializer());
//设置序列化Value的实例化对象
redisTemplate.setValueSerializer(new GenericJackson2JsonRedisSerializer());
return redisTemplate;
}
}
再次运行保存
public void set(Student student){
// redisTemplate.opsForValue().set("name",student.getName());
redisTemplate.opsForValue().set("student",student); //存储对象
}
在redis 中就可以看到和使用 student 作为 key 来查看数据了。