由于 Spring 引导版本升级到 2.3.1,Spring 数据 cassandra 出现问题



由于 Spring boot 的 2.3 版本中对 docker 镜像支持的改进,我们决定迁移到这个版本。在我们的项目中,我们使用Cassandra作为数据库之一。但似乎春季数据 cassandra 发生了很多变化,除了迁移到 cassandra 驱动程序 verison 4。问题是此异常不允许应用程序启动,

java.lang.IllegalStateException: Since you provided explicit contact points, the local DC must be explicitly set (see basic.load-balancing-policy.local-datacenter in the config, or set it programmatically with SessionBuilder.withLocalDatacenter)

现在,我在网上搜索,发现有人建议:

将此属性添加到我的应用程序属性:

spring.data.cassandra.local-datacenter=datacenter1 (in my case since in the exception that it throws, it's mentioned that the local datacenter is - datacenter1)

并在创建 CqlSession bean 时使用指定它,我正在这样做:

public CqlSession session() {
String containerIpAddress = getContactPoints();
int containerPort = getPort();
InetSocketAddress containerEndPoint = new InetSocketAddress(containerIpAddress, containerPort);
return CqlSession.builder().withLocalDatacenter(getLocalDataCenter())
.addContactPoint(containerEndPoint)
.withAuthCredentials(dbProperties.getCassandraUserName(), dbProperties.getCassandraPassword())
.withKeyspace(getKeyspaceName()).build(); }

但是我仍然被困住了,无法启动应用程序。如何解决这个问题?

我正在使用 Reactive Cassandra,但它大致相同。数据中心字段是新的,可以通过登录到 cassandra 实例并运行

select data_center from system.local;

至于我的配置,它看起来像这样:

@Configuration
@EnableReactiveCassandraRepositories
public class CassandraConfig {
@Value("${spring.data.cassandra.contact-points}")
private String hostList;
@Value("${spring.data.cassandra.datacenter}")
private String datacenter;
@Value("${spring.data.cassandra.keyspace-name}")
private String keyspaceName;
@Value("${spring.data.cassandra.username}")
private String userName;
@Value("${spring.data.cassandra.password}")
private String password;
@Value("${spring.data.cassandra.port}")
private Integer port;
@Bean
public CqlSessionFactoryBean getCqlSession() {
CqlSessionFactoryBean factory = new CqlSessionFactoryBean();
factory.setUsername(userName);
factory.setPassword(password);
factory.setPort(port);
factory.setKeyspaceName(keyspaceName);
factory.setContactPoints(hostList);
factory.setLocalDatacenter(datacenter);
return factory;
}
}

使用此配置对我有用

public CqlSession session() {
return CqlSession.builder().withLocalDatacenter(getLocalDataCenter())
.addContactPoint(InetSocketAddress.createUnresolved(getContactPoints(), 9042))
//.withAuthCredentials(dbProperties.getCassandraUserName(), dbProperties.getCassandraPassword())
.withKeyspace(getKeyspaceName()).build();
}

@Bean
@ConditionalOnMissingBean
public CassandraTemplate cassandraTemplate(CqlSession session) throws Exception {
return new CassandraTemplate(session);
}

实际上,Apache Cassandra 需要不同的配置才能真正与新的 spring 版本一起工作。我花了大约 50 个小时的搜索才在本文档中找到它 - https://docs.spring.io/spring-data/cassandra/docs/current/reference/html/#cassandra.cassandra-java-config

您需要按照此处指定的方式创建新的配置文件。为此,请遵循以下操作:

创建名为config的新包 在名为 -CassandraConfig的包中创建.java类文件 将以下代码复制并粘贴到其中。

@Configuration public class CassandraConfig { public @Bean CqlSession session() { return CqlSession.builder().withKeyspace("mykeyspacename").build(); } }

请注意,将密钥空间名称更改为属性文件中定义的密钥空间名称。如果您尚未创建密钥空间,请在系统上启动 Cassandra 服务器,通过发出cqlsh登录到终端或 cmd 上的cqlsh,然后发出以下命令 -

CREATE KEYSPACE IF NOT EXISTS mykeyspacename WITH REPLICATION = { 'class' : 'SimpleStrategy', 'replication_factor' : 1 } AND DURABLE_WRITES = true ;

到目前为止,当您启动 Spring 启动应用程序时,它应该运行没有任何错误。

最新更新