spring - UncategorizedKeyValueException 试图通过具有事务支持的存储库保存 RedisHash

标签 spring spring-data spring-data-redis

问题:

启用事务支持后(redisTemplate.setEnableTransactionSupport(true)) 我得到 UncategorizedKeyValueException 试图在存储库中保存 @RedisHash

禁用事务支持时一切正常。

通过 RedisTemplate 的直接操作可以很好地支持事务。

堆栈跟踪:

...
at org.lorem.LoremController.create(TestController.java:41)
at org.springframework.cglib.proxy.MethodProxy.invoke(MethodProxy.java:204)
at org.springframework.aop.framework.CglibAopProxy$CglibMethodInvocation.invokeJoinpoint(CglibAopProxy.java:746)
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:163)
at org.springframework.transaction.interceptor.TransactionAspectSupport.invokeWithinTransaction(TransactionAspectSupport.java:294)
at org.springframework.transaction.interceptor.TransactionInterceptor.invoke(TransactionInterceptor.java:98)
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:185)
at org.springframework.aop.framework.CglibAopProxy$DynamicAdvisedInterceptor.intercept(CglibAopProxy.java:688)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at org.springframework.web.method.support.InvocableHandlerMethod.doInvoke(InvocableHandlerMethod.java:209)
at org.springframework.web.method.support.InvocableHandlerMethod.invokeForRequest(InvocableHandlerMethod.java:136)
at org.springframework.web.servlet.mvc.method.annotation.ServletInvocableHandlerMethod.invokeAndHandle(ServletInvocableHandlerMethod.java:102)
at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.invokeHandlerMethod(RequestMappingHandlerAdapter.java:877)
at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.handleInternal(RequestMappingHandlerAdapter.java:783)
at org.springframework.web.servlet.mvc.method.AbstractHandlerMethodAdapter.handle(AbstractHandlerMethodAdapter.java:87)
at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:991)
at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:925)
at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:974)
... 17 more
Caused by: java.lang.NullPointerException
at org.springframework.data.redis.core.RedisKeyValueAdapter.lambda$put$0(RedisKeyValueAdapter.java:236)
at org.springframework.data.redis.core.RedisTemplate.execute(RedisTemplate.java:224)
at org.springframework.data.redis.core.RedisTemplate.execute(RedisTemplate.java:184)
at org.springframework.data.redis.core.RedisTemplate.execute(RedisTemplate.java:171)
at org.springframework.data.redis.core.RedisKeyValueAdapter.put(RedisKeyValueAdapter.java:231)
at org.springframework.data.keyvalue.core.KeyValueTemplate.lambda$insert$0(KeyValueTemplate.java:165)
at org.springframework.data.keyvalue.core.KeyValueTemplate.execute(KeyValueTemplate.java:343)
... 56 more

背景:

我正在使用 spring-boot-starter-data-redis:2.0.4.RELEASE

配置:

@Bean
@Primary
StringRedisTemplate redisTemplate(RedisConnectionFactory redisConnectionFactory) {
    StringRedisTemplate redisTemplate = new StringRedisTemplate();
    redisTemplate.setConnectionFactory(redisConnectionFactory);
    redisTemplate.setEnableTransactionSupport(true);
    redisTemplate.afterPropertiesSet();

    return redisTemplate;
}

Redis哈希:

@RedisHash("test")
public class Test {
    private String id;
    private String field;

    public String getId() {
        return id;
    }

    public void setId(String id) {
        this.id = id;
    }

    public String getField() {
        return field;
    }

    public void setField(String field) {
        this.field = field;
    }
}

存储库:

public interface TestRepository extends CrudRepository<Test, String> {
}

谢谢:)

更新:

RedisKeyValueAdapter 中的以下行出现问题:

boolean isNew = connection.del(objectKey) == 0;

del() 返回 null,因为它在事务中运行。存储库不应该在启用事务支持的情况下工作吗?

最佳答案

Redis 存储库不适用于 Redis 事务。这在这里解释:https://jira.spring.io/browse/DATAREDIS-862

Redis Repositories do not work with Redis transactions as operations that change the underlying data are queued and executed at the end of the transaction. These commands return null. However, we require the outcome immediately at invocation time.

关于spring - UncategorizedKeyValueException 试图通过具有事务支持的存储库保存 RedisHash,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/52222970/

相关文章:

java - 如何定义整个spring项目的连接范围——web服务连接范围

java - 如何从Redis客户端获取ttl Redisson键值

java - 如何通过 DomainClassConverter 使用自定义 ID 转换?

redis - 带有缓存管理器的 spring-data-redis

spring-boot - spring redis运行脚本: how to pass expiry time value

java - 如何在 Spring JMS 监听器中从 JMS 消息获取自定义属性

spring - 带有休眠 :3. 6.10.15 插件的 grails 2.4.0 中的错误

java - Spring异常类型链中的路由器

java - 在 spring-data 中为 MongoDB 配置 GridFS 模板

Spring Data Rest PUT 与 PATCH LinkableResources