Redis 的 Java 客户端的详细介绍(Jedis,SpringDataRedis,RedisTemplated,StringRedisTemplated)
5. Java客户端
5.1 简介
Java的Redis客户端(如Jedis、Lettuce)通过封装Redis协议,允许Java应用与Redis服务器交互。它们提供直观的API执行数据操作,支持连接池、集群、哨兵等部署模式。其中Jedis轻量高效但线程不安全,需配合连接池使用;Lettuce基于Netty实现异步与线程安全;Redisson专注分布式服务。开发者可根据性能、线程模型和功能需求灵活选用。

5.2 Jedis
5.2.1 简介
Jedis 是一款轻量级、同步阻塞的 Java Redis 客户端,通过直连模式与 Redis 服务器通信。其 API 直接映射 Redis 原生命令(如
set()对应SET指令),学习成本低且稳定性强;但原生线程不安全(多线程需依赖连接池),适用于并发要求不高的传统项目或小型应用,是 Java 生态中最经典的 Redis 集成方案之一。
5.2.2 特点
-
优点:
Jedis 设计小巧,实现简洁,稳定性高。其最大优势在于 API 与 Redis 原生命令高度一致:方法名和参数直接对应官方文档指令。这使得开发者遇到不熟悉的操作时,无需额外学习客户端封装,直接查阅 Redis 命令文档即可快速上手,显著降低了学习成本。相比之下,某些客户端重命名 API 的做法虽意图简化,实则增加了额外的记忆负担。 -
缺点:
Jedis 采用直连模式且非线程安全。其核心问题在于:单个Jedis实例内的RedisOutputStream(写流) 和RedisInputStream(读流) 是共享的全局资源。当多个线程并发操作同一实例时,会争抢这些流资源,导致读写数据混乱(如数据错位、混合),而非 Redis 服务本身的数据安全问题。
5.2.3 Jedis 的使用
- 引用依赖
<dependency>
<groupId>redis.clients</groupId>
<artifactId>jedis</artifactId>
<version>3.7.0</version>
</dependency>
- 建立连接
private Jedis jedis;
@Before // 该注解,表示在所有你创键的测试方法前先执行,这里用于建立连接
public void setUp() throws Exception {
jedis = new Jedis("192.168.195.132", 6379); //建立连接
jedis.auth("123456"); //密码
jedis.select(0); //选择库
}
- 使用 Jedis
@Test
public void testString() {
//命令名和 Redis 的一致
String s = jedis.set("name", "tom");
String name = jedis.get("name");
}
- 释放资源
@After // 该注解,表示在所有你创键的测试方法后执行,这里用于关闭连接
public void tearDown() throws Exception {
// 如果在建立连接的时候抛出了异常,那么运行到这的时就会有空指针异常的风险
if(jedis != null) {
jedis.close();
}
}
5.2.4 Jedis连接池
Jedis本身是线程不安全的,并且频繁的创建和销毁连接会有性能损耗。所以建议使用 Jedis 的连接池来代替 Jedis的直连方式。
public class JedisConnectionFactory {
private static JedisPool jedisPool;
static {
//配置连接池
JedisPoolConfig poolConfig = new JedisPoolConfig();
//最大连接量,表示最多建立8个连接
poolConfig.setMaxTotal(8);
//最大空闲连接,表示即便没有线程访问我这个池子,也会最多预备8个连接
poolConfig.setMaxIdle(8);
//最小空闲连接,表示空闲连接存放一段时间后,会被自动释放,直到预备连接小于等于2个
poolConfig.setMinIdle(2);
//最长等待时间,表示当连接池内没有空闲连接时,线程对多等多久后放弃等待
poolConfig.setMaxWaitMillis(1000);
//建立连接
jedisPool = new JedisPool(poolConfig,
"192.168.195.132", 6379, 1000, "123456");
}
// 获取连接
public static Jedis getJedis() {
return jedisPool.getResource();
}
}
5.3 SpringDataRedis
5.3.1 简介
- Spring Data Redis 是 Spring 生态的 Redis 集成框架,内部整合来 Jedis 和 Lettuce。
- 提供了
RedisTemplate统一 API 来操作 Redis。- 简化数据操作(自动处理序列化/连接管理)
- 支持事务、发布订阅、集群与哨兵模式,并天然适配 Spring 事务管理,显著降低 Java 应用访问 Redis 的复杂度,适用于需与 Spring 深度整合的中大型项目。

5.3.2 SpringDataRedis的使用
**SpringBoot 已经整合 SpringDataRedis,并且实现了自动装配,使用起来非常方便,**所以下面我们基于SpringBoot 来使用 SpringDataRedis
- 引入依赖
<!--redis起步依赖-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>
<!--连接池依赖-->
<!--无论是 Jedis 还是 Luttce,都是基于 commons-pool 来实现连接池的效果 -->
<dependency>
<groupId>org.apache.commons</groupId>
<artifactId>commons-pool2</artifactId>
</dependency>
- 连接和连接池配置
spring:
data:
redis:
host: 192.168.195.132 #连接的虚拟机的 IP 地址
port: 6379 #端口号
database: 0 #连接的数据库
password: 123456 #密码
lettuce:
pool: #连接池的配置
max-active: 8 #最大连接数
max-idle: 8 #最大空闲连接数
min-idle: 0 #最小空闲连接数
max-wait: 100ms #最大等待时间
#具体解释可以看 Jedis 配置连接池那一节
- 测试代码
@SpringBootTest
class RedisDemoApplicationTests {
@Autowired
private RedisTemplate redisTemplate;
@Test
void stringTest() {
redisTemplate.opsForValue().set("name", "虎哥");
Object name = redisTemplate.opsForValue().get("name");
System.out.println(name);
}
}
5.3.3 RedisTemplated的缺点
RedisTemplate 可以存储任意类型的数据,原因是在存储之前会先把存储的数据序列化字节形式,默认采用的 JDK 序列化。但是得到的结果,可读性差,并且占用了更多的内存

5.3.3 解决方式
RedisTemplate 的缺点产生原因在于他默认的序列化方式不太合适,所以我们可以更改他的序列化方式即可解决这个问题。

存在的小问题以及解决办法
- 但是这种方式还是存在一点点问题就是,他 Value 使用的是 Json 序列化器,当存入和获取的数据类型是对象是会自动序列化和反序列化,但是要实现自动反序列化,存入 Redis 的数据数据需要加一段额外的信息来记录该 Json 数据属于哪个对象,这样就造成了,内存的额外开销。
- 解决方式也很简单,就是再一次跟换 Value 的序列化方式,采用和 Key 一样的 String 序列化器,但是后果就是,存入数据类型只能是 String 类型。但是没关系,只要当我们要存入对象时,就先将他转为 Json 字符串格式
- 但是幸运的是我们不要自己再去修改,RedisTemplate 的 Value 的序列化方式了。这个别人已经写好了。Spring 提供了一个 StringRedisTemplate 类,他的 Key 和 Value 默认的序列化方式就是 String 序列化,省去了我们自己定义 RedisTemplate。

5.3.4 StringRedisTemplate
5.3.4.1 简介
为了节省空间我们并不会使用 Json 的序列化器来处理 value,而是统一的使用 String 的序列化器,要求只能存储String 类型的 key 和 value。当需要存储 Java 对象的时候,需手动完成对象序列化和反序列化。

5.3.4.2 使用步骤
至于序列化工具,使用自己喜欢的就好,我这里使用的 FastJson
- 导入依赖
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>fastjson</artifactId>
<version>1.2.7</version>
</dependency>
- 代码演示
@Autowired
private StringRedisTemplate stringRedisTemplate;
@Test
void objectTest() {
User user = new User("name", "虎哥");
//手动序列化(object -> Json)
String s = JSON.toJSONString(user);
stringRedisTemplate.opsForValue().set("user:100", s);
String s1 = stringRedisTemplate.opsForValue().get("user:100");
//手动反序列化(Json -> object)
User user1 = JSON.parseObject(s1, User.class);
System.out.println(user1);
}
更多推荐
所有评论(0)