Redis-java客户端

开启远程连接#

Linux 更改设置

shutdown

exit

把 bind:127.0.0.1 注释掉

requirepass password 设置密码

开启服务:

Copy
redis-server redis.conf

redis-cli -a password

Jedis#

创建一个普通的 maven 项目

项目创建成功后添加 jedis 依赖:

Copy
<dependency> <groupId>redis.clients</groupId> <artifactId>jedis</artifactId> <version>3.3.0</version> </dependency>

创建一个测试方法

Copy
public class MyJedis { public static void main(String[] args) { //1. 构建一个 jedis 对象,默认端口 6379 Jedis jedis = new Jedis("127.0.0.1"); //2. 密码认证 jedis.auth("root"); //3. 测试是否连接成功 String ping = jedis.ping(); //4. 返回 pong 表示连接成功 System.out.println(ping);
}

}

Jedis, 方法中的 API 和 Redis 命令高度一致

连接池#

由于 redis 不是线程安全的,所以我们使用 redis 对象时,用连接池来使用 redis

Copy
public class MyRedisPoolTest { public static void main(String[] args) { // 构建一个连接池 JedisPool pool = new JedisPool("127.0.0.1",6379); // 从连接池获取一个 Jedis 连接 Jedis jedis = pool.getResource(); try { jedis.auth("root"); //Jedis 操作 String ping = jedis.ping(); System.out.println(ping); } finally { // 归还连接 if(jedis!=null){ jedis.close(); } } } }

利用 jdk1.7 try-with-resource 特性,可以改造

Copy
public class MyRedisPoolTest { public static void main(String[] args) { // 构建一个连接池 JedisPool pool = new JedisPool("127.0.0.1",6379); try(Jedis jedis = pool.getResource();) { jedis.auth("root"); //Jedis 操作 String ping = jedis.ping(); System.out.println(ping); } } }

由于 redis 不是线程安全的,所以我们使用 redis 对象时,用连接池来使用 redis

但是上面代码无法实现强约束,可以进一步做出改进

Copy
public interface CallwithJedis { void call(Jedis jedis); }

public class Redis {
private JedisPool pool;

<span class="hljs-keyword">public</span> <span class="hljs-title function_">Redis</span><span class="hljs-params">()</span>{
    <span class="hljs-type">GenericObjectPoolConfig</span> <span class="hljs-variable">config</span> <span class="hljs-operator">=</span> <span class="hljs-keyword">new</span> <span class="hljs-title class_">GenericObjectPoolConfig</span>();
    <span class="hljs-comment">//连接池最大休闲数</span>
    config.setMaxIdle(<span class="hljs-number">300</span>);
    <span class="hljs-comment">//最大连接数</span>
    config.setMaxTotal(<span class="hljs-number">1000</span>);
    <span class="hljs-comment">//连接最大等待时间,如果是-1,表示没有限制</span>
    config.setMaxWaitMillis(<span class="hljs-number">30000</span>);
    <span class="hljs-comment">//在休闲时检查有效性</span>
    config.setTestOnBorrow(<span class="hljs-literal">true</span>);
    pool=<span class="hljs-keyword">new</span> <span class="hljs-title class_">JedisPool</span>(config,<span class="hljs-string">"192.168.91.128"</span>,<span class="hljs-number">6379</span>,<span class="hljs-number">30000</span>,<span class="hljs-string">"javaboy"</span>);

}
<span class="hljs-keyword">public</span> <span class="hljs-keyword">void</span> <span class="hljs-title function_">execute</span><span class="hljs-params">(CallwithJedis callwithJedis)</span>{
    <span class="hljs-keyword">try</span>(<span class="hljs-type">Jedis</span> <span class="hljs-variable">jedis</span> <span class="hljs-operator">=</span> pool.getResource()){
        callwithJedis.call(jedis);
    }
}

}

Redis redis = new Redis();
redis.execute(jedis -> {
System.out.println(jedis.ping());
});

Lettuce#

Lettuce 和 Jedis 的一个比较

1.jedis 在实现过程中是直接连接 Redis 的,在多个线程之间共享一个 Jedis 实例,这是线程不安全的,如果想要在多线程下使用 Jedis, 就得使用连接池,这样,每个线程都有自己的 Jedis 实例。

2.Lettue 基于目前很火的 Netty NIO 框架来构建,所以克服了 Jedis 中线程不安全的情况,Lettuce 支持同步,异步,以及响应式调用,多个线程可以共享一个连接实例。

添加依赖:

Copy
<dependency> <groupId>io.lettuce</groupId> <artifactId>lettuce-core</artifactId> <version>5.3.1.RELEASE</version> </dependency>

public class LettuceTest {
public static void main(String[] args) {
RedisClient redisClient = RedisClient.create("redis://root@127.0.0.1");
StatefulRedisConnection<String, String> connect =redisClient.connect();
RedisCommands<String, String> async = connect.sync();
async.set("name", "javaboy");
String name = async.get("name");
System.out.println(name);
}
}