Why Redis Increment Returns Null When Using @Transactional with Transaction Support in Spring Boot

The production failure where a customer‑service event creation stopped each morning was traced to RedisTemplate’s increment returning null because @Transactional combined with enabled Redis transaction support caused the command to be queued in a MULTI/EXEC block, which is fixed by using separate non‑transactional and transactional StringRedisTemplate beans.

Java Tech Enthusiast
Java Tech Enthusiast
Java Tech Enthusiast
Why Redis Increment Returns Null When Using @Transactional with Transaction Support in Spring Boot

The article describes a production issue where creating a customer‑service event fails every morning until the microservice is restarted. The failure is caused by the Redis increment operation returning null, which leads to a cascade of errors.

Initial investigation shows that the code uses return redisTemplate.opsForValue().increment("count", 1); and that the increment call returns null only in the early‑morning runs. The team first hypothesized a connection‑leak, but other Redis‑using features worked fine, so this was ruled out.

The second hypothesis focused on Redis transactions. Official Redis documentation states that increment returns null when executed inside a pipeline or a transaction. The service implementation is annotated with @Transactional, which may cause the Redis command to be treated as part of a transaction.

Experiments were performed:

When Redis transaction support is disabled, the increment call returns the expected numeric value, regardless of the @Transactional annotation.

When Redis transaction support is enabled ( setEnableTransactionSupport(true)) and the method is marked with @Transactional, the increment call consistently returns null, reproducing the production symptom.

Root cause analysis revealed that enabling Redis transaction support makes RedisTemplate bind a connection. Inside a Spring @Transactional method, the bound connection treats the increment as part of a Redis MULTI/EXEC block, queuing the command and returning null until the transaction is committed.

Two remediation strategies are proposed:

Disable transaction support after each Redis transaction. This approach works but still fails if a Redis command is issued inside a @Transactional method while the transaction is active.

Use two separate StringRedisTemplate beans: one with transaction support for explicit Redis transaction scenarios, and another without transaction support for ordinary Redis commands. The configuration example:

\@Bean
public StringRedisTemplate stringRedisTemplate(RedisConnectionFactory factory) {
    StringRedisTemplate template = new StringRedisTemplate(factory);
    template.setEnableTransactionSupport(false);
    return template;
}
\@Bean
public StringRedisTemplate stringRedisTemplateTransaction(RedisConnectionFactory factory) {
    StringRedisTemplate template = new StringRedisTemplate(factory);
    template.setEnableTransactionSupport(true);
    return template;
}

Service classes can then inject the appropriate bean and avoid the null result.

After applying the second solution, the Redis increment returns the correct count value even inside @Transactional methods, and the original production issue is resolved.

Original Source

Signed-in readers can open the original source through BestHub's protected redirect.

Sign in to view source
Republication Notice

This article has been distilled and summarized from source material, then republished for learning and reference. If you believe it infringes your rights, please contactadmin@besthub.devand we will review it promptly.

DebuggingJavatransactionredisSpring Boottransactional
Java Tech Enthusiast
Written by

Java Tech Enthusiast

Sharing computer programming language knowledge, focusing on Java fundamentals, data structures, related tools, Spring Cloud, IntelliJ IDEA... Book giveaways, red‑packet rewards and other perks await!

0 followers
Reader feedback

How this landed with the community

Sign in to like

Rate this article

Was this worth your time?

Sign in to rate
Discussion

0 Comments

Thoughtful readers leave field notes, pushback, and hard-won operational detail here.