Re: Apache tribes deserialization issues

2012-01-09 Thread Filip Hanik - Dev Lists

your workaround is valid
I would not expect thread context class loader to work, as the thread for 
deserializing is the thread from the tribes TCP thread pool


On 12/29/2011 5:06 AM, Madhav Bhargava wrote:

Hi All,

We are using Apache tribes library for presence and inter node
communication within an OSGi runtime environment. We have a central node
(say node A) receiving messages from other nodes ( say node B, C). The
message passed is a custom class which is present as part of the API
defined in a separate OSGi bundle. This custom class is Serializable.

When a send method is invoked on the GroupChannel to send the custom class
message to node A then it throws an exception with the following stack
trace:

java.lang.ClassNotFoundException: com.sap.nm.NodeSnapshot
at
org.eclipse.osgi.internal.loader.BundleLoader.findClassInternal(BundleLoader.java:513)
at
org.eclipse.osgi.internal.loader.BundleLoader.findClass(BundleLoader.java:429)
at
org.eclipse.osgi.internal.loader.BundleLoader.findClass(BundleLoader.java:417)
at
org.eclipse.osgi.internal.baseadaptor.DefaultClassLoader.loadClass(DefaultClassLoader.java:107)
at java.lang.ClassLoader.loadClass(Unknown Source)
at java.lang.Class.forName0(Native Method)
at java.lang.Class.forName(Unknown Source)
at java.io.ObjectInputStream.resolveClass(Unknown Source)
at java.io.ObjectInputStream.readNonProxyDesc(Unknown Source)
at java.io.ObjectInputStream.readClassDesc(Unknown Source)
at java.io.ObjectInputStream.readOrdinaryObject(Unknown Source)
at java.io.ObjectInputStream.readObject0(Unknown Source)
at java.io.ObjectInputStream.readObject(Unknown Source)
at
org.apache.catalina.tribes.io.XByteBuffer.deserialize(XByteBuffer.java:568)
at
org.apache.catalina.tribes.io.XByteBuffer.deserialize(XByteBuffer.java:554)
at
org.apache.catalina.tribes.group.GroupChannel.messageReceived(GroupChannel.java:261)
at
org.apache.catalina.tribes.group.ChannelInterceptorBase.messageReceived(ChannelInterceptorBase.java:84)
at
org.apache.catalina.tribes.group.ChannelInterceptorBase.messageReceived(ChannelInterceptorBase.java:84)
at
org.apache.catalina.tribes.group.ChannelCoordinator.messageReceived(ChannelCoordinator.java:253)
at
org.apache.catalina.tribes.transport.ReceiverBase.messageDataReceived(ReceiverBase.java:287)
at
org.apache.catalina.tribes.transport.nio.NioReplicationTask.drainChannel(NioReplicationTask.java:212)
at
org.apache.catalina.tribes.transport.nio.NioReplicationTask.run(NioReplicationTask.java:101)
at java.util.concurrent.ThreadPoolExecutor$Worker.runTask(Unknown Source)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(Unknown Source)
at java.lang.Thread.run(Unknown Source)

The problem is that OSGi has a totally different class loading mechanism
that what is followed in java/j2ee applications. We looked at the tribes
source code and found out that following piece of code is the culprit:

Class: XByteBuffer.java

public static Serializable deserialize(byte[] data, int offset, int length)
 throws IOException, ClassNotFoundException, ClassCastException {
 return deserialize(data,offset,length,null);
 }

Instead of passing null to the ClassLoader[] (last argument), Thread
context classloader should have been passed. What is happening is that the
tribes is trying to load the class with the tribes class loader and not
using the current thread classloader and is therefore not able to find the
custom class.

A workaround that we have adopted now is to use byte[] and set
Channel.SEND_OPTIONS_BYTE_MESSAGE option while sending the message. We then
explicitly recreate the object in the ChannelListener in bundle A from the
bytes message.  This is possible because in GroupChannel byte messages are
not deserialized using XByteBuffer.

It will great if anyone can investigate this issue.

Best Regards,
Madhav




-
To unsubscribe, e-mail: users-unsubscr...@tomcat.apache.org
For additional commands, e-mail: users-h...@tomcat.apache.org



Apache tribes deserialization issues

2011-12-29 Thread Madhav Bhargava
Hi All,

We are using Apache tribes library for presence and inter node
communication within an OSGi runtime environment. We have a central node
(say node A) receiving messages from other nodes ( say node B, C). The
message passed is a custom class which is present as part of the API
defined in a separate OSGi bundle. This custom class is Serializable.

When a send method is invoked on the GroupChannel to send the custom class
message to node A then it throws an exception with the following stack
trace:

java.lang.ClassNotFoundException: com.sap.nm.NodeSnapshot
at
org.eclipse.osgi.internal.loader.BundleLoader.findClassInternal(BundleLoader.java:513)
at
org.eclipse.osgi.internal.loader.BundleLoader.findClass(BundleLoader.java:429)
at
org.eclipse.osgi.internal.loader.BundleLoader.findClass(BundleLoader.java:417)
at
org.eclipse.osgi.internal.baseadaptor.DefaultClassLoader.loadClass(DefaultClassLoader.java:107)
at java.lang.ClassLoader.loadClass(Unknown Source)
at java.lang.Class.forName0(Native Method)
at java.lang.Class.forName(Unknown Source)
at java.io.ObjectInputStream.resolveClass(Unknown Source)
at java.io.ObjectInputStream.readNonProxyDesc(Unknown Source)
at java.io.ObjectInputStream.readClassDesc(Unknown Source)
at java.io.ObjectInputStream.readOrdinaryObject(Unknown Source)
at java.io.ObjectInputStream.readObject0(Unknown Source)
at java.io.ObjectInputStream.readObject(Unknown Source)
at
org.apache.catalina.tribes.io.XByteBuffer.deserialize(XByteBuffer.java:568)
at
org.apache.catalina.tribes.io.XByteBuffer.deserialize(XByteBuffer.java:554)
at
org.apache.catalina.tribes.group.GroupChannel.messageReceived(GroupChannel.java:261)
at
org.apache.catalina.tribes.group.ChannelInterceptorBase.messageReceived(ChannelInterceptorBase.java:84)
at
org.apache.catalina.tribes.group.ChannelInterceptorBase.messageReceived(ChannelInterceptorBase.java:84)
at
org.apache.catalina.tribes.group.ChannelCoordinator.messageReceived(ChannelCoordinator.java:253)
at
org.apache.catalina.tribes.transport.ReceiverBase.messageDataReceived(ReceiverBase.java:287)
at
org.apache.catalina.tribes.transport.nio.NioReplicationTask.drainChannel(NioReplicationTask.java:212)
at
org.apache.catalina.tribes.transport.nio.NioReplicationTask.run(NioReplicationTask.java:101)
at java.util.concurrent.ThreadPoolExecutor$Worker.runTask(Unknown Source)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(Unknown Source)
at java.lang.Thread.run(Unknown Source)

The problem is that OSGi has a totally different class loading mechanism
that what is followed in java/j2ee applications. We looked at the tribes
source code and found out that following piece of code is the culprit:

Class: XByteBuffer.java

public static Serializable deserialize(byte[] data, int offset, int length)
throws IOException, ClassNotFoundException, ClassCastException {
return deserialize(data,offset,length,null);
}

Instead of passing null to the ClassLoader[] (last argument), Thread
context classloader should have been passed. What is happening is that the
tribes is trying to load the class with the tribes class loader and not
using the current thread classloader and is therefore not able to find the
custom class.

A workaround that we have adopted now is to use byte[] and set
Channel.SEND_OPTIONS_BYTE_MESSAGE option while sending the message. We then
explicitly recreate the object in the ChannelListener in bundle A from the
bytes message.  This is possible because in GroupChannel byte messages are
not deserialized using XByteBuffer.

It will great if anyone can investigate this issue.

Best Regards,
Madhav

-- 
When I tell the truth, it is not for the sake of convincing those who do
not know it, but for the sake of defending those that do