Intro to Jedis Part 2

Intro to Jedis Part 2

Transactions:

Transactions guarantee atomicity and thread safety operations, which means that requests
from other clients will never be handled concurrently during Redis transactions:
String friendsPrefix = “friends#”;
String userOneId = “4352523”;
String userTwoId = “5552321”;

Transaction t = jedis.multi();
t.sadd(friendsPrefix + userOneId, userTwoId);
t.sadd(friendsPrefix + userTwoId, userOneId);
t.exec();

You can even make a transaction success dependent on a specific key
by “watching” it right before you instantiate your Transaction:

Pipelining:

When we have to send multiple commands, we can pack them together in one request and save connection overhead by using pipelines,
it is essentially a network optimization. As long as the operations are mutually independent, we can take advantage of this technique:
String userOneId = “4352523”;
String userTwoId = “4849888”;

Pipeline p = jedis.pipelined();
p.sadd(“searched#” + userOneId, “paris”);
p.zadd(“ranking”, 126, userOneId);
p.zadd(“ranking”, 325, userTwoId);
ResponsepipeExists = p.sismember(“searched#” + userOneId, “paris”);
Response<Set> pipeRanking = p.zrange(“ranking”, 0, -1);
p.sync();

String exists = pipeExists.get();
Setranking = pipeRanking.get();

Notice we do not get direct access to the command responses, instead, we’re given a Response instance
from which we can request the underlying response after the pipeline has been synced.

Publish/Subscribe:

*Subscriber
Subscribe and listen to messages sent to a channel:

Jedis jSubscriber = new Jedis();
jSubscriber.subscribe(new JedisPubSub() {
@Override
public void onMessage(String channel, String message) {
// handle message
}
}, “channel”);

*Publisher
Then simply send messages to that same channel from the publisher’s thread:

Jedis jPublisher = new Jedis();
jPublisher.publish(“channel”, “test message”);

Connection Pooling:

A pool that is thread safe and reliable as long as you return the resource to the pool when you are done with it.
Let’s create the JedisPool:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
final JedisPoolConfig poolConfig = buildPoolConfig();
JedisPool jedisPool = new JedisPool(poolConfig, "localhost");

private JedisPoolConfig buildPoolConfig() {
final JedisPoolConfig poolConfig = new JedisPoolConfig();
poolConfig.setMaxTotal(128);
poolConfig.setMaxIdle(128);
poolConfig.setMinIdle(16);
poolConfig.setTestOnBorrow(true);
poolConfig.setTestOnReturn(true);
poolConfig.setTestWhileIdle(true);
poolConfig.setMinEvictableIdleTimeMillis(Duration.ofSeconds(60).toMillis());
poolConfig.setTimeBetweenEvictionRunsMillis(Duration.ofSeconds(30).toMillis());
poolConfig.setNumTestsPerEvictionRun(3);
poolConfig.setBlockWhenExhausted(true);
return poolConfig;
}

Now we can make use of our pool from anywhere in the application when needed:

1
2
3
try (Jedis jedis = jedisPool.getResource()) {
// do operations with jedis resource
}

We used the Java try-with-resources statement to avoid having to manually close the Jedis resource,
but if you cannot use this statement you can also close the resource manually in the finally clause.