Valkey GLIDE to Redisson Migration Guide

Published on
July 1, 2026

Since it emerged as an open source, drop-in replacement for the popular in-memory data store Redis, Valkey has become a cornerstone of many enterprise architectures. To help increase adoption, the project also shipped the Valkey GLIDE (General Language Independent Driver for Enterprise) client for Java developers. As with Redis Java clients such as Jedis or Lettuce, Valkey GLIDE is a fast, reliable tool for sending raw commands to a server and retrieving stored data.

However, as enterprise applications scale, development teams often find that sticking with Valkey GLIDE can lead to a lot of extra work. The limitation of only being able to send commands to a Valkey server leads them to write custom Lua synchronization scripts and build custom caching solutions. At a certain point, the development team is no longer just coding application logic; they're building their own client frameworks from scratch. The open source Valkey/Redis Java client Redisson and its commercial version, Redisson PRO, wrap Valkey's features in custom objects and add advanced messaging features that let developers get back to coding.

While GLIDE is a lean, command-oriented client, Redisson transforms your Valkey deployment into a robust distributed data platform by providing familiar, thread-safe Java objects. Here is a complete migration guide that details everything you need to transition from Valkey GLIDE to Redisson.

Signs You've Outgrown Valkey GLIDE

How do you know if you really need to transition from GLIDE to Redisson? If you or your Java developers have run into any of the issues below, you've outgrown GLIDE:

  • You're manually managing distributed locks or synchronization primitives — reentrant locks, fair locks, read/write locks, semaphores, countdown latches — using only basic Valkey commands.
  • Your application requires ultra-low-latency reads and local caching (near-cache) to prevent unnecessary network round-trips to the Valkey cluster.
  • Your architecture is built on enterprise frameworks like Spring, Spring Boot, Hibernate, Quarkus, or Micronaut, and you need your apps to integrate with their native caching and session management features.
  • Your engineering team prefers working with idiomatic Java collections (Map, List, Set, Queue) and asynchronous, reactive, or RxJava streams over raw commands.

What Redisson Gives You (That GLIDE Leaves to You)

Valkey's documentation provides guidance for migrating from Redisson to GLIDE. However, when that guide points out the differences between the two Java clients, it actually lists the reasons a developer would want to migrate to Redisson. Here's a look at what you get by switching to Redisson, features you would have to manually implement and maintain yourself with GLIDE:

Distributed Locks and Concurrency Primitives

Valkey GLIDE features no native distributed lock primitives, leaving concurrency control up to you. In contrast, Redisson provides a thread-safe implementation of the java.util.concurrent.locks.Lock interface across a distributed cluster:

RLock lock = redisson.getLock("order:1234");
lock.lock();
try {
    // critical section, safe across every node in the cluster
} finally {
    lock.unlock();
}

Behind the scenes of the RLock API is a transparent "watchdog" mechanism. This background task automatically extends the lease time of the distributed lock while the holding thread remains active. The default lease timeout is 30 seconds (configurable via the lockWatchdogTimeout parameter). This mechanism prevents long-running operations from dropping locks prematurely, while ensuring that crashed or disconnected lock holders release their claims gracefully without inducing permanent deadlocks.

In addition, Redisson supports various concurrency models, including fair locks, multi-locks, read/write locks, fenced locks, spin locks, semaphores, permit-expirable semaphores, and countdown latches. Each is fully supported across synchronous, asynchronous, reactive, and RxJava execution paths. To replicate this safety in GLIDE, an engineer would need to hand-craft a complex web of SET key value NX PX commands, maintain secondary background threads for lease renewals, and develop custom Lua scripts to guarantee safe lock releases.

Near-Caching for Low-Latency Performance

Even with today's faster networks, latency remains the ultimate bottleneck in high-throughput distributed systems. Redisson solves this with its RLocalCachedMap abstraction, which caches frequently accessed map entries directly in the application client's JVM memory. This setup allows hot-key reads to bypass the network entirely. Vendor benchmarks indicate that local-cache reads can execute up to 45 times faster than standard remote map lookups.

Developers can configure the following:

  • Invalidation strategies: Options include INVALIDATE (notifying other client instances to purge stale keys), UPDATE (proactively pushing mutations), or NONE.
  • Eviction policies: Redisson has built-in support for Least Frequently Used (LFU), Least Recently Used (LRU), Soft, or Weak reference handling.
  • Third-party providers: Redisson supports optional backing through high-performance storage engines such as Caffeine.

