使用谓词加载缓存
Load cache with predicate
我有一个缓存,里面有很多类型。我是 运行 纯 Java 节点。我在部署服务之前在启动时加载缓存。缓存由 CacheJdbcPojoStore 支持。我正在使用 Ignite 1.8。
当我加载空谓词时,一切正常。所有类型及其实例都加载到内存中。但是,当我加载谓词时,出现以下错误。奇怪的是,在 windows 上,错误没有发生并且谓词工作正常。但是在 Linux 上,它失败了。这里可能出了什么问题?
缓存加载代码。 ServiceStatus 和 ServiceMetric 只是我的数据库支持的两种 pojo 类型。
log.info("Local load cache started.");
cache.localLoadCache(new IgniteBiPredicate() {
@Override
public boolean apply(Object key, Object value) {
// include by default, exclude explicitly
// no service status before today
if (value instanceof ServiceStatus) {
if (((ServiceStatus)value).getLastUpdated().before(Timestamp.valueOf(LocalDate.now().atStartOfDay()))){
return false;
}
}
// no service metrics before today
if (value instanceof ServiceMetric) {
if (((ServiceMetric)value).getLastUpdated().before(Timestamp.valueOf(LocalDate.now().atStartOfDay()))){
return false;
}
}
return true;
}
}, null);
log.info("Local load cache finished.");
错误。
[错误] 2017-01-30 13:01:28.913 [main] ServiceGrid - 异常失败。
javax.cache.integration.CacheLoaderException:加载缓存失败:D9Cache
在 org.apache.ignite.cache.store.jdbc.CacheAbstractJdbcStore.loadCache(CacheAbstractJdbcStore.java:847) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.internal.processors.cache.store.GridCacheStoreManagerAdapter.loadCache(GridCacheStoreManagerAdapter.java:512) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.internal.processors.cache.distributed.dht.GridDhtCacheAdapter.localLoadCache(GridDhtCacheAdapter.java:497) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.internal.processors.cache.IgniteCacheProxy.localLoadCache(IgniteCacheProxy.java:413) ~[ignite-core-1.8.0.jar:1.8.0]
在 com.nmf.model.persistence.CacheUtil.loadCache(CacheUtil.java:87) ~[shared-data-model-1.0-SNAPSHOT.jar:?]
在 com.nmf.grid.ServiceGrid.main(ServiceGrid.java:75) [dragon9-service-grid-1.0-SNAPSHOT.jar:?]
由以下原因引起:org.apache.ignite.binary.BinaryObjectException:ID 的 class 解析失败:292145121
在 org.apache.ignite.internal.binary.BinaryContext.descriptorForTypeId(BinaryContext.java:696) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.internal.binary.BinaryReaderExImpl.deserialize0(BinaryReaderExImpl.java:1491) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.internal.binary.BinaryReaderExImpl.deserialize(BinaryReaderExImpl.java:1450) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.internal.binary.BinaryObjectImpl.deserializeValue(BinaryObjectImpl.java:637) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.internal.binary.BinaryObjectImpl.value(BinaryObjectImpl.java:142) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.internal.processors.cache.distributed.dht.GridDhtCacheAdapter.loadEntry(GridDhtCacheAdapter.java:528) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.internal.processors.cache.distributed.dht.GridDhtCacheAdapter.access$300(GridDhtCacheAdapter.java:94) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.internal.processors.cache.distributed.dht.GridDhtCacheAdapter$4.apply(GridDhtCacheAdapter.java:501) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.internal.processors.cache.distributed.dht.GridDhtCacheAdapter$4.apply(GridDhtCacheAdapter.java:497) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.internal.processors.cache.store.GridCacheStoreManagerAdapter$3.apply(GridCacheStoreManagerAdapter.java:528) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.cache.store.jdbc.CacheAbstractJdbcStore$1.call(CacheAbstractJdbcStore.java:462) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.cache.store.jdbc.CacheAbstractJdbcStore$1.call(CacheAbstractJdbcStore.java:429) ~[ignite-core-1.8.0.jar:1.8.0]
在 java.util.concurrent.FutureTask.run(FutureTask.java:266) ~[?:1.8.0_111]
在 java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142) ~[?:1.8.0_111]
在 java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617) ~[?:1.8.0_111]
在 java.lang.Thread.run(Thread.java:745) ~[?:1.8.0_111]
原因:org.apache.ignite.IgniteCheckedException:在编组器缓存和本地文件中找不到 Class 定义。 [id=292145121, file=/tmp/ignite/work/marshaller/292145121.classname]
在 org.apache.ignite.internal.MarshallerContextImpl.className(MarshallerContextImpl.java:218) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.internal.MarshallerContextAdapter.getClass(MarshallerContextAdapter.java:174) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.internal.binary.BinaryContext.descriptorForTypeId(BinaryContext.java:680) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.internal.binary.BinaryReaderExImpl.deserialize0(BinaryReaderExImpl.java:1491) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.internal.binary.BinaryReaderExImpl.deserialize(BinaryReaderExImpl.java:1450) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.internal.binary.BinaryObjectImpl.deserializeValue(BinaryObjectImpl.java:637) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.internal.binary.BinaryObjectImpl.value(BinaryObjectImpl.java:142) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.internal.processors.cache.distributed.dht.GridDhtCacheAdapter.loadEntry(GridDhtCacheAdapter.java:528) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.internal.processors.cache.distributed.dht.GridDhtCacheAdapter.access$300(GridDhtCacheAdapter.java:94) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.internal.processors.cache.distributed.dht.GridDhtCacheAdapter$4.apply(GridDhtCacheAdapter.java:501) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.internal.processors.cache.distributed.dht.GridDhtCacheAdapter$4.apply(GridDhtCacheAdapter.java:497) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.internal.processors.cache.store.GridCacheStoreManagerAdapter$3.apply(GridCacheStoreManagerAdapter.java:528) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.cache.store.jdbc.CacheAbstractJdbcStore$1.call(CacheAbstractJdbcStore.java:462) ~[ignite-core-1.8.0.jar:1.8.0]
在 org.apache.ignite.cache.store.jdbc.CacheAbstractJdbcStore$1.call(CacheAbstractJdbcStore.java:429) ~[ignite-core-1.8.0.jar:1.8.0]
在 java.util.concurrent.FutureTask.run(FutureTask.java:266) ~[?:1.8.0_111]
在 java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142) ~[?:1.8.0_111]
在 java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617) ~[?:1.8.0_111]
在 java.lang.Thread.run(Thread.java:745) ~[?:1.8.0_111]
没有其他信息,很难给出建议,但您可以使用 cache.withKeepBinary() 检查它是否可重现。另外,尝试反弹整个集群。奇怪的是这个案例只代表 Linux.
我也看到了这个问题(为了节省时间)让我完全放弃使用谓词。在使用谓词加载缓存时,我 有时 会收到您在上面提到的异常。我在 Linux 和 windows 上都观察到了这一点,但它并不一致。有时缓存会加载,有时不会。正如我所说,我被赶时间所以假设它是 Ignite 代码中某处的竞争条件,即 运行 谓词并解决了这个问题。
如果任何 Ignite 专家可以进一步阐明问题的潜在根源,我很乐意尽可能提供帮助。
--更新--
在尝试从后备存储加载日期之前,我已经通过 "warming" 二进制编组器解决了这个问题(这导致文件未找到错误)
所以我所做的是沿着以下几行:
IgniteCache cache = ignite.getOrCreateCache("my-cache");
warmBinaryMarshaller(cache);
cache.localLoadCache(cache, new MyPredicate(), (Object[])null);
...
private static void warmBinaryMarshaller(IgniteCache cache) throws Exception
{
final IgniteCache transientCache = cache.withSkipStore();
try{
CacheKey key = new CacheKey();
CacheEntity entity = CacheEntity();
key.setId(0);
entity.setId(0);
transientCache.put(key, entity);
transientCache.remove(key);
} catch (Exception e) {
log.error(e.getMessage(), e);
}
}
...
然后我可以成功地从我的数据库加载对象
我有一个缓存,里面有很多类型。我是 运行 纯 Java 节点。我在部署服务之前在启动时加载缓存。缓存由 CacheJdbcPojoStore 支持。我正在使用 Ignite 1.8。
当我加载空谓词时,一切正常。所有类型及其实例都加载到内存中。但是,当我加载谓词时,出现以下错误。奇怪的是,在 windows 上,错误没有发生并且谓词工作正常。但是在 Linux 上,它失败了。这里可能出了什么问题?
缓存加载代码。 ServiceStatus 和 ServiceMetric 只是我的数据库支持的两种 pojo 类型。
log.info("Local load cache started.");
cache.localLoadCache(new IgniteBiPredicate() {
@Override
public boolean apply(Object key, Object value) {
// include by default, exclude explicitly
// no service status before today
if (value instanceof ServiceStatus) {
if (((ServiceStatus)value).getLastUpdated().before(Timestamp.valueOf(LocalDate.now().atStartOfDay()))){
return false;
}
}
// no service metrics before today
if (value instanceof ServiceMetric) {
if (((ServiceMetric)value).getLastUpdated().before(Timestamp.valueOf(LocalDate.now().atStartOfDay()))){
return false;
}
}
return true;
}
}, null);
log.info("Local load cache finished.");
错误。
[错误] 2017-01-30 13:01:28.913 [main] ServiceGrid - 异常失败。 javax.cache.integration.CacheLoaderException:加载缓存失败:D9Cache 在 org.apache.ignite.cache.store.jdbc.CacheAbstractJdbcStore.loadCache(CacheAbstractJdbcStore.java:847) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.internal.processors.cache.store.GridCacheStoreManagerAdapter.loadCache(GridCacheStoreManagerAdapter.java:512) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.internal.processors.cache.distributed.dht.GridDhtCacheAdapter.localLoadCache(GridDhtCacheAdapter.java:497) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.internal.processors.cache.IgniteCacheProxy.localLoadCache(IgniteCacheProxy.java:413) ~[ignite-core-1.8.0.jar:1.8.0] 在 com.nmf.model.persistence.CacheUtil.loadCache(CacheUtil.java:87) ~[shared-data-model-1.0-SNAPSHOT.jar:?] 在 com.nmf.grid.ServiceGrid.main(ServiceGrid.java:75) [dragon9-service-grid-1.0-SNAPSHOT.jar:?] 由以下原因引起:org.apache.ignite.binary.BinaryObjectException:ID 的 class 解析失败:292145121 在 org.apache.ignite.internal.binary.BinaryContext.descriptorForTypeId(BinaryContext.java:696) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.internal.binary.BinaryReaderExImpl.deserialize0(BinaryReaderExImpl.java:1491) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.internal.binary.BinaryReaderExImpl.deserialize(BinaryReaderExImpl.java:1450) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.internal.binary.BinaryObjectImpl.deserializeValue(BinaryObjectImpl.java:637) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.internal.binary.BinaryObjectImpl.value(BinaryObjectImpl.java:142) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.internal.processors.cache.distributed.dht.GridDhtCacheAdapter.loadEntry(GridDhtCacheAdapter.java:528) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.internal.processors.cache.distributed.dht.GridDhtCacheAdapter.access$300(GridDhtCacheAdapter.java:94) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.internal.processors.cache.distributed.dht.GridDhtCacheAdapter$4.apply(GridDhtCacheAdapter.java:501) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.internal.processors.cache.distributed.dht.GridDhtCacheAdapter$4.apply(GridDhtCacheAdapter.java:497) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.internal.processors.cache.store.GridCacheStoreManagerAdapter$3.apply(GridCacheStoreManagerAdapter.java:528) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.cache.store.jdbc.CacheAbstractJdbcStore$1.call(CacheAbstractJdbcStore.java:462) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.cache.store.jdbc.CacheAbstractJdbcStore$1.call(CacheAbstractJdbcStore.java:429) ~[ignite-core-1.8.0.jar:1.8.0] 在 java.util.concurrent.FutureTask.run(FutureTask.java:266) ~[?:1.8.0_111] 在 java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142) ~[?:1.8.0_111] 在 java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617) ~[?:1.8.0_111] 在 java.lang.Thread.run(Thread.java:745) ~[?:1.8.0_111] 原因:org.apache.ignite.IgniteCheckedException:在编组器缓存和本地文件中找不到 Class 定义。 [id=292145121, file=/tmp/ignite/work/marshaller/292145121.classname] 在 org.apache.ignite.internal.MarshallerContextImpl.className(MarshallerContextImpl.java:218) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.internal.MarshallerContextAdapter.getClass(MarshallerContextAdapter.java:174) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.internal.binary.BinaryContext.descriptorForTypeId(BinaryContext.java:680) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.internal.binary.BinaryReaderExImpl.deserialize0(BinaryReaderExImpl.java:1491) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.internal.binary.BinaryReaderExImpl.deserialize(BinaryReaderExImpl.java:1450) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.internal.binary.BinaryObjectImpl.deserializeValue(BinaryObjectImpl.java:637) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.internal.binary.BinaryObjectImpl.value(BinaryObjectImpl.java:142) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.internal.processors.cache.distributed.dht.GridDhtCacheAdapter.loadEntry(GridDhtCacheAdapter.java:528) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.internal.processors.cache.distributed.dht.GridDhtCacheAdapter.access$300(GridDhtCacheAdapter.java:94) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.internal.processors.cache.distributed.dht.GridDhtCacheAdapter$4.apply(GridDhtCacheAdapter.java:501) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.internal.processors.cache.distributed.dht.GridDhtCacheAdapter$4.apply(GridDhtCacheAdapter.java:497) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.internal.processors.cache.store.GridCacheStoreManagerAdapter$3.apply(GridCacheStoreManagerAdapter.java:528) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.cache.store.jdbc.CacheAbstractJdbcStore$1.call(CacheAbstractJdbcStore.java:462) ~[ignite-core-1.8.0.jar:1.8.0] 在 org.apache.ignite.cache.store.jdbc.CacheAbstractJdbcStore$1.call(CacheAbstractJdbcStore.java:429) ~[ignite-core-1.8.0.jar:1.8.0] 在 java.util.concurrent.FutureTask.run(FutureTask.java:266) ~[?:1.8.0_111] 在 java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142) ~[?:1.8.0_111] 在 java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617) ~[?:1.8.0_111] 在 java.lang.Thread.run(Thread.java:745) ~[?:1.8.0_111]
没有其他信息,很难给出建议,但您可以使用 cache.withKeepBinary() 检查它是否可重现。另外,尝试反弹整个集群。奇怪的是这个案例只代表 Linux.
我也看到了这个问题(为了节省时间)让我完全放弃使用谓词。在使用谓词加载缓存时,我 有时 会收到您在上面提到的异常。我在 Linux 和 windows 上都观察到了这一点,但它并不一致。有时缓存会加载,有时不会。正如我所说,我被赶时间所以假设它是 Ignite 代码中某处的竞争条件,即 运行 谓词并解决了这个问题。
如果任何 Ignite 专家可以进一步阐明问题的潜在根源,我很乐意尽可能提供帮助。
--更新-- 在尝试从后备存储加载日期之前,我已经通过 "warming" 二进制编组器解决了这个问题(这导致文件未找到错误)
所以我所做的是沿着以下几行:
IgniteCache cache = ignite.getOrCreateCache("my-cache");
warmBinaryMarshaller(cache);
cache.localLoadCache(cache, new MyPredicate(), (Object[])null);
...
private static void warmBinaryMarshaller(IgniteCache cache) throws Exception
{
final IgniteCache transientCache = cache.withSkipStore();
try{
CacheKey key = new CacheKey();
CacheEntity entity = CacheEntity();
key.setId(0);
entity.setId(0);
transientCache.put(key, entity);
transientCache.remove(key);
} catch (Exception e) {
log.error(e.getMessage(), e);
}
}
...
然后我可以成功地从我的数据库加载对象