绑定RMI服务时抛出ServerException

时间:2009-09-28 14:09:16

标签: java exception rmi

我正在尝试将简单的echo服务器构建为RMI应用程序(按照Sun教程中的描述逐步进行)。

所有源代码如下所示,非常简单:

package test;

import java.rmi.Remote;
import java.rmi.RemoteException;

public interface EchoServer extends Remote {
    public String sendString (String str) throws RemoteException;        
}

package test;

import java.rmi.server.UnicastRemoteObject;
import java.rmi.RemoteException;

public class EchoServerImpl extends UnicastRemoteObject implements EchoServer {

    public EchoServerImpl () throws RemoteException {
        super ();
    }

    public String sendString (String str) throws RemoteException {
        return str.toUpperCase();
    }
}

package test;

import java.rmi.Naming;

public class RMIServer {

    public RMIServer () {
        try {
            EchoServer eServer = new EchoServerImpl ();
            Naming.rebind ("rmi://localhost:1099/EchoService", eServer); // <--exception
        } catch (Exception e) {
            e.printStackTrace ();
        }
    }

    public static void main(String[] args) {
        new RMIServer ();
    }
}

我用rmic编译代码,我看到文件EchoServerImpl_Stub.class。之后我运行'rmiregistry',然后我启动RMIServer。那一刻我看到ServerException:

java.rmi.ServerException: RemoteException occurred in server thread; nested exception is: 
    java.rmi.UnmarshalException: error unmarshalling arguments; nested exception is: 
    java.lang.ClassNotFoundException: test.EchoServerImpl_Stub
    at sun.rmi.server.UnicastServerRef.oldDispatch(Unknown Source)
    at sun.rmi.server.UnicastServerRef.dispatch(Unknown Source)
    at sun.rmi.transport.Transport$1.run(Unknown Source)
    at java.security.AccessController.doPrivileged(Native Method)
    at sun.rmi.transport.Transport.serviceCall(Unknown Source)
    at sun.rmi.transport.tcp.TCPTransport.handleMessages(Unknown Source)
    at sun.rmi.transport.tcp.TCPTransport$ConnectionHandler.run0(Unknown Source)
    at sun.rmi.transport.tcp.TCPTransport$ConnectionHandler.run(Unknown Source)
    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)
    at sun.rmi.transport.StreamRemoteCall.exceptionReceivedFromServer(StreamRemoteCall.java:255)
    at sun.rmi.transport.StreamRemoteCall.executeCall(StreamRemoteCall.java:233)
    at sun.rmi.server.UnicastRef.invoke(UnicastRef.java:359)
    at sun.rmi.registry.RegistryImpl_Stub.rebind(Unknown Source)
    at java.rmi.Naming.rebind(Naming.java:160)
    at test.RMIServer.(RMIServer.java:10)
    at test.RMIServer.main(RMIServer.java:17)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
    at java.lang.reflect.Method.invoke(Method.java:597)
    at com.intellij.rt.execution.application.AppMain.main(AppMain.java:90)
Caused by: java.rmi.UnmarshalException: error unmarshalling arguments; nested exception is: 
    java.lang.ClassNotFoundException: test.EchoServerImpl_Stub
    at sun.rmi.registry.RegistryImpl_Skel.dispatch(Unknown Source)
    at sun.rmi.server.UnicastServerRef.oldDispatch(Unknown Source)
    at sun.rmi.server.UnicastServerRef.dispatch(Unknown Source)
    at sun.rmi.transport.Transport$1.run(Unknown Source)
    at java.security.AccessController.doPrivileged(Native Method)
    at sun.rmi.transport.Transport.serviceCall(Unknown Source)
    at sun.rmi.transport.tcp.TCPTransport.handleMessages(Unknown Source)
    at sun.rmi.transport.tcp.TCPTransport$ConnectionHandler.run0(Unknown Source)
    at sun.rmi.transport.tcp.TCPTransport$ConnectionHandler.run(Unknown Source)
    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)
Caused by: java.lang.ClassNotFoundException: test.EchoServerImpl_Stub
    at java.net.URLClassLoader$1.run(Unknown Source)
    at java.security.AccessController.doPrivileged(Native Method)
    at java.net.URLClassLoader.findClass(Unknown Source)
    at java.lang.ClassLoader.loadClass(Unknown Source)
    at java.lang.ClassLoader.loadClass(Unknown Source)
    at java.lang.ClassLoader.loadClassInternal(Unknown Source)
    at java.lang.Class.forName0(Native Method)
    at java.lang.Class.forName(Unknown Source)
    at sun.rmi.server.LoaderHandler.loadClass(Unknown Source)
    at sun.rmi.server.LoaderHandler.loadClass(Unknown Source)
    at java.rmi.server.RMIClassLoader$2.loadClass(Unknown Source)
    at java.rmi.server.RMIClassLoader.loadClass(Unknown Source)
    at sun.rmi.server.MarshalInputStream.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)
    ... 12 more  

我认为这是一个常见问题,而且可能与错误的部署有关。如何解决?

1 个答案:

答案 0 :(得分:0)

我认为这是你的 rmiregistry 类路径。 rmiregistry 本身需要可以访问test.EchoServer接口。在运行 rmiregistry 之前设置CLASSPATH环境变量,例如

C:\>set CLASSPATH="MyBinFolder"
C:\>rmiregistry

此外, rmic 是Java 5之前的宿醉。不再需要再运行它。只需正常运行您的服务器和客户端,代理将动态创建。

此致 MK

相关问题