java - 点燃 Spring + 点燃 SQL ClassCastException
问题描述
每次我尝试交替使用 Ignite Spring API 和 Ignite SQL API 时,都会出现类转换异常或“找不到 xxxx 的 sql 表”
发生这种情况是因为我使用 ignite spring 创建了一个缓存并尝试使用 Ignite SQL API 使用数据,反之亦然:
@Configuration
@EnableIgniteRepositories("local.teste.is.api.repositories")
public class SpringAppCfg {
@Bean
public Ignite igniteInstance() {
IgniteConfiguration cfg = new IgniteConfiguration();
cfg.setIgniteInstanceName("springDataNode");
cfg.setPeerClassLoadingEnabled(true);
cfg.setClientMode(true);
...
// Defining and creating a new cache to be used by Ignite Spring Data
// repository.
CacheConfiguration ccfg = new CacheConfiguration("SQL_PUBLIC_SAMPLETYPE3");
// Setting SQL schema for the cache.
ccfg.setIndexedTypes(Integer.class, SampleType.class);
cfg.setCacheConfiguration(ccfg);
Ignite ignite = Ignition.start(cfg);
IgniteCache cache = ignite.getOrCreateCache(ccfg);
SqlQuery sql = new SqlQuery(SampleType.class, "true");
try (QueryCursor<Entry<Integer, SampleType>> cursor = cache.query(sql)) {
for (Entry<Integer, SampleType> e : cursor)
System.out.println(e.getValue().toString());
}
return ignite;
}
样本类型存储库:
package local.teste.is.api.repositories;
import org.apache.ignite.springdata.repository.IgniteRepository;
import org.apache.ignite.springdata.repository.config.RepositoryConfig;
import local.al40.is.api.entities.SampleType;
@RepositoryConfig(cacheName = "SQL_PUBLIC_SAMPLETYPE")
public interface SampleTypeRepository extends IgniteRepository<SampleType, Integer> {
public SampleType getSampleTypeBySampleTypeId(Integer id);
}
使用 ignite Spring 的一切工作,包括保存和读取数据:
public class Application {
private static AnnotationConfigApplicationContext dataCtx;
private static SampleTypeRepository repo;
public static void main(String[] args) throws Exception {
dataCtx = new AnnotationConfigApplicationContext();
// Explicitly registering Spring configuration.
dataCtx.register(SpringAppCfg.class);
dataCtx.refresh();
repo = dataCtx.getBean(SampleTypeRepository.class);
System.out.println(repo);
SampleType s = new SampleType(1, "teste");
repo.save(s.getSampleTypeId(), s);
System.out.println(repo.getSampleTypeBySampleTypeId(1).getSampleTypeName());
如果我通过 DDL 创建一个 Ignite SQL 表并尝试通过 Ignite Spring 使用它,就会发生这种情况,给我一个 ClassCastException,例如“...ignite.IgniteRepositoryImpl#123456 cannot be cast to SampleType.class”。这让我相信这是一个与序列化有关的问题。如果我通过 Ignite Spring 创建表并尝试查询它,它还会给我“找不到 xxxx 的 sql 表”。有人尝试过整合这两种观点吗?我在网上找到的示例仅假设使用 Ignite Spring 创建的缓存,并且 Ignite 的文档表明这种交换是可能的并且是透明的。但是,显然不是,除非我忘记了什么。
此致,
卡洛斯·科斯塔
解决方案
好的,我解决了我的问题。感谢大家的帮助。为了进一步澄清我相当复杂的疑问,我将编写以下指南,如果尝试互换使用 Ignite SQL 和 Ignite Spring,应考虑这些指南:
选项 1) 通过 Ignite Spring 创建缓存:
a) 在存储库类中明确定义缓存名称:
...
@RepositoryConfig(cacheName = "My Cache Name")
public interface SampleTypeRepository extends IgniteRepository<SampleType, Integer> {
public SampleType getSampleTypeBySampleTypeId(Integer id);
}
b) 在 Spring 应用程序中配置 Ignite 实例时定义缓存和索引:
...
CacheConfiguration ccfg = new CacheConfiguration("My Chache Name");
// Setting SQL schema for the cache.
ccfg.setIndexedTypes(Integer.class, SampleType.class);
config.setCacheConfiguration(ccfg);
Ignite ignite = Ignition.start(config);
...
c) 查询它,但请注意,由于某种原因,SQL 表名称是“SampleType”而不是“我的缓存名称”。我不知道,但这似乎是我在 Ignite Spring 文档中没有明确找到的一些默认行为。否则你可能会得到“找不到 SQL 表”:
...
IgniteCache cache = ignite.cache("My Chache Name");
SqlFieldsQuery sql = new SqlFieldsQuery("select * from SampleType");
try (QueryCursor<List<?>> cursor = cache.query(sql)) {
for (List<?> e : cursor)
System.out.println(e.get(1));
}
选项 2) 通过 SQL DDL 创建缓存:
a) 通过明确定义 cache_name、key_type 和 value_type 来创建您的 SQL 表/缓存,使用与键和值类型对应的类的完全限定包名称:
CREATE TABLE IF NOT EXISTS SampleType(SampleTypeID int, SampleTypeName varchar, PRIMARY KEY (SampleTypeID)) WITH "cache_name=mycachename, key_type=java.lang.Integer, value_type=local.teste.is.api.entities.SampleType";
b) 要插入数据,通过 ignite Spring 就像使用文档中显示的 API 方法的魅力一样。但是,通过 DDL 或 JDBC 插入,您需要清楚地识别 _KEY 属性(显然是隐藏属性:P):
INSERT INTO SampleType(_KEY, SAMPLETYPEID, SAMPLETYPENAME) VALUES(?,?,?)
然后,我认为您可以互换使用这些 API。
最好的问候,卡洛斯·科斯塔
推荐阅读
- c# - 数据在 SQL DB 中保存为 1/1/0001 12:00:00 AM
- xaml - 在 Xamarin Forms iOS 中实现分组时,如何知道项目的集合视图滚动到达终点(在最后一项)?
- drools - 无法在 Drools 规则文件的 KIE 有状态会话中检索会话对象
- python - 嵌套列表计数器
- google-apps-script - 获取多个现有工作表的基于时间的触发事件中的当前工作表
- python-3.x - 从动态加载的站点中提取数据
- c - int (*ptr)[4] 的真正含义是什么,它与 *ptr 有何不同?
- javascript - 有人可以解释如何使用插件 vuejs-progress-bar
- python - 错误:找不到满足 kivy-deps.angle 要求的版本(来自版本:无)
- matlab - 使用 Filtering、butterworth、filtfilt 命令去除相位差