spring-projects / spring-data-cassandra

Provides support to increase developer productivity in Java when using Apache Cassandra. Uses familiar Spring concepts such as a template classes for core API usage and lightweight repository style data access.
https://spring.io/projects/spring-data-cassandra/
Apache License 2.0
373 stars 307 forks source link

How do I add converter from Instant to org.joda.time.DateTime to spring-data-commons-3.2.1 and spring-data-cassandra-4.2.1 #1481

Closed thaparraj closed 4 months ago

thaparraj commented 4 months ago

I started getting the exception after I upgraded to spring-data-commons-3.2.1 and spring-data-cassandra-4.2.1.

I added the custom conversions (below) but still get the error

@configuration
public class CassandraConfig {
...
@bean
CassandraCustomConversions cassandraCustomConversions() {
List<Converter> converters = new ArrayList<>();
converters.add(new InstantToDateTimeConverter());
converters.add(new DateTimeToInstantConverter());
CassandraCustomConversions ccv = new CassandraCustomConversions(converters);
return ccv;
}
class DateTimeToInstantConverter implements Converter<DateTime, java.time.Instant> {
@OverRide
public java.time.Instant convert(DateTime source) {
return source.toDate().toInstant();
}
}
class InstantToDateTimeConverter implements Converter<java.time.Instant, DateTime> {
@OverRide
public DateTime convert(java.time.Instant source) {
return new DateTime(Date.from(source));
}
}
...
}
mp911de commented 4 months ago

but still get the error

What error?

If you would like us to spend some time helping you to diagnose the problem, please spend some time describing it and, ideally, providing a minimal yet complete sample that reproduces the problem. You can share it with us by pushing it to a separate repository on GitHub or by zipping it up and attaching it to this issue.

thaparraj commented 4 months ago

I am preparing a sample program, it connects to a Cassandra server installed within company. Will that be ok if I leave out instructions for deploying Cassandra server.

thaparraj commented 4 months ago

Error:

org.springframework.core.convert.ConverterNotFoundException: No converter found capable of converting from type [java.time.Instant] to type [org.joda.time.DateTime]

        at org.springframework.core.convert.support.GenericConversionService.handleConverterNotFound(GenericConversionService.java:294) ~[spring-core-6.1.2.jar:6.1.2]

        at org.springframework.core.convert.support.GenericConversionService.convert(GenericConversionService.java:185) ~[spring-core-6.1.2.jar:6.1.2]

        at org.springframework.core.convert.support.GenericConversionService.convert(GenericConversionService.java:165) ~[spring-core-6.1.2.jar:6.1.2]

        at org.springframework.data.cassandra.core.convert.MappingCassandraConverter.doConvert(MappingCassandraConverter.java:1059) ~[spring-data-cassandra-4.2.1.jar:4.2.1]

        at org.springframework.data.cassandra.core.convert.MappingCassandraConverter.getPotentiallyConvertedSimpleRead(MappingCassandraConverter.java:1054) ~[spring-data-cassandra-4.2.1.jar:4.2.1]

        at org.springframework.data.cassandra.core.convert.MappingCassandraConverter.getPotentiallyConvertedSimpleRead(MappingCassandraConverter.java:1022) ~[spring-data-cassandra-4.2.1.jar:4.2.1]

        at org.springframework.data.cassandra.core.convert.MappingCassandraConverter$ConversionContext.convert(MappingCassandraConverter.java:1362) ~[spring-data-cassandra-4.2.1.jar:4.2.1]

        at org.springframework.data.cassandra.core.convert.MappingCassandraConverter.getReadValue(MappingCassandraConverter.java:1102) ~[spring-data-cassandra-4.2.1.jar:4.2.1]

        at org.springframework.data.cassandra.core.convert.MappingCassandraConverter.readProperties(MappingCassandraConverter.java:541) ~[spring-data-cassandra-4.2.1.jar:4.2.1]

        at org.springframework.data.cassandra.core.convert.MappingCassandraConverter.doReadEntity(MappingCassandraConverter.java:521) ~[spring-data-cassandra-4.2.1.jar:4.2.1]

        at org.springframework.data.cassandra.core.convert.MappingCassandraConverter.doReadEntity(MappingCassandraConverter.java:478) ~[spring-data-cassandra-4.2.1.jar:4.2.1]

        at org.springframework.data.cassandra.core.convert.MappingCassandraConverter.doReadEntity(MappingCassandraConverter.java:441) ~[spring-data-cassandra-4.2.1.jar:4.2.1]

        at org.springframework.data.cassandra.core.convert.MappingCassandraConverter.doReadRow(MappingCassandraConverter.java:421) ~[spring-data-cassandra-4.2.1.jar:4.2.1]

        at org.springframework.data.cassandra.core.convert.MappingCassandraConverter.readRow(MappingCassandraConverter.java:417) ~[spring-data-cassandra-4.2.1.jar:4.2.1]

        at org.springframework.data.cassandra.core.convert.MappingCassandraConverter.read(MappingCassandraConverter.java:399) ~[spring-data-cassandra-4.2.1.jar:4.2.1]

        at org.springframework.data.cassandra.core.convert.MappingCassandraConverter.project(MappingCassandraConverter.java:290) ~[spring-data-cassandra-4.2.1.jar:4.2.1]

        at org.springframework.data.cassandra.core.CassandraTemplate.lambda$getMapper$23(CassandraTemplate.java:936) ~[spring-data-cassandra-4.2.1.jar:4.2.1]

        at org.springframework.data.cassandra.core.CassandraTemplate.lambda$select$0(CassandraTemplate.java:371) ~[spring-data-cassandra-4.2.1.jar:4.2.1]

        at org.springframework.data.cassandra.core.cql.RowMapperResultSetExtractor.extractData(RowMapperResultSetExtractor.java:80) ~[spring-data-cassandra-4.2.1.jar:4.2.1]

        at org.springframework.data.cassandra.core.cql.RowMapperResultSetExtractor.extractData(RowMapperResultSetExtractor.java:43) ~[spring-data-cassandra-4.2.1.jar:4.2.1]

        at org.springframework.data.cassandra.core.cql.CqlTemplate.query(CqlTemplate.java:406) ~[spring-data-cassandra-4.2.1.jar:4.2.1]

        at org.springframework.data.cassandra.core.cql.CqlTemplate.query(CqlTemplate.java:424) ~[spring-data-cassandra-4.2.1.jar:4.2.1]

        at org.springframework.data.cassandra.core.CassandraTemplate.doQuery(CassandraTemplate.java:852) ~[spring-data-cassandra-4.2.1.jar:4.2.1]

        at org.springframework.data.cassandra.core.CassandraTemplate.select(CassandraTemplate.java:371) ~[spring-data-cassandra-4.2.1.jar:4.2.1]

        at org.springframework.data.cassandra.repository.query.CassandraQueryExecution$CollectionExecution.execute(CassandraQueryExecution.java:159) ~[spring-data-cassandra-4.2.1.jar:4.2.1]

        at org.springframework.data.cassandra.repository.query.CassandraQueryExecution$ResultProcessingExecution.execute(CassandraQueryExecution.java:270) ~[spring-data-cassandra-4.2.1.jar:4.2.1]

        at org.springframework.data.cassandra.repository.query.AbstractCassandraQuery.execute(AbstractCassandraQuery.java:86) ~[spring-data-cassandra-4.2.1.jar:4.2.1]

        at org.springframework.data.repository.core.support.RepositoryMethodInvoker.doInvoke(RepositoryMethodInvoker.java:170) ~[spring-data-commons-3.2.1.jar:3.2.1]

        at org.springframework.data.repository.core.support.RepositoryMethodInvoker.invoke(RepositoryMethodInvoker.java:158) ~[spring-data-commons-3.2.1.jar:3.2.1]

        at org.springframework.data.repository.core.support.QueryExecutorMethodInterceptor.doInvoke(QueryExecutorMethodInterceptor.java:164) ~[spring-data-commons-3.2.1.jar:3.2.1]

        at org.springframework.data.repository.core.support.QueryExecutorMethodInterceptor.invoke(QueryExecutorMethodInterceptor.java:143) ~[spring-data-commons-3.2.1.jar:3.2.1]

        at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:184) ~[spring-aop-6.1.2.jar:6.1.2]

        at org.springframework.data.projection.DefaultMethodInvokingMethodInterceptor.invoke(DefaultMethodInvokingMethodInterceptor.java:70) ~[spring-data-commons-3.2.1.jar:3.2.1]

        at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:184) ~[spring-aop-6.1.2.jar:6.1.2]

        at org.springframework.aop.interceptor.ExposeInvocationInterceptor.invoke(ExposeInvocationInterceptor.java:97) ~[spring-aop-6.1.2.jar:6.1.2]

        at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:184) ~[spring-aop-6.1.2.jar:6.1.2]

        at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:249) ~[spring-aop-6.1.2.jar:6.1.2]

        at jdk.proxy2/jdk.proxy2.$Proxy157.findBySomeCriteria(Unknown Source) ~[?:?]

        at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method) ~[?:?]

        at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:77) ~[?:?]

        at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) ~[?:?]

        at java.base/java.lang.reflect.Method.invoke(Method.java:568) ~[?:?]

        at org.springframework.aop.support.AopUtils.invokeJoinpointUsingReflection(AopUtils.java:352) ~[spring-aop-6.1.2.jar:6.1.2]

        at org.springframework.aop.framework.ReflectiveMethodInvocation.invokeJoinpoint(ReflectiveMethodInvocation.java:196) ~[spring-aop-6.1.2.jar:6.1.2]

        at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:163) ~[spring-aop-6.1.2.jar:6.1.2]

        at org.springframework.dao.support.PersistenceExceptionTranslationInterceptor.invoke(PersistenceExceptionTranslationInterceptor.java:137) ~[spring-tx-6.1.2.jar:6.1.2]

        at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:184) ~[spring-aop-6.1.2.jar:6.1.2]

        at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:249) ~[spring-aop-6.1.2.jar:6.1.2]

        at jdk.proxy2/jdk.proxy2.$Proxy157.findBySomeCriteria(Unknown Source) ~[?:?]

        at com.myorg.resolver.SomeQuery.SomeDataBySomeId(SomeQuery.java:33) ~[classes/:?]
mp911de commented 4 months ago

I wasn't able to reproduce the problem with the code you've provided, see https://gist.github.com/mp911de/3603c9c78d6326f3cc8ea912ceeb1506.

Having the CQL for your schema, the entities and a really tiny reproducer is all that we need. We don't require any huge setup so that you can leave away any controllers, services, …

thaparraj commented 4 months ago

my code:

file1: CassandraClusterConfig.java

package com.myorg.aiml.config;

import java.net.InetSocketAddress; import java.util.Date; import java.util.ArrayList; import java.util.Arrays; import java.util.List;

import com.datastax.oss.driver.api.core.CqlSessionBuilder; import org.joda.time.DateTime; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.beans.factory.annotation.Value; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.Primary; import org.springframework.core.convert.converter.Converter; import org.springframework.data.cassandra.config.CqlSessionFactoryBean; import org.springframework.data.cassandra.config.SessionBuilderConfigurer; import org.springframework.data.cassandra.core.CassandraTemplate; import org.springframework.data.cassandra.core.convert.CassandraCustomConversions; import org.springframework.data.cassandra.repository.config.EnableCassandraRepositories; import org.springframework.data.convert.ReadingConverter; import org.springframework.data.convert.WritingConverter; import org.springframework.stereotype.Component; import org.springframework.util.StringUtils;

import com.datastax.oss.driver.api.core.config.DefaultDriverOption; import com.datastax.oss.driver.api.core.config.DriverConfigLoader;

/**

@EnableCassandraRepositories @Configuration public class CassandraClusterConfig { private static final Logger logger = LoggerFactory.getLogger(CassandraClusterConfig.class); @Value("${CASSANDRA_HOSTS}") private String contactPoints; @Value("${CASSANDRA_PORT}") private int port; @Value("${CASSANDRA_KEYSPACE}") private String keyspaceName; @Value("${CASSANDRA_USERNAME}") private String userName; @Value("${CASSANDRA_PASSWORD}") private String password; @Value("${CASSANDRA_LOCAL_DC}") private String localDataCenter;

@Value("${session_bean_consistency_level}")
private String sessionBeanConsistency;

@Value("${cassandra_query_request_timeout}")
private String cassandraQueryRequestTimeout;

public String getKeyspaceName() {
   return this.keyspaceName;
}

protected String getContactPoints() {
   return this.contactPoints;
}

@Bean("session")
@Primary
public CqlSessionFactoryBean session() {
    CqlSessionFactoryBean session = new CqlSessionFactoryBean();
   List<InetSocketAddress> addressList = getInetSoketAddress(contactPoints);
   DriverConfigLoader driverConfigLoader = DriverConfigLoader.programmaticBuilder()
         .withString(DefaultDriverOption.REQUEST_CONSISTENCY, sessionBeanConsistency.trim())
         .withString(DefaultDriverOption.REQUEST_TIMEOUT, cassandraQueryRequestTimeout)
         .build();
   logger.info("Session Bean consistency level set to: " + sessionBeanConsistency);
   logger.info("cassandraQueryRequestTimeout set to:" + cassandraQueryRequestTimeout);
   SessionBuilderConfigurer sessionBuilderConfigurer = getSessionBuilderConfigurer(addressList, driverConfigLoader,
         localDataCenter);
   session.setSessionBuilderConfigurer(sessionBuilderConfigurer);
   session.setKeyspaceName(getKeyspaceName());
    return session;
}

@Bean("cassandraTemplate")
@Primary
public CassandraTemplate cassandraTemplate(CqlSessionFactoryBean session, CassandraCustomConversions ccv) {
   CassandraTemplate ct = new CassandraTemplate(session.getObject());
   return ct;
}

@Bean
public CassandraCustomConversions cassandraCustomConversions(DateTimeToInstantConverter dateTimeToInstantConverter,
                                              InstantToDateTimeConverter instantToDateTimeConverter) {
   return new CassandraCustomConversions(Arrays.asList(dateTimeToInstantConverter, instantToDateTimeConverter));
}
@Component
@WritingConverter
public static class DateTimeToInstantConverter implements Converter<DateTime, java.time.Instant> {
   @Override
   public java.time.Instant convert(DateTime source) {
      return source.toDate().toInstant();
   }
}

@Component
@ReadingConverter
public static class InstantToDateTimeConverter implements Converter<java.time.Instant, DateTime> {
   @Override
   public DateTime convert(java.time.Instant source) {
      return new DateTime(Date.from(source));
   }
}

private SessionBuilderConfigurer getSessionBuilderConfigurer(List<InetSocketAddress> addressList, DriverConfigLoader driverConfigLoader, String dataCenter) {
   SessionBuilderConfigurerModel configurerModel = new SessionBuilderConfigurerModel();
   configurerModel.setAddressList(addressList);
   configurerModel.setDataCenter(dataCenter);
   configurerModel.setDriverConfigLoader(driverConfigLoader);
   configurerModel.setKeyspaceName(keyspaceName);
   configurerModel.setPassword(password);
   configurerModel.setUserName(userName);
   return getSessionBuilderConfigurer(configurerModel);
}

private SessionBuilderConfigurer getSessionBuilderConfigurer(SessionBuilderConfigurerModel configurerModel) {
   return new SessionBuilderConfigurer() {
      @Override
      public CqlSessionBuilder configure(CqlSessionBuilder sessionBuilder) {
         DriverConfigLoader driverConfigLoader = configurerModel.getDriverConfigLoader();
         sessionBuilder.addContactPoints(configurerModel.getAddressList())
               .withConfigLoader(driverConfigLoader)
               .withLocalDatacenter(configurerModel.getDataCenter())
               .withKeyspace(configurerModel.getKeyspaceName())
               .withAuthCredentials(configurerModel.getUserName(), configurerModel.getPassword());
         return sessionBuilder;
      }
   };
}
private List<InetSocketAddress> getInetSoketAddress(String contactPoints) {
   List<InetSocketAddress> addressList = new ArrayList<>();
   StringUtils.commaDelimitedListToSet(contactPoints)
         .forEach(host -> addressList.add(new InetSocketAddress(host, port)));
   return addressList;
}

}

File: SessionBuilderConfigurerModel.java

package com.myorg.aiml.config;

import com.datastax.oss.driver.api.core.config.DriverConfigLoader; import lombok.Data; import org.springframework.context.ApplicationContext;

import java.net.InetSocketAddress; import java.util.List;

@Data public class SessionBuilderConfigurerModel { List addressList; DriverConfigLoader driverConfigLoader; String keyspaceName; String dataCenter; String userName; String password; String prefix = ""; ApplicationContext context; }

File3: ackage com.myorg.aiml.repo;

import com.myorg.aiml.model.MyUserAccount; import com.myorg.aiml.model.UserAccount;

import java.util.List; import org.springframework.data.cassandra.repository.CassandraRepository; import org.springframework.stereotype.Repository;

@Repository public interface AccntsByUseridRepo extends CassandraRepository<MyUserAccount, String> { public List findByUserid(String userid); }

File4: application.properties spring.autoconfigure.exclude=org.springframework.boot.actuate.autoconfigure.metrics.MetricsAspectsAutoConfiguration spring.application.name=mycassandra server.servlet.context-path=/ server.port=8075

CASSANDRA_HOSTS=localhost CASSANDRA_PORT=9042 CASSANDRA_KEYSPACE=accountdb CASSANDRA_USERNAME=cassandra CASSANDRA_PASSWORD=cassandra CASSANDRA_LOCAL_DC=datacenter1 session_bean_consistency_level=LOCAL_ONE cassandra_query_request_timeout=2000 milliseconds date_limit_duration_in_days=30 date_time_limit_duration_in_days=30

File5: Readme

custom conversions sample

setting up casandra locally on Mac

  1. download docker desktop

  2. run commands:

    docker run --name mycass -p 9042:9042 -d cassandra:3.11.5 docker exec -it mycass cqlsh cqlsh> CREATE KEYSPACE accountdb WITH REPLICATION = { 'class' : 'SimpleStrategy', 'replication_factor' : 1 }; cqlsh> create table account_tbl (name text, status boolean, createts timestamp, userid text, primary key (userid)); cqlsh> insert into account_tbl (name , status , createts , userid) values ('john', true, toTimeStamp(now()), 'idjohn');
    cqlsh> select * from account_tbl;

  3. start app

  4. run following curl command: curl --location 'http://localhost:8075/Users/idjohn'

thaparraj commented 4 months ago

Controller., service and pom files file1: package com.myorg.aiml.controller;

import com.myorg.aiml.model.MyUserAccount; import com.myorg.aiml.model.UserAccount; import com.myorg.aiml.service.AccountsService; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.web.bind.annotation.*;

import java.util.List;

@RestController public class AccountsController { @Autowired private AccountsService accountsService; @GetMapping(path="/Users/{id}") @ResponseBody public List get(@PathVariable String id) { List users = accountsService.getByAccountId(id); return users; }

@PostMapping(path="/Users")
public void addAccount(@RequestBody MyUserAccount userAccount) {
    accountsService.createAccnt(userAccount);
}

@PutMapping(path="/Users/{id}")
public void updateAccount(@PathVariable String id, @RequestBody MyUserAccount userAccount) {
    accountsService.updateAccnt(userAccount);
}

}

file2: package com.myorg.aiml.service;

import com.myorg.aiml.model.MyUserAccount; import com.myorg.aiml.model.UserAccount; import com.myorg.aiml.repo.AccntsByUseridRepo; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.data.cassandra.CassandraConnectionFailureException; import org.springframework.data.cassandra.CassandraInvalidQueryException; import org.springframework.stereotype.Service;

import java.util.*; import java.util.stream.Collectors;

@Service public class AccountsService { private static final Logger logger = LoggerFactory.getLogger(AccountsService.class); @Autowired AccntsByUseridRepo accntsByUseridRepo; public List getByAccountId(String userid) { List list = new ArrayList<>(); try { if (userid != null) { list = accntsByUseridRepo .findByUserid(userid).stream() .distinct().collect(Collectors.toList()); } if (list.isEmpty()) { logger.warn("No data available for given parameter"); } return list; } catch (CassandraInvalidQueryException e) { throw e; } catch (CassandraConnectionFailureException e) { throw e; } }

public void createAccnt(MyUserAccount userAccount) {
    try {
        accntsByUseridRepo.save(userAccount);
    } catch (CassandraInvalidQueryException e) {
        throw e;
    }
}

public void updateAccnt(MyUserAccount userAccount) {
    try {
        accntsByUseridRepo.save(userAccount);
    } catch (Exception e) {
        throw e;
    }
}

}

file3: package com.myorg.aiml.model;

import lombok.AllArgsConstructor; import lombok.Getter; import lombok.RequiredArgsConstructor; import lombok.Setter; import org.joda.time.DateTime; import org.springframework.boot.autoconfigure.domain.EntityScan; import org.springframework.data.cassandra.core.cql.PrimaryKeyType; import org.springframework.data.cassandra.core.mapping.Column; import org.springframework.data.cassandra.core.mapping.PrimaryKeyColumn; import org.springframework.data.cassandra.core.mapping.Table;

import java.io.Serializable;

@EntityScan @Table("account_tbl") @Getter @Setter @RequiredArgsConstructor @AllArgsConstructor public class MyUserAccount implements Serializable { // create table account_tbl (name text, status boolean, createts timestamp, userid text, primary key (userid)); // insert into account_tbl (name , status , createts , userid) values ('john', true, toTimeStamp(now()), 'idjohn'); private static final long serialVersionUID = 1L; @Column("name") private String name; @Column("status") private Boolean status; @Column("status") private DateTime createts; @PrimaryKeyColumn(name = "userid", type = PrimaryKeyType.PARTITIONED) @Column("userid") private String userid; }

file4: package com.myorg.aiml;

import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.EnableAutoConfiguration; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration;

@SpringBootApplication(scanBasePackages = "com.myorg") @EnableAutoConfiguration(exclude = { DataSourceAutoConfiguration.class }) public class CrudGraphQlApplication {

public static void main(String[] args){

   SpringApplication.run(CrudGraphQlApplication.class,  args);

}

}

file5: <?xml version="1.0" encoding="UTF-8" standalone="no"?> <project xmlns=http://maven.apache.org/POM/4.0.0 xmlns:xsi=http://www.w3.org/2001/XMLSchema-instance xsi:schemaLocation=http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd>

4.0.0
<parent>
   <groupId>org.springframework.boot</groupId>
   <artifactId>spring-boot-starter-parent</artifactId>
   <version>3.2.1</version>
   <relativePath />
</parent>

<groupId>com.myorg.aiml</groupId>
<artifactId>custom-conversions-sample</artifactId>
<version>2.0.0</version>
<name>custom-conversions-sample</name>
<description>custom-conversions-sample</description>

<!-- Start SpringBoot Dependencies -->
<dependencies>
   <dependency>
      <groupId>org.springframework.boot</groupId>
      <artifactId>spring-boot-starter-web</artifactId>
   </dependency>
   <!--<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-devtools</artifactId> 
      <scope>runtime</scope> </dependency> -->
   <dependency>
      <groupId>org.springframework.boot</groupId>
      <artifactId>spring-boot-starter-test</artifactId>
      <scope>test</scope>
   </dependency>
   <dependency>
      <groupId>com.fasterxml.jackson.datatype</groupId>
      <artifactId>jackson-datatype-joda</artifactId>
   </dependency>
   <dependency>
      <groupId>org.springframework.boot</groupId>
      <artifactId>spring-boot-starter-data-cassandra</artifactId>
      <exclusions>
         <exclusion>
            <groupId>org.apache.tinkerpop</groupId>
            <artifactId>gremlin-core</artifactId>
         </exclusion>
         <exclusion>
            <groupId>org.apache.tinkerpop</groupId>
            <artifactId>gremlin-shaded</artifactId>
         </exclusion>
      </exclusions>
   </dependency>

   <dependency>
      <groupId>org.projectlombok</groupId>
      <artifactId>lombok</artifactId>
      <scope>provided</scope>
   </dependency>
</dependencies>

<build>
   <plugins>
      <plugin>
         <groupId>org.springframework.boot</groupId>
         <artifactId>spring-boot-maven-plugin</artifactId>
      </plugin>
      <plugin>
         <artifactId>maven-resources-plugin</artifactId>
      </plugin>
   </plugins>
</build>

mp911de commented 4 months ago
@Bean("cassandraTemplate")
@Primary
public CassandraTemplate cassandraTemplate(CqlSessionFactoryBean session, CassandraCustomConversions ccv) {
   CassandraTemplate ct = new CassandraTemplate(session.getObject());
   return ct;
}

Well, if you spin up a custom CassandraTemplate that isn't wired with CassandraCustomConversions (ideally through CassandraMappingContext and MappingCassandraConverter), then your converters won't get applied.

thaparraj commented 4 months ago

I need help in wiring the conversions to CassandraTemplate. I have uploaded code to github: https://github.com/thaparraj/custom-conversions-sample.git