2016-09-16 197 views
0
  1. 当我启动GUI时,它启动一个新线程。关闭Java RMI服务器

    final Server myServer = new Server(); 
    final Thread t1 = new Thread(myServer, "T1"); 
    t1.start(); 
    
  2. 的GUI只有一个按钮,将在单击停止线程:

    final JButton btnStartServer = new JButton("Stop server"); 
    btnStartServer.addActionListener(new ActionListener() { 
        public void actionPerformed(ActionEvent arg0) { 
         myServer.stop(); 
        } 
    }); 
    
  3. 线程将创建一个对象TrackingServiceImpl它是Java RMI服务器。线程本身看起来是这样的:

    class Server implements Runnable { 
        private volatile boolean exit = false; 
    
        public void run() { 
    
         try { 
          TrackingService server1 = new TrackingServiceImpl(); 
    
          TrackingService serverInstance, stub = null; 
          Registry registry = null; 
    
          while (!exit) { 
           serverInstance = ((TrackingServiceImpl) server1).getInstance(); 
           stub = (TrackingService) UnicastRemoteObject.exportObject((TrackingService) serverInstance, 0); 
           registry = LocateRegistry.createRegistry(4444); 
           registry.bind("TrackingService", stub); 
           System.out.println("Tracking service has started at port " + 4444); 
          } 
    
          System.out.println("Server is stopping...."); 
          registry.unbind("TrackingService"); 
          UnicastRemoteObject.unexportObject(registry, false); 
         } catch (Exception e) { 
    
         } 
    
        } 
    
        public void stop() { 
         exit = true; 
        } 
    } 
    
  4. 现在,如果我的任何客户端连接到服务器之前,点击按钮,代码工作。客户端将无法连接到服务器。但是,如果我让客户端连接到服务器,然后单击按钮,即使服务器应该已经停止(注册表未绑定和导出),客户端仍然可以调用服务器上的方法。

在此先感谢!

+0

_“即使服务器应该已经停止(注册表未绑定并导出)。”_这是一个假设还是一个事实? –

+0

这难道不能阻止它吗? registry.unbind(“TrackingService”); UnicastRemoteObject.unexportObject(registry,false); 我的意思是,如果我在连接任何客户端之前停止服务器,它不会让客户端连接。但是,如果我在连接客户端后停止它,它似乎不会阻止它,客户端仍然能够调用方法。 – Teddy

+0

@泰迪不,解除绑定并停止注册表。什么都没有停止远程对象。已持有存根的客户端可以继续调用它。看到我的答案。 – EJP

回答

0

这一切都没有任何意义。您的代码无法正确执行。您不需要循环或exit变量或Runnable或线程。一旦远程对象被构造,导出和绑定,客户端就可以使用远程方法调用。要停止它,只需取消绑定并用UnicastRemoteObject.unexportObject()将其取出。注意目前你只是取消注册注册表。没有必要这样做。

+0

我把它做成了一个线程,因为我希望GUI能够启动Java RMI服务器并停止正在运行的当前程序。停止RMI服务器不应该关闭我的GUI。它确实执行,请阅读我在线程中的最后一点。 – Teddy

+0

您不需要线程来启动注册表或导出远程对象,因为它们不会阻止操作,也不需要循环。你的代码永远循环抛出忽略'ExportExceptions'。 – EJP

+0

尝试导出存根,但它表示存根未导出。有任何想法吗? stub =(TrackingService)UnicastRemoteObject.unexportObject((TrackingService)serverInstance,0); – Teddy