我正在尝试使用Hazelcast连续查询缓存特性。
我的用例是跟踪分布式系统中的api调用总数,并在需要时应用阈值。每个客户机节点定期插入自己的数据以进行映射,并定期接收/查询
我有hazelcast版本设置为3.9的客户机-服务器拓扑。我在客户机节点上使用连续查询缓存的合并特性。我用ttl将元素插入到地图中(通常为30秒)。查询字段存在索引。
1) 当我尝试使用组合Hazelcast谓词(EqualPredicate、GreaterPredicate等与and结合使用)进行连续缓存查询时,我经常在Hazelcast节点中看到以下异常:
2018-07-27 14:26:38,799 : [ERROR] [hz._hzInstance_1_mycluster.partition-operation.thread-7][SetOperation] [myhost]:9000 [mycluster] [3.9] null
java.lang.NullPointerException
at com.hazelcast.query.impl.CachedQueryEntry.getTargetObject(CachedQueryEntry.java:105)
at com.hazelcast.query.impl.QueryableEntry.extractAttributeValue(QueryableEntry.java:81)
at com.hazelcast.query.impl.QueryableEntry.getAttributeValue(QueryableEntry.java:48)
at com.hazelcast.query.impl.predicates.AbstractPredicate.readAttributeValue(AbstractPredicate.java:132)
at com.hazelcast.query.impl.predicates.AbstractPredicate.apply(AbstractPredicate.java:57)
at com.hazelcast.query.impl.predicates.NotEqualPredicate.apply(NotEqualPredicate.java:41)
at com.hazelcast.query.impl.predicates.AndPredicate.apply(AndPredicate.java:129)
at com.hazelcast.map.impl.query.QueryEventFilter.eval(QueryEventFilter.java:53)
at com.hazelcast.map.impl.event.AbstractFilteringStrategy.evaluateQueryEventFilter(AbstractFilteringStrategy.java:77)
at com.hazelcast.map.impl.event.DefaultEntryEventFilteringStrategy.processQueryEventFilter(DefaultEntryEventFilteringStrategy.java:125)
at com.hazelcast.map.impl.event.DefaultEntryEventFilteringStrategy.doFilter(DefaultEntryEventFilteringStrategy.java:84)
at com.hazelcast.map.impl.event.QueryCacheEventPublisher.getCQCEventTypeOrNull(QueryCacheEventPublisher.java:164)
at com.hazelcast.map.impl.event.QueryCacheEventPublisher.convertQueryCacheEventDataOrNull(QueryCacheEventPublisher.java:129)
at com.hazelcast.map.impl.event.QueryCacheEventPublisher.addEventToQueryCache(QueryCacheEventPublisher.java:92)
at com.hazelcast.map.impl.event.MapEventPublisherImpl.postPublishEvent(MapEventPublisherImpl.java:224)
at com.hazelcast.map.impl.event.MapEventPublisherImpl.publishEvent(MapEventPublisherImpl.java:204)
at com.hazelcast.map.impl.event.MapEventPublisherImpl.publishEvent(MapEventPublisherImpl.java:160)
at com.hazelcast.map.impl.event.MapEventPublisherImpl.publishEvent(MapEventPublisherImpl.java:148)
at com.hazelcast.map.impl.operation.BasePutOperation.afterRun(BasePutOperation.java:53)
at com.hazelcast.map.impl.operation.SetOperation.afterRun(SetOperation.java:40)
at com.hazelcast.spi.impl.operationservice.impl.OperationRunnerImpl.afterRun(OperationRunnerImpl.java:295)
at com.hazelcast.spi.impl.operationservice.impl.OperationRunnerImpl.run(OperationRunnerImpl.java:196)
at com.hazelcast.spi.impl.operationexecutor.impl.OperationExecutorImpl.run(OperationExecutorImpl.java:406)
at com.hazelcast.spi.impl.operationexecutor.impl.OperationExecutorImpl.runOrExecute(OperationExecutorImpl.java:433)
at com.hazelcast.spi.impl.operationservice.impl.Invocation.doInvokeLocal(Invocation.java:569)
at com.hazelcast.spi.impl.operationservice.impl.Invocation.doInvoke(Invocation.java:554)
at com.hazelcast.spi.impl.operationservice.impl.Invocation.invoke0(Invocation.java:513)
at com.hazelcast.spi.impl.operationservice.impl.Invocation.invoke(Invocation.java:207)
at com.hazelcast.spi.impl.operationservice.impl.InvocationBuilderImpl.invoke(InvocationBuilderImpl.java:60)
at com.hazelcast.client.impl.protocol.task.AbstractPartitionMessageTask.processMessage(AbstractPartitionMessageTask.java:67)
at com.hazelcast.client.impl.protocol.task.AbstractMessageTask.initializeAndProcessMessage(AbstractMessageTask.java:123)
at com.hazelcast.client.impl.protocol.task.AbstractMessageTask.run(AbstractMessageTask.java:103)
at com.hazelcast.spi.impl.operationservice.impl.OperationRunnerImpl.run(OperationRunnerImpl.java:154)
at com.hazelcast.spi.impl.operationexecutor.impl.OperationThread.process(OperationThread.java:125)
at com.hazelcast.spi.impl.operationexecutor.impl.OperationThread.run(OperationThread.java:100)
这对我来说毫无意义。似乎入口值是空的?这个到期了吗?这能避免吗?
public class MyCustomPredicate implements Predicate<String, MyMapElement>, Serializable {
@Override
public boolean apply(Entry<String, MyMapElement> paramEntry) {
MyMapElement myMapElement = paramEntry.getValue();
if (myMapElement == null) {
return false;
}
//MY CUSTOM PREDICATE LOGIC
}
}
就像上面的入口值有时是空的。。。所以我才把空头支票放进去。。
但是对于这个实现,我认为我的索引配置是无用的?对吗?如果是这样的话,如何让我的自定义谓词使用索引?
4) 这最终将在大约70个客户端(即70个不同的连续查询)的生产代码中工作,映射大小大约为50000。这样合适吗?
谨致问候