问题
searching for a long time, but didn't find any answer on that one:
I have a server and I have a client. The server should receive an object via ObjectInputStream
and ObjectOutputStream
. That already works for any class
, known on the server.
Now I want to send an Object
of a class
the server doesn't know. He only knows the interface of that class. And that obviously fails...
How can I avoid the ClassNotFoundException
? I thought interfaces were the solution. I only want to access the functions I know by the interface, but Java wants to have the class anyway.
Thank you.
回答1:
There is no way. To be able to execute a method on an object, you need to have the byte-code of the concrete class of the object. Its interface isn't sufficient.
回答2:
Object of some class may exist in JVM only if JVM has this class loaded. Probably instead of sending objects of unknown type, you better send some well-known data structure that describes the object, i.e. HashMap. So, instead of doing:
MySecretClass o = new MySecretClass ();
o.setFoo ("Hello, World!");
o.setBar (123);
send (o);
you do the following:
Map o = new HashMap ();
o.put ("foo", "Hello, World!");
o.put ("bar", 123);
send (o);
回答3:
You need the particular class' bytecode on server, so it won't work as you imagined.
You could send a proxy object of a class that would be known to both the client and the server. The proxy would contain the object of the class unknown to the server and its class would be stored in the proxy as a byte array. The proxy class would be Externalizable and would use Classloader.defineClass to dynamically create the unknown class in the server JVM when the proxy object is deserialized (using the byte array with class definition passed from the client). It won't be exactly fast, but could be optimized, like do not send and load definition of a class twice etc.
In case you need to call the interface specific methods directly on the object passed from client, make the proxy implement your interface and use dynamic proxy pattern on the proxy object (java.lang.reflect.Proxy/InvocationHandler) to pass calls to the proxied object of the previously unknown class.
It's rather complicated, but could be done like this, I believe.
来源:https://stackoverflow.com/questions/15090069/sending-java-object-of-an-unknown-class