写入Oracle Coherence缓存时出现java.io.NotSerializableException

时间:2016-02-23 09:55:38

标签: preloading oracle-coherence notserializableexception

我有2个存储启用的缓存节点,我试图用于预加载缓存。这两个存储启用节点将加载大约100万个帐户。键和值都是String个对象,我试图写入缓存。我正在使用InvocationService.execute()方法异步调用预加载任务:

for (Map.Entry<Member, LoaderInvocable> entry : mappedWork.entrySet()) {
    Member member = entry.getKey();
    LoaderInvocable task = entry.getValue();
    invocationService.execute(task, Collections.singleton(member), null);
}

LoaderInvocable是一个实现InvocableSerializable接口的类,它的run()方法已被重写,以执行从数据库读取和写入的实际工作。高速缓存中。

InvocationService在coherence配置文件中定义如下:

<invocation-scheme>
      <scheme-name>
      InvocationScheme</scheme-name>
      <service-name>
      LoaderInvocationService</service-name>
      <autostart system-property="tangosol.coherence.invocation.autostart">true</autostart>
 </invocation-scheme>   

以下是我得到的例外情况:

2016-02-22 17:16:24,612 [pool-1-thread-1] ERROR (support.context.SessionExecutable) Caught exception from SessionExecutable.execute()
(Wrapped) java.io.NotSerializableException: com.oracle.common.collections.ConcurrentLinkedQueue
    at com.tangosol.util.Base.ensureRuntimeException(Base.java:289)
    at com.tangosol.util.Base.ensureRuntimeException(Base.java:270)
    at com.tangosol.coherence.component.util.daemon.queueProcessor.packetProcessor.PacketPublisher.packetizeMessage(PacketPublisher.CDB:28)
    at com.tangosol.coherence.component.util.daemon.queueProcessor.packetProcessor.PacketPublisher$InQueue.add(PacketPublisher.CDB:8)
    at com.tangosol.coherence.component.util.daemon.queueProcessor.packetProcessor.PacketPublisher.post(PacketPublisher.CDB:1)
    at com.tangosol.coherence.component.net.Message.dispatch(Message.CDB:77)
    at com.tangosol.coherence.component.net.Message.post(Message.CDB:1)
    at com.tangosol.coherence.component.util.daemon.queueProcessor.service.Grid.post(Grid.CDB:2)
    at com.tangosol.coherence.component.util.daemon.queueProcessor.service.Grid.send(Grid.CDB:1)
    at com.tangosol.coherence.component.util.daemon.queueProcessor.service.grid.InvocationService.execute(InvocationService.CDB:33)
    at com.tangosol.coherence.component.util.safeService.SafeInvocationService.execute(SafeInvocationService.CDB:1)

。 。 。 。 。

Caused by: java.io.NotSerializableException: com.oracle.common.collections.ConcurrentLinkedQueue
    at java.io.ObjectOutputStream.writeObject0(ObjectOutputStream.java:1180)
    at java.io.ObjectOutputStream.defaultWriteFields(ObjectOutputStream.java:1528)
    at java.io.ObjectOutputStream.writeSerialData(ObjectOutputStream.java:1493)
    at java.io.ObjectOutputStream.writeOrdinaryObject(ObjectOutputStream.java:1416)
    at java.io.ObjectOutputStream.writeObject0(ObjectOutputStream.java:1174)
    at java.io.ObjectOutputStream.writeObject(ObjectOutputStream.java:346)
    at java.util.Hashtable.writeObject(Hashtable.java:988)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:601)
    at java.io.ObjectStreamClass.invokeWriteObject(ObjectStreamClass.java:975)
    at java.io.ObjectOutputStream.writeSerialData(ObjectOutputStream.java:1480)
    at java.io.ObjectOutputStream.writeOrdinaryObject(ObjectOutputStream.java:1416)
    at java.io.ObjectOutputStream.writeObject0(ObjectOutputStream.java:1174)
    at java.io.ObjectOutputStream.defaultWriteFields(ObjectOutputStream.java:1528)
    at java.io.ObjectOutputStream.defaultWriteObject(ObjectOutputStream.java:438)
    at com.tangosol.coherence.Component.writeObject(Component.CDB:1)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:601)
    at java.io.ObjectStreamClass.invokeWriteObject(ObjectStreamClass.java:975)
    at java.io.ObjectOutputStream.writeSerialData(ObjectOutputStream.java:1480)
    at java.io.ObjectOutputStream.writeOrdinaryObject(ObjectOutputStream.java:1416)
    at java.io.ObjectOutputStream.writeObject0(ObjectOutputStream.java:1174)
    at java.io.ObjectOutputStream.defaultWriteFields(ObjectOutputStream.java:1528)
    at java.io.ObjectOutputStream.defaultWriteObject(ObjectOutputStream.java:438)
    at com.tangosol.coherence.Component.writeObject(Component.CDB:1)

似乎有一半的帐户已成功缓存。可以是特定于节点的问题吗?两个启用存储的缓存节点都使用相同的群集配置位于同一服务器上。从日志中可以清楚地看到两个节点都成功加入了集群。

1 个答案:

答案 0 :(得分:0)

感谢Praveen。我已经实现了PortableObject界面,而不再面对NotSerializableException了。但现在我正面临一个新问题。第二个节点没有调用任务并且在日志中没有任何异常地离开集群。

我使用InvocationObserver表示memberLeft()群集。我实施readExternal()writeExternal()序列化方法可能有问题吗?以下是实施:

@Override
public void readExternal(PofReader paramPofReader) throws IOException {
    // TODO Auto-generated method stub

    cacheName = paramPofReader.readString(0);
    firstRow = paramPofReader.readLong(1);
    lastRow = paramPofReader.readLong(2);

}

@Override
public void writeExternal(PofWriter paramPofWriter) throws IOException {
    // TODO Auto-generated method stub
    paramPofWriter.writeString(0, cacheName);
    paramPofWriter.writeLong(1, firstRow);
    paramPofWriter.writeLong(2, lastRow);
}