Redis第2讲——Java三种客户端(Jedis、Lettuce和Redisson)
全文30053字(大部分是代码案例)
hello,球友们早上好,今天介绍一下Java的三种客户端——Jedis、Lettuce和Redisson。这个相比于Redis其它知识的重要性感觉还差那么一点,但项目中会用到的。目录如下:

原文链接:Redis第2讲——Java三种客户端(Jedis、Lettuce和Redisson)
正文开始。。。。
上篇文章介绍了Redis的9种数据类型和常命令、7种数据结构和9种编码方式。但是如果想要把它应用到项目中,我们还需要一个redis的客户端。redis的Java客户端种类还是很多的,其中使用最广泛的有三种——Jedis、lettuce和redisson,下面我们一起来学习下。
一、Redis客户端简介
介绍之前我们先来了解一下什么是客户端。客户端——即真正的使用者,比如进入redis命令操作有一个redis-cli,这其实就是redis提供的一个基于操作系统(linux、windows)的客户端,此时的使用者是电脑,电脑通过这个客户端可以连接redis并操作redis。同理,在java中如果想要要操作redis同样需要客户端来与redis建立连接。
基于redis开放的通信协议,大神们纷纷开发出了各种语言的redis客户端,包括C、C++、C#、D、java、Python、Ruby等50多种,这些客户端都是基于redis命令做了一层封装,并打包成工具,以便更方便地操作redis。
在java语言里redis官方最推荐的便是jedis、lettuce和redisson,如下图。

二、Jedis
2.1 简介
Jedis是redis老牌的Java客户端,它把Redis的所有命令封装成了Java可直接调用的方法,但它并没有替我们封装一些基于redis的特殊功能,比如分布式锁等。
官方网址:GitHub - redis/jedis: Redis Java client
2.2 基本使用
2.2.1 导入依赖
2.2.2 建立连接
Jedis实例连接redis
对于Jedis而言,一旦连接上了redis服务器,剩下的操作就非常容易了,因为Jedis提供的API和redis的命令基本相同,比如get命令Jedis里面也是get,set对应set...
不过我们通常不用这种方式连接redis,而是用连接池,因为在多线程共享一个Jedis实例是线程不安全的。这里并不是说redis处理数据不安全,而是Jedis向reids推数据和获取数据不安全。在单个Jedis实例中有RedisInputStream和RedisOutPutStream两个成员变量,发送命令和获取返回值都是使用这两个变量,显然这很容易发生并发问题。

既然多个线程使用一个实例就会产生问题,那我们就给每个线程分配一个Jedis实例,让他们单独取操作自己的数据,这里就得使用JedisPool线程池来实现了,在使用过程中,我们通常会封装一个工具类:

2.2.3 操作redis
本次就演示String数据类型的操作。
测试结果:

2.3 集群配置
redis通常是通过集群配置,来保证服务的高可用。常用的搭建的方式有2种:
- 哨兵模式:在主从复制的基础上,增加一个节点对redis服务进行监控,如果master宕机,就从slave节点选一个作为master,实现自动切换。
- Cluster模式:将数据进行分片存储,避免全部节点数据一样,浪费空间。
ps:这里就简单介绍一下,后续会专门有一篇介绍redis集群的文章。
2.3.1 哨兵模式
哨兵模式简单来说就是一台主机、一台或多台备机、外加一台监控节点(哨兵节点),当主机宕机,监控节点就会将备用节点自动切换成主机,以便继续提供服务。

2.3.2 Cluster集群配置
Cluster模式是一种高级集群模式,它通过数据分片和分布式存储实现了负载均衡和高可用。在Cluster模式下,redis将所有键值对数据分散在多个节点上。每个节点负责一部分数据(slot槽),简而言之,Cluster模式突破了单节点的内存限制,实现了更大规模的数据存储。

2.4 byte[]方式操作
使用的时候不难发现,除了String方式,还支持byte[]方式操作。Spring提供了序列化byte[]的操作
- 导入依赖
- 测试

2.5 Jedis管道操作
Redis更多的使用来做缓存。
应当在项目启动时,就从传统的MySQL、Oracle数据库中将作为缓存的数据查询出来并且同步到Redis服务中。
可能需要在项目启动时,将数10W甚至上百万的数据同步到Redis中,会在客户端和Redis服务交互时,网络传输数据所带来的性能损耗是很大的,采用管道来解决这个问题。
管道可以实现将大量的请求任务在客户端封装好,一次性的发送给Redis服务,从而减少网络请求带来的损耗
- 现测试不用管道存储10w条数据(测试4.06秒)
- 采用管道(测试0.64秒)
2.6 优缺点
优点:
- Jedis 提供了简单直观的API,它的API与Redis命令一一对应,易于学习和使用。
- Jedis 客户端使用高性能的连接池,支持连接复用,可有效地减少频繁创建和关闭连接对性能的影响。同时支持 pipelining 等批量操作,能够有效地提升 Redis 的性能,减少网络开销。并且使用高效的序列化机制(如使用对象池和二进制序列化)来提供快速的数据访问和传输。
- Jedis 客户端提供了对 Redis Cluster(Redis 集群)的支持,可以轻松地与 Redis 集群进行交互、自动故障转移和负载均衡。
缺点:
- Jedis 客户端的使用方式相对简单,只提供了一些基本的接口方法,如果需要实现自己的功能,需要自己重写或者拓展 Jedis 客户端。
- Jedis 客户端实例不是线程安全的,需要借助连接池来管理和使用 Jedis。
- 使用阻塞的I/O,且其方法调用都是同步的,程序流需要等到 sockets 处理完 I/O 才能执行,不支持异步
三、Lettuce
3.1 简介
Lettuce是一个高级redis客户端,支持高级的redis特性,比如Sentinel、集群、流水线、自动重新连接和redis数据模型等。目前已成为SpringBoot 2.0版本默认的redis客户端。
相比于Jedis,lettuce不仅功能丰富,而且提供了很多新的功能特性,比如异步操作、响应式编程等,同时还解决了Jedis线程不安全的问题。
3.2 基本使用
3.2.1 导入依赖

3.2.2 建立连接
Lettuce连接设计的时候,就是线程安全的,所以一个连接可以被多个线程共享,同时lettuce连接默认是自动重连的,使用单连接基本可以满足业务需求,大多数情况下不需要配置线程池,多连接并不会给操作带来性能上的提升。
工具类:
测试:
3.2.3 操作redis
其实和Jedis操作大差不差,这里就不纠结了:
3.2.4 响应式编程
Lettuce引入响应式编程框架时Project Reactor,通过使用Lettuce的响应式API,可以以流式方式处理redis:
运行结果:
3.2.5 发布订阅
测试结果:
3.3 集群配置
3.3.1 主从模式
Lettuce支持自动发现主从模式下的节点信息,然后保存到本地,具体如下:
3.3.2 哨兵模式
3.3.3 Cluster模式
3.4 优缺点
优点:
- 异步和非阻塞:Lettuce 客户端使用异步和非阻塞的方式与 Redis 交互,可以处理并行的请求和高并发的场景,提供更高的吞吐量和响应速度。
- 响应式编程模型:Lettuce 客户端支持 Reactive 编程模型,可以通过使用 Reactive Streams、Flux 或 Mono 这样的响应式类型来处理异步操作和流式数据处理。
- 完整的特性支持:Lettuce 客户端支持 Redis 的所有高级特性,如事务、流水线操作、发布/订阅、Lua 脚本等,可以满足复杂的应用需求。
- 集群支持:Lettuce 客户端提供了对 Redis Cluster 的支持,可以轻松地与 Redis 集群进行交互,并进行自动的故障转移和节点发现。
- 可扩展性:Lettuce 客户端使用模块化的设计,可以通过插件机制进行功能扩展,可以根据需求选择所需的模块,减小依赖的大小。
缺点:
- 和其他 Redis 客户端相比,Lettuce 的使用可能稍微复杂,需要更多的学习和了解。
四、Redisson
Redis官方置顶推荐的Java客户端Redisson。
4.1 简介
Redisson是架设再redis基础上的一个Java驻内存数据网格(In-Memory Data Grid)。它不仅将原生的redis Hash、List、Set、String等数据结构封装为Java里大家熟悉的Map、List、Set、Object Bukcket等数结构,并在此基础上还提供了许多分布式服务,比如分布式锁、分布式对象、分布式集合、分布式调度任务等。
相比于Jedis、Lettuce等基于redis基础命令封装的客户端,Redisson提供的功能更加高端和抽象。
4.2 基本使用
4.2.1 导入依赖
4.2.2 建立连接
单机模式连接如下:
当然也可以用配置文件的方式:
测试连接:
4.2.3 操作redis
下面我们介绍一下5中基本类型的操作:
运行结果:
4.2.4 布隆过滤器
布隆过滤器是由布隆在1970年提出的。它实际上是一个很长的二进制向量和一系列的随机映射函数(哈希函数)两部分组成的结构,用于快速检索一个元素是否可能存在于一个集合(bit数组中)。
实现方式有很多,比如Guava、Apache Commons、Jedis和Redisson等,我们今天就介绍一下Redisson的实现方式:
4.2.5 分布式锁
Redisson最大的亮点,也是使用最多的功能,就是分布式锁,使用起来还是挺简单的:
ps:另外,Redisson还支持公平锁、联锁、红锁、读写锁、信号量、闭锁等,后续会专门总结一篇分布式锁的文章。
4.3 集群配置
上面已经简单介绍过了,这次就简单说了。
4.3.1 主从模式
yaml格式:
4.3.2 哨兵模式
yaml格式:
4.3.3 Cluster模式
yaml格式:
4.4 优缺点
优点:
- 实现了分布式特性和可扩展的 Java 数据结构,例如分布式锁,分布式集合,分布式对象,分布式远程调度等等高级功能,适合分布式开发
- 与 Lettuce 一样,基于 Netty 框架的事件驱动与 redis 通信,支持异步调用,性能高
- Redisson 的 API 是线程安全的,所以可以使用单个 Redisson 连接来完成各种操作。
- 支持读写分离,支持读负载均衡,在主从复制和 Redis Cluster 架构下都可以使用
- 内建 Tomcat Session Manager,为 Tomcat 6/7/8 提供了会话共享功能,可以与 Spring Session 集成,实现基于 Redis 的会话共享
- 相比于 Jedis、Lettuce 等基于 redis 命令封装的客户端,Redisson 提供的功能更加高端和抽象,Redisson 可以类比 Spring 框架,这些框架搭建了应用程序的基础框架和功能,可以显著提升开发效率,让开发者有更多的时间来关注业务逻辑
缺点:
- 和 Jedis、Lettuce 客户端相比,功能较为简单,对字符串的支持比较差,不支持排序、事务、管道、分区等 Redis 特性
- API 更加抽象,学习使用成本高
End:希望对大家有所帮助,如果有纰漏或者更好的想法,请您一定不要吝啬你的赐教🙋。