Ecosystem and Framework Integration

Redisson implements standard Java frameworks, making it a drop-in component for several popular enterprise ecosystems, including:

  • Spring and Spring Boot: Redisson provides a Spring Boot starter, along with implementations for Spring Cache and for annotation-driven caching.
  • Spring Data Redis: The fully compatible RedisConnectionFactory allows you to preserve legacy RedisTemplate configurations during migration to Redisson.
  • Session management: With support for Spring Session and an Apache Tomcat session manager, Redisson facilitates clustered HTTP session persistence.
  • Transaction and spec standards: Redisson natively integrates with Spring Transaction Manager, MyBatis, Hibernate, Quarkus, Micronaut, and JCache (JSR-107).

Advanced Enterprise Distributed Services

Redisson provides these high-level distributed infrastructure engines that have no counterpart in Valkey GLIDE, including a remote procedure call (RPC) service, a Live Object service that maps Java objects to Valkey hashes, an executor service and scheduler for distributed tasks, and a MapReduce service.

In addition, Redisson PRO offers a unique, reliable messaging infrastructure. It includes Reliable Queue, which provides message queues with exactly-once delivery guarantees, custom visibility timeouts, priority tiers, acknowledgment workflows, and dead-letter queues (DLQs). Redisson PRO's Reliable PubSub supports consumer groups and delivery limits, which powers a fully TCK-compliant JMS 2.0 (JSR-343) and Jakarta Messaging provider.

Atomic Operations

To combine multi-command sequences into single round-trip atomic operations with Valkey GLIDE, you have to write and maintain Lua scripts. Redisson accomplishes this via familiar Java methods. For example:

  • put(key, value) atomically updates a key and retrieves its prior value by combining HGET and HSET round-trip.

  • putIfAbsent(key, value) evaluates field existence before executing a write operation, combining HSETNX and conditional HGET logic.

  • fastReplace(key, value) modifies a target field only if it already exists within the remote structure, combining HEXISTS and HSET behaviors.

With GLIDE, each of these becomes two separate calls and two round trips.

When return values are discarded, Redisson's fast* family optimizes performance by dropping back to the single underlying database command. This approach ensures you never incur a network penalty for an unused read payload.

Is Redisson Compatible With Valkey?

For years, Redisson has been known as the premier Redis client for Java developers. Therefore, it's easy to see why some might wonder whether Redisson is compatible with Valkey.

Redisson supports all Valkey deployments from version 7.2.5 through the latest production releases. It works with the valkey:// and secure valkeys:// (TLS) URL schemes in addition to traditional redis:// endpoints. It's also formally listed within the official Valkey project client directory as an approved Java driver.

Newer versions of Redisson include specialized connection managers tailored for Valkey Cluster mode and Valkey Serverless configurations. Redisson also supports your Valkey infrastructure, whether in your server room or in managed cloud deployments like Google Cloud Memorystore for Valkey and Aiven for Valkey.

Valkey GLIDE to Redisson: The Step-by-Step Migration Guide

Switching from GLIDE to Redisson requires a few changes to your Java dependencies and the adoption of new approaches to take advantage of Redisson's advanced capabilities. Here's a step-by-step guide:

Step 1: Update Dependencies

Since GLIDE compiles native binary dependencies down to C, its Maven coordinates require platform-specific classifiers, such as linux-x86_64 or osx-aarch_64. Redisson is pure Java, so you don't have to worry about that.

To update a Maven configuration, remove your existing GLIDE artifacts and integrate the Redisson core library into your pom.xml:

<dependency>
    <groupId>org.redisson</groupId>
    <artifactId>redisson</artifactId>
    <version>4.6.0</version>
</dependency>

For Gradle, update your build.gradle file by exchanging driver implementations:

implementation 'org.redisson:redisson:4.6.0'

If your app architecture relies on the Spring Boot framework, use the specialized starter package org.redisson:redisson-spring-boot-starter to automatically handle bean wire-ups.

Step 2: Initialization and Connection Lifecycle

Valkey GLIDE is initialized using a declarative builder pattern, which creates an asynchronous client container. Redisson centralizes network, pooling, retry, and thread settings inside a Config object, which is then used to initialize the RedissonClient interface.

To move a single-server connection from GLIDE to Redisson, configure the target network coordinates on the SingleServerConfig object:

Config config = new Config();
config.useSingleServer()
      .setAddress("valkey://127.0.0.1:6379");   // redis:// also works
RedissonClient redisson = Redisson.create(config);

For distributed environments, add your entry node routing rules using Redisson's cluster server configuration:

Config config = new Config();
config.useClusterServers()
      .addNodeAddress("valkey://127.0.0.1:7000",
                      "valkey://127.0.0.1:7001",
                      "valkey://127.0.0.1:7002");
RedissonClient redisson = Redisson.create(config);

Redisson provides support for a wide range of architectures through dedicated methods, including useSentinelServers(), useReplicatedServers(), and useMasterSlaveServers().

To keep environment settings decoupled from your application code, you can bootstrap your connections directly from external configuration templates using Config.fromYAML(...) or matching JSON definitions.

Security policies, access control lists (ACLs), and isolation namespaces are configured directly on the chosen connection manager using .setUsername(...) and .setPassword(...). To handle database indexing in non-clustered environments, provide your targeted index via .setDatabase(int). Finally, when shutting down your application context, replace GLIDE's asynchronous client.close() invocation with a call to redisson.shutdown() to safely terminate open socket channels and drain connection thread pools.

Step 3: Translate Valkey Commands Into Objects

The most critical part of the migration is shifting your data access layer from GLIDE's command-driven futures to Redisson's distributed objects.

GLIDE requires developers to invoke specific command strings and manually handle the resulting CompletableFuture arrays. With Redisson, you use proxy objects that track your data structures directly and offer synchronous methods by default, eliminating the redundancy of asynchronous unpacking in GLIDE.

Strings and Basic Values

In GLIDE, simple value lookups are treated as direct command executions against a key string. In Redisson, you obtain a thread-safe reference to an RBucket container object to read and write the payloads of the underlying objects:

// GLIDE
client.set("user:1", "Ada").get();
String name = client.get("user:1").get();

// Redisson
RBucket bucket = redisson.getBucket("user:1");
bucket.set("Ada");
String name = bucket.get();

Expiration Controls and Conditional Writes (SETEX / SETNX)

Handling time-to-live (TTL) properties and conditional write patterns in GLIDE requires passing complex configuration options through command parameter builders. Redisson makes these features available through intuitive, type-safe method overloads on the target bucket instance:

// GLIDE
client.set("k", "v", SetOptions.builder()
        .expiry(SetOptions.Expiry.Seconds(60L)).build()).get();
client.set("k", "v", SetOptions.builder()
        .conditionalSet(ConditionalChange.ONLY_IF_DOES_NOT_EXIST).build()).get();

// Redisson — direct methods on RBucket
bucket.set("v", Duration.ofSeconds(60));   // SETEX
boolean created = bucket.trySet("v");      // SETNX

Binary Streams and Selective Range Mutation

When working with raw byte arrays, appending logs, or performing partial updates via range commands, GLIDE maps operations directly to low-level string manipulations. Meanwhile, Redisson's RBinaryStream interface mirrors the standard Java NIO streaming and channel components, making it easy to interact with raw byte buffers:

// GLIDE
client.append("log", "entry").get();
String slice = client.getRange("log", 0, 3).get();
client.setRange("log", 0, "PREF").get();

// Redisson — RBinaryStream exposes the value as a stream and a channel
RBinaryStream stream = redisson.getBinaryStream("log");
ByteBuffer buf = ByteBuffer.allocate(4);
stream.getOutputStream().write("entry".getBytes());   // APPEND
stream.getChannel().write(buf);                         // SETRANGE
stream.getChannel().read(buf);                          // GETRANGE

For range-bound operations, adjust your channel position to your target offset before performing disk or network I/O. If your workflow requires non-blocking execution, call getAsynchronousChannel() to fetch an equivalent asynchronous channel wrapper.

Atomic Numerical Counters

Incrementing and decrementing statistical tracking numbers changes from raw string increments in GLIDE to Redisson's implementation of distributed atomic longs:

// GLIDE
client.incr("visits").get();

// Redisson
RAtomicLong visits = redisson.getAtomicLong("visits");
visits.incrementAndGet();

Key Management and Bulk Operations

Managing key lifecycles can be handled on individual data structures or batched across global namespaces via the RKeys interface:

// GLIDE
client.expire("user:1", 60).get();
client.del(new String[]{"user:1"}).get();
long count = client.exists(new String[]{"user:1"}).get();

// Redisson — per-object methods for a single key…
RBucket b = redisson.getBucket("user:1");
b.expire(Duration.ofSeconds(60));
b.delete();
boolean exists = b.isExists();

// …and RKeys for bulk or pattern operations
RKeys keys = redisson.getKeys();
keys.delete("user:1", "user:2");
Iterable matched = keys.getKeysByPattern("user:*");

Hash Structure and Map Interacting

Interacting with nested field-value structures in GLIDE translates directly into Redisson's standard RMap interface, which inherits all behavior from java.util.Map:

// GLIDE
client.hset("user:1", Map.of("name", "Ada")).get();
String n = client.hget("user:1", "name").get();

// Redisson
RMap user = redisson.getMap("user:1");
user.put("name", "Ada");
String n = user.get("name");

Java Collections

Whether managing queues, stacks, unique groupings, or prioritized indexes, Redisson intuitively maps standard Valkey collections to familiar Java counterparts (RList, RSet, and RScoredSortedSet):

// GLIDE
client.rpush("tasks", new String[]{"first"}).get();
client.sadd("tags", new String[]{"java"}).get();
client.zadd("leaderboard", Map.of("alice", 100.0)).get();

// Redisson — each implements the matching java.util type
RList list = redisson.getList("tasks");
list.add("first");
RSet set = redisson.getSet("tags");
set.add("java");
RScoredSortedSet board = redisson.getScoredSortedSet("leaderboard");
board.add(100.0, "alice");

Pipelining and Transactional Isolation

GLIDE wraps batched commands into a Batch object, using an atomic boolean flag to switch between standard network pipelining and true database transactions (MULTI/EXEC). Redisson decouples these strategies into distinct APIs: RBatch optimizes network performance via high-throughput pipelining, while RTransaction guarantees full ACID isolation:

// GLIDE — Batch(isAtomic): false = pipeline, true = atomic transaction (MULTI/EXEC)
Batch glideBatch = new Batch(false);
glideBatch.set("a", "1").set("b", "2");
client.exec(glideBatch, true).get();

// Redisson — RBatch pipelines; RTransaction adds ACID semantics
RBatch batch = redisson.createBatch();
batch.getBucket("a").setAsync("1");
batch.getBucket("b").setAsync("2");
batch.execute();

Server-Side Scripting

With GLIDE, you write Lua scripts full of commands to execute on the Valkey server. These are replaced by Redisson's clean scripting management interface:

// GLIDE
Script glideScript = new Script("return 1");
client.invokeScript(glideScript).get();

// Redisson
RScript script = redisson.getScript();
script.eval(RScript.Mode.READ_ONLY, "return 1", RScript.ReturnType.LONG);

PubSub Message Processing

GLIDE handles PubSub message subscriptions by attaching static callbacks during the client build phase. For busy production workloads, Valkey recommends dedicating separate client instances to these tasks. Redisson simplifies this with its RTopic object, which allows you to dynamically add listeners and publish messages anywhere in your application using a single client connection:

// GLIDE — subscriptions are configured when the client is built (use a dedicated client)
MessageCallback callback = (message, context) -> { /* handle message */ };
GlideClientConfiguration subConfig = GlideClientConfiguration.builder()
        .address(NodeAddress.builder().host("127.0.0.1").port(6379).build())
        .subscriptionConfiguration(StandaloneSubscriptionConfiguration.builder()
                .subscription(PubSubChannelMode.EXACT, "news")
                .callback(callback)
                .build())
        .build();
GlideClient subscriber = GlideClient.createClient(subConfig).get();

// publish from a separate client; note GLIDE passes the message first, then the channel
publisher.publish("hello", "news").get();

// Redisson — subscribe and publish at runtime on the same client
RTopic topic = redisson.getTopic("news");
topic.addListener(String.class, (channel, msg) -> handle(msg));
topic.publish("hello");

For commands not shown above, Redisson's command-to-object mapping reference lists every Redis and Valkey command alongside the object and method that issues it, across the sync, reactive, and RxJava APIs. As that page notes, Redisson's distributed features — locks, rate limiters, near-cache, reliable messaging — aren't listed there because they map to no single command, which is exactly the abstraction layer this migration buys you.

And that's it. You have now successfully migrated from Valkey GLIDE to Redisson. The only other thing to do is decide whether Redisson Community Edition or Redisson PRO is right for you. For complex, enterprise-scale deployments, Redisson PRO provides extra performance optimizations and advanced architectural components. Learn more by reviewing the Redisson vs. Redisson PRO feature comparison.

Similar articles