java - Hazelcast - java.lang.IllegalArgumentException:键不能是数据类型
问题描述
我们刚刚将我们的应用程序从 Hazelcast 3.8.0 升级到 3.10.1。
我们收到一条错误消息“密钥不能属于数据类型!” 在 Hazelcast 中访问数据时。
java.lang.IllegalArgumentException: key cannot be of type Data!
at com.hazelcast.util.Preconditions.checkNotInstanceOf(Preconditions.java:300)
at com.hazelcast.internal.nearcache.impl.DefaultNearCache.checkKeyFormat(DefaultNearCache.java:226)
at com.hazelcast.internal.nearcache.impl.DefaultNearCache.get(DefaultNearCache.java:114)
at com.hazelcast.map.impl.tx.TransactionalMapProxySupport.getCachedValue(TransactionalMapProxySupport.java:183)
at com.hazelcast.map.impl.tx.TransactionalMapProxySupport.getInternal(TransactionalMapProxySupport.java:132)
at com.hazelcast.map.impl.tx.TransactionalMapProxy.get(TransactionalMapProxy.java:110)
at com.hazelcast.client.impl.protocol.task.transactionalmap.TransactionalMapGetMessageTask.innerCall(TransactionalMapGetMessageTask.java:43)
at com.hazelcast.client.impl.protocol.task.AbstractTransactionalMessageTask.call(AbstractTransactionalMessageTask.java:34)
at com.hazelcast.client.impl.protocol.task.AbstractCallableMessageTask.processMessage(AbstractCallableMessageTask.java:35)
at com.hazelcast.client.impl.protocol.task.AbstractMessageTask.initializeAndProcessMessage(AbstractMessageTask.java:130)
at com.hazelcast.client.impl.protocol.task.AbstractMessageTask.run(AbstractMessageTask.java:110)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
at java.lang.Thread.run(Thread.java:745)
at com.hazelcast.util.executor.HazelcastManagedThread.executeRun(HazelcastManagedThread.java:64)
at com.hazelcast.util.executor.HazelcastManagedThread.run(HazelcastManagedThread.java:80)
at ------ submitted from ------.(Unknown Source)
我 100% 确定我们使用的“键”是一个字符串。代码片段如下所示:
String key = getKey(blah, blah);
TransactionContext context = client.newTransactionContext();
context.beginTransaction();
TransactionalMap<String, AppPrefs> dataMap = context.getMap(MAP_NAME);
try {
prefs = dataMap.get(key);
context.commitTransaction();
} catch (Throwable t) {
LOGGER.error("Error getting AppPrefs.", t);
context.rollbackTransaction();
}
引发错误的代码行是:
prefs = dataMap.get(key);
设置字符串的代码行之间没有任何内容
String key = getKey(blah, blah);
和吹的线:(
顺着源码看,TransactionalMapProxySupport的方法“toNearCacheKeyWithStrategy”有这样的逻辑:
final Object toNearCacheKeyWithStrategy(Object key) {
if (!nearCacheEnabled) {
return key;
}
return serializeKeys ? ss.toData(key, partitionStrategy) : key;
}
“DefaultNearCache”对象然后执行
private void checkKeyFormat(K key) {
if (!serializeKeys) {
checkNotInstanceOf(Data.class, key, "key cannot be of type Data!");
}
}
因此,看起来名为“serializeKeyes”的“TransactionalMapProxySupport”属性必须为 FALSE,但“DefaultNearCache”中的同名属性必须为 true :(
git 中“DefaultNearCache”的历史显示代码在一年前被更改,并显示消息:“Changed serialize-keys default for Near Cache from true to false”
我应该设置一些配置吗?
我对地图的配置很简单:
<near-cache name="AppPrefsCache">
<!-- Cache locally for 10 mins -->
<max-idle-seconds>600</max-idle-seconds>
</near-cache>
啊! 看来我可以在这个xml中添加一个(true|false)的“serialize-keys”标签并设置值。
似乎 Hazelcast 代码库的不同位为“序列化键”假设了不同的默认值。要么它应该是配置中的强制元素,要么默认值应该在任何地方都相同,是吗?
解决方案
提到的行为实际上是 Hazelcast 中的一个错误。我为它创建了一个新的 GitHub 问题,因此我们可以正确处理它 - hazelcast/hazelcast#13371。
受该错误影响的版本的解决方法是在配置中设置serialize-keys
为。该值在这里无济于事。true
near-cache
false
Config config = new Config();
config.getMapConfig(testName)
.setNearCacheConfig(new NearCacheConfig().setSerializeKeys(true));
谢谢你的报告和伟大的调查,彼得。
推荐阅读
- neural-network - ValueError: 操作数不能与形状一起广播 (54, 54, 128) (54, 54, 64)
- javascript - 如何在three.js中垂直定位相机
- customization - 如何在自定义仪器上精确绘制先前的高点和低点?
- javascript - 将 div 放在 div 之上
- sql - 在 PostgreSQL 中查找多个用户的时间戳差距
- java - Neo4j 嵌入式抛出 IllegalArgumentException:配置与设置没有关联:'unsupported.dbms.lucene.ephemeral'
- php - Laravel 从 5.1.46 更新到 5.2.* php artisan Segmentation fault
- .net - PDFBox 1.8.9 添加外部签名
- swift - 将我的 Fluent 模型链接到预先存在的数据库表
- ibm-cloud - 如何从 API 密钥生成 IBM Cloud 令牌