Apache Ignite - Cassandra 持久性问题
Apache Ignite - Cassandra persistence issue
此问题与 密切相关。
快速总结:我正在努力将 Cassandra 配置为我的 Ignite 2.0 缓存的持久层。由于以下原因,后写操作失败:
java.lang.IllegalArgumentException: object is not an instance of declaring class
我尝试使用 Cassandra 上的模式、持久性设置中的字段配置、缓存属性等,但我无法克服它。以下是我最后尝试的配置:
持久性设置:
<persistence keyspace="ignite" table="odbc_test" ttl="86400">
<keyspaceOptions>
REPLICATION = {'class' : 'SimpleStrategy', 'replication_factor' : 1}
AND DURABLE_WRITES = true
</keyspaceOptions>
<tableOption>
comment = 'Cache test'
AND read_repair_chance = 0.2
</tableOption>
<keyPersistence class="java.lang.String" strategy="PRIMITIVE" column="key"/>
<valuePersistence class="com.riccamini.ignite.ValueClass" strategy="POJO"/>
</persistence>
值类:
public class ValueClass implements Serializable{
@QuerySqlField
private int numberOne;
@QuerySqlField
private int numberTwo;
public int getNumberOne(){ return numberOne;}
public int getNumberTwo(){ return numberTwo;}
public void setNumberOne(int value){
numberOne = value;
}
public void setNumberTwo(int value){
numberTwo = value;
}
}
卡桑德拉的 table:
CREATE TABLE ignite.odbc_test (
key text PRIMARY KEY,
numberone int,
numbertwo int);
Ignite配置:
boolean persistence = true;
IgniteConfiguration cfg = new IgniteConfiguration();
CacheConfiguration<String, ValueClass> configuration = new CacheConfiguration<String, ValueClass>();
configuration.setName("test-cache");
configuration.setIndexedTypes(String.class, ValueClass.class);
if(persistence){
// Configuring Cassandra's persistence
DataSource dataSource = new DataSource();
dataSource.setContactPoints("172.17.0.2");
RoundRobinPolicy robinPolicy = new RoundRobinPolicy();
dataSource.setLoadBalancingPolicy(robinPolicy);
dataSource.setReadConsistency("ONE");
dataSource.setWriteConsistency("ONE");
String persistenceSettingsXml = FileUtils.readFileToString(new File(persistenceSettingsConfig), "utf-8");
KeyValuePersistenceSettings persistenceSettings = new KeyValuePersistenceSettings(persistenceSettingsXml);
CassandraCacheStoreFactory cacheStoreFactory = new CassandraCacheStoreFactory();
cacheStoreFactory.setDataSource(dataSource);
cacheStoreFactory.setPersistenceSettings(persistenceSettings);
configuration.setCacheStoreFactory(cacheStoreFactory);
configuration.setWriteThrough(true);
configuration.setReadThrough(true);
configuration.setWriteBehindEnabled(true);
configuration.setStoreKeepBinary(true);
}
// Setting cache configuration
cfg.setCacheConfiguration(configuration);
// Configuring ODBC
OdbcConfiguration odbcConfig = new OdbcConfiguration();
odbcConfig.setMaxOpenCursors(100);
cfg.setOdbcConfiguration(odbcConfig);
// Starting Ignite
Ignite ignite = Ignition.start(cfg);
完整堆栈跟踪:
SEVERE: Failed to process 1 of 1 elements, during BULK_WRITE operation with Cassandra
class org.apache.ignite.IgniteException: Failed to execute Cassandra BULK_WRITE operation
at org.apache.ignite.cache.store.cassandra.session.CassandraSessionImpl.execute(CassandraSessionImpl.java:266)
at org.apache.ignite.cache.store.cassandra.CassandraCacheStore.writeAll(CassandraCacheStore.java:333)
at org.apache.ignite.internal.processors.cache.store.GridCacheWriteBehindStore.updateStore(GridCacheWriteBehindStore.java:804)
at org.apache.ignite.internal.processors.cache.store.GridCacheWriteBehindStore.applyBatch(GridCacheWriteBehindStore.java:720)
at org.apache.ignite.internal.processors.cache.store.GridCacheWriteBehindStore.access00(GridCacheWriteBehindStore.java:75)
at org.apache.ignite.internal.processors.cache.store.GridCacheWriteBehindStore$Flusher.flushCacheCoalescing(GridCacheWriteBehindStore.java:1135)
at org.apache.ignite.internal.processors.cache.store.GridCacheWriteBehindStore$Flusher.body(GridCacheWriteBehindStore.java:1006)
at org.apache.ignite.internal.util.worker.GridWorker.run(GridWorker.java:110)
at java.lang.Thread.run(Thread.java:748)
Caused by: class org.apache.ignite.IgniteException: Failed to get value of the field 'numberOne' from the instance of 'class org.apache.ignite.internal.binary.BinaryObjectImpl' class
at org.apache.ignite.cache.store.cassandra.persistence.PojoField.getValueFromObject(PojoField.java:165)
at org.apache.ignite.cache.store.cassandra.persistence.PersistenceController.bindValues(PersistenceController.java:450)
at org.apache.ignite.cache.store.cassandra.persistence.PersistenceController.bindKeyValue(PersistenceController.java:203)
at org.apache.ignite.cache.store.cassandra.CassandraCacheStore.bindStatement(CassandraCacheStore.java:347)
at org.apache.ignite.cache.store.cassandra.CassandraCacheStore.bindStatement(CassandraCacheStore.java:333)
at org.apache.ignite.cache.store.cassandra.session.CassandraSessionImpl.execute(CassandraSessionImpl.java:230)
... 8 more
Caused by: java.lang.IllegalArgumentException: object is not an instance of declaring class
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:498)
at org.apache.ignite.cache.store.cassandra.persistence.PojoField.getValueFromObject(PojoField.java:147)
... 13 more
感谢您迄今为止提供的所有帮助。
发生这种情况是因为您设置了:
configuration.setStoreKeepBinary(true);
将其设置为 false(默认值),在服务器节点上部署 POJO 类,它就会工作。当前的实现不能直接使用二进制对象,这将在这张票的范围内得到改进:https://issues.apache.org/jira/browse/IGNITE-5270
此问题与
快速总结:我正在努力将 Cassandra 配置为我的 Ignite 2.0 缓存的持久层。由于以下原因,后写操作失败:
java.lang.IllegalArgumentException: object is not an instance of declaring class
我尝试使用 Cassandra 上的模式、持久性设置中的字段配置、缓存属性等,但我无法克服它。以下是我最后尝试的配置:
持久性设置:
<persistence keyspace="ignite" table="odbc_test" ttl="86400">
<keyspaceOptions>
REPLICATION = {'class' : 'SimpleStrategy', 'replication_factor' : 1}
AND DURABLE_WRITES = true
</keyspaceOptions>
<tableOption>
comment = 'Cache test'
AND read_repair_chance = 0.2
</tableOption>
<keyPersistence class="java.lang.String" strategy="PRIMITIVE" column="key"/>
<valuePersistence class="com.riccamini.ignite.ValueClass" strategy="POJO"/>
</persistence>
值类:
public class ValueClass implements Serializable{
@QuerySqlField
private int numberOne;
@QuerySqlField
private int numberTwo;
public int getNumberOne(){ return numberOne;}
public int getNumberTwo(){ return numberTwo;}
public void setNumberOne(int value){
numberOne = value;
}
public void setNumberTwo(int value){
numberTwo = value;
}
}
卡桑德拉的 table:
CREATE TABLE ignite.odbc_test (
key text PRIMARY KEY,
numberone int,
numbertwo int);
Ignite配置:
boolean persistence = true;
IgniteConfiguration cfg = new IgniteConfiguration();
CacheConfiguration<String, ValueClass> configuration = new CacheConfiguration<String, ValueClass>();
configuration.setName("test-cache");
configuration.setIndexedTypes(String.class, ValueClass.class);
if(persistence){
// Configuring Cassandra's persistence
DataSource dataSource = new DataSource();
dataSource.setContactPoints("172.17.0.2");
RoundRobinPolicy robinPolicy = new RoundRobinPolicy();
dataSource.setLoadBalancingPolicy(robinPolicy);
dataSource.setReadConsistency("ONE");
dataSource.setWriteConsistency("ONE");
String persistenceSettingsXml = FileUtils.readFileToString(new File(persistenceSettingsConfig), "utf-8");
KeyValuePersistenceSettings persistenceSettings = new KeyValuePersistenceSettings(persistenceSettingsXml);
CassandraCacheStoreFactory cacheStoreFactory = new CassandraCacheStoreFactory();
cacheStoreFactory.setDataSource(dataSource);
cacheStoreFactory.setPersistenceSettings(persistenceSettings);
configuration.setCacheStoreFactory(cacheStoreFactory);
configuration.setWriteThrough(true);
configuration.setReadThrough(true);
configuration.setWriteBehindEnabled(true);
configuration.setStoreKeepBinary(true);
}
// Setting cache configuration
cfg.setCacheConfiguration(configuration);
// Configuring ODBC
OdbcConfiguration odbcConfig = new OdbcConfiguration();
odbcConfig.setMaxOpenCursors(100);
cfg.setOdbcConfiguration(odbcConfig);
// Starting Ignite
Ignite ignite = Ignition.start(cfg);
完整堆栈跟踪:
SEVERE: Failed to process 1 of 1 elements, during BULK_WRITE operation with Cassandra
class org.apache.ignite.IgniteException: Failed to execute Cassandra BULK_WRITE operation
at org.apache.ignite.cache.store.cassandra.session.CassandraSessionImpl.execute(CassandraSessionImpl.java:266)
at org.apache.ignite.cache.store.cassandra.CassandraCacheStore.writeAll(CassandraCacheStore.java:333)
at org.apache.ignite.internal.processors.cache.store.GridCacheWriteBehindStore.updateStore(GridCacheWriteBehindStore.java:804)
at org.apache.ignite.internal.processors.cache.store.GridCacheWriteBehindStore.applyBatch(GridCacheWriteBehindStore.java:720)
at org.apache.ignite.internal.processors.cache.store.GridCacheWriteBehindStore.access00(GridCacheWriteBehindStore.java:75)
at org.apache.ignite.internal.processors.cache.store.GridCacheWriteBehindStore$Flusher.flushCacheCoalescing(GridCacheWriteBehindStore.java:1135)
at org.apache.ignite.internal.processors.cache.store.GridCacheWriteBehindStore$Flusher.body(GridCacheWriteBehindStore.java:1006)
at org.apache.ignite.internal.util.worker.GridWorker.run(GridWorker.java:110)
at java.lang.Thread.run(Thread.java:748)
Caused by: class org.apache.ignite.IgniteException: Failed to get value of the field 'numberOne' from the instance of 'class org.apache.ignite.internal.binary.BinaryObjectImpl' class
at org.apache.ignite.cache.store.cassandra.persistence.PojoField.getValueFromObject(PojoField.java:165)
at org.apache.ignite.cache.store.cassandra.persistence.PersistenceController.bindValues(PersistenceController.java:450)
at org.apache.ignite.cache.store.cassandra.persistence.PersistenceController.bindKeyValue(PersistenceController.java:203)
at org.apache.ignite.cache.store.cassandra.CassandraCacheStore.bindStatement(CassandraCacheStore.java:347)
at org.apache.ignite.cache.store.cassandra.CassandraCacheStore.bindStatement(CassandraCacheStore.java:333)
at org.apache.ignite.cache.store.cassandra.session.CassandraSessionImpl.execute(CassandraSessionImpl.java:230)
... 8 more
Caused by: java.lang.IllegalArgumentException: object is not an instance of declaring class
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:498)
at org.apache.ignite.cache.store.cassandra.persistence.PojoField.getValueFromObject(PojoField.java:147)
... 13 more
感谢您迄今为止提供的所有帮助。
发生这种情况是因为您设置了:
configuration.setStoreKeepBinary(true);
将其设置为 false(默认值),在服务器节点上部署 POJO 类,它就会工作。当前的实现不能直接使用二进制对象,这将在这张票的范围内得到改进:https://issues.apache.org/jira/browse/IGNITE-5270