Spring Data默认值的错误

阿里云国内75折 回扣 微信号:monov8
阿里云国际,腾讯云国际,低至75折。AWS 93折 免费开户实名账号 代冲值 优惠多多 微信号:monov8 飞机:@monov6

Spring Data有很多配置的默认值但不一定都适合你。如一个依赖Cassandra 的项目有时写入数据后并不能立马读到。这种错误并没有什么报错一切都是正常的就是读不到数据。

1 源码解析

直接使用 Spring Data Cassandra 操作时实际依赖 Cassandra driver 内部的配置文件目录

.m2\repository\com\datastax\oss\java-driver-core\4.6.1\java-driver-core-4.6.1.jar!\reference.conf

很多默认配置很重要配置是 Consistencydriver中默认为 LOCAL_ONE

basic.request {
 

  # The consistency level.
  #
  # Required: yes
  # Modifiable at runtime: yes, the new value will be used for requests issued after the change.
  # Overridable in a profile: yes
  consistency = LOCAL_ONE
 
//省略其他非关键配置 
}

执行读写操作时都会使用 LOCAL_ONE。运行时配置调试截图

Cassandra 使用核心原则使R读+W写>N即读和写的节点数之和大于备份数。

设数据备份 3 份待写入数据分别存储在 A、B、C 节点。常见搭配是 R读和 W写的一致性都是 LOCAL_QURAM这样可以保证能及时读到写入的数据而假设在这种情况下读写都用 LOCAL_ONE则可能发生这样的情况用户写入一个节点 A 就返回但用户 B 立马读的节点是 C由于是LOCAL_ONE 一致性则读完 C 就可立马返回。此时就会出现数据读取可能落空case。

为何Cassandra driver 默认使用 LOCAL_ONE其实是最合适的因为只有一台机器读写都只能命中一台。但产线上的 Cassandra 大多都是多数据中心多节点的备份数大于1。所以读写都用 LOCAL_ONE 就会出现问题。

修正

修改默认值以 consistency 为例。

@Override
protected SessionBuilderConfigurer getSessionBuilderConfigurer() {
    return cqlSessionBuilder -> {
        DefaultProgrammaticDriverConfigLoaderBuilder defaultProgrammaticDriverConfigLoaderBuilder = new DefaultProgrammaticDriverConfigLoaderBuilder();
        driverConfigLoaderBuilderCustomizer().customize(defaultProgrammaticDriverConfigLoaderBuilder);
        cqlSessionBuilder.withConfigLoader(defaultProgrammaticDriverConfigLoaderBuilder.build());
        return cqlSessionBuilder;
    };
}

@Bean
public DriverConfigLoaderBuilderCustomizer driverConfigLoaderBuilderCustomizer() {
    return loaderBuilder -> loaderBuilder
            .withString(REQUEST_CONSISTENCY, ConsistencyLevel.LOCAL_QUORUM.name())
}

将一致性级别从 LOCAL_ONE 改成了 LOCAL_QUARM符合实际产品部署和应用情况。

阿里云国内75折 回扣 微信号:monov8
阿里云国际,腾讯云国际,低至75折。AWS 93折 免费开户实名账号 代冲值 优惠多多 微信号:monov8 飞机:@monov6
标签: Spring