I'm frensh so sorry for my english.
I'm trying to start a server rmi but the application stop whitout error :
Here my code:
public class Server {
public static void main(String[] args) {
try {
RemoteFunction skeleton = (RemoteFunction) UnicastRemoteObject.exportObject(new FunctionImpl(), 0);
int port = Integer.parseInt(Jndiprop.getString("port"));
Registry registry = LocateRegistry.createRegistry(port);
registry.rebind(Jndiprop.getString("url"), skeleton);
System.out.println("Rmi start");
} catch (Exception e) {
e.printStackTrace();
}
}
}
the port and the url are ok.
Someone can help me ?
You must store the Registry in a static variable. Otherwise it can be garbage-collected, which leads to a train of events that allows the whole JVM to exit.
Related
I've just started RMI programming recently and had complete most of the parts for the assignment requirements. But there was this question in my head where one of the requirements is supporting multiple threads. Basically in which part should the multi thread be implemented?
Should I make the Server class Runnable or make the objects that are being created in the Server class Runnable?
Here's the code of my Server class:
public class Server {
public static void main(String args[]) {
String portNum = "4444";
try {
Account_Server_Controller accountController = new Account_Server_Controller();
BookCategory_Server_Controller categoryController = new BookCategory_Server_Controller();
Book_Server_Controller bookController = new Book_Server_Controller();
BookActivity_Server_Controller bookActivityController = new BookActivity_Server_Controller();
startRegistry(Integer.parseInt(portNum));
Naming.rebind(ServerLocater.getAccountRegistryURL(), accountController);
Naming.rebind(ServerLocater.getBookRegistryURL(), bookController);
Naming.rebind(ServerLocater.getCategoryRegistryURL(), categoryController);
Naming.rebind(ServerLocater.getBookActivityRegistryURL(), bookActivityController);
System.out.println("Server is Ready.");
} catch (NumberFormatException | MalformedURLException | RemoteException e) {
System.out.println("Exception in Server.main: " + e);
}
}
private static void startRegistry(int rmiPortNum) throws RemoteException {
try {
Registry registry = LocateRegistry.getRegistry(rmiPortNum);
registry.list();
} catch (RemoteException ex) {
System.out.println("RMI registry is not located at port " + rmiPortNum);
Registry registry = LocateRegistry.createRegistry(rmiPortNum);
System.out.println("RMI registry created at port " + rmiPortNum);
}
}
}
No. You don't have to start any threads or implement any Runnables.
You just have to make sure that your remote method implementations are thread-safe.
Hi all I have question related with Pyro4 and Java. My question is how can I send information between RMI server in Java and clients RMI in Python?.
This is my code, I don't have any errors but I can't send anything.
Java Code:
implements ReceiveMessageInterface
{
int thisPort;
String thisAddress;
Registry registry; // rmi registry for lookup the remote objects.
// This method is called from the remote client by the RMI.
// This is the implementation of the �gReceiveMessageInterface�h.
public void receiveMessage(String x) throws RemoteException
{
System.out.println(x);
}
public RmiServer() throws RemoteException
{
try{
// get the address of this host.
thisAddress= (InetAddress.getLocalHost()).toString();
}
catch(Exception e){
throw new RemoteException("can't get inet address.");
}
thisPort=3232; // this port(registry�fs port)
System.out.println("this address="+thisAddress+",port="+thisPort);
try{
// create the registry and bind the name and object.
registry = LocateRegistry.createRegistry( thisPort );
registry.rebind("rmiServer", this);
}
catch(RemoteException e){
throw e;
}
}
static public void main(String args[])
{
try{
RmiServer s=new RmiServer();
}
catch (Exception e) {
e.printStackTrace();
System.exit(1);
}
}
}
And this is my code in Python:
import Pyro4
proxy=Pyro4.core.Proxy("PYRONAME:PhDJara/127.0.1.1")
print("5*11=%d" % proxy.multiply(5,11)) print("'x'*10=%s" %
proxy.multiply('x',10))
Thanks for your help.
jarain78
What makes you think that you should be able to connect these two?
Pyro4 is only conceptually similar to Java's RMI, but they're two totally different protocols. You cannot connect them directly.
If you want to write a Python client using Pyro and talk to a server, that server has to be a Pyro server. The only way to create one in Java is by using Jython + Pyro.
I'm trying to get a RMI program to work. So far, the server starts up correctly but the client fails casting the remote object to the interface.
Exception in thread "AWT-EventQueue-0" java.lang.ClassCastException:
com.sun.proxy.$Proxy0 cannot be cast to MonitorClient.InterfaceMonitor
All other answers I've found are for cases where the end user has cast the equivalent of InterfaceMonitorImpl (unknown to the client) instead of the Interface instead. This is not my case and I'm really at a loss here — RMI is nightmare-ish.
Server side
Main:
InterfaceMonitor obj;
try {
LocateRegistry.createRegistry(1099);
InterfaceMonitor stub = (InterfaceMonitor) UnicastRemoteObject.exportObject(new InterfaceMonitorImpl(), 0);
Registry registry = LocateRegistry.getRegistry();
registry.bind("imon", stub);
System.out.println("Server ready");
} catch (RemoteException | AlreadyBoundException ex) {
System.out.println("Server error: " + ex.toString());
}
InterfaceMonitor.java:
public interface InterfaceMonitor extends Remote {
int checkAge() throws RemoteException;
}
InterfaceMonitorImpl.java:
public class InterfaceMonitorImpl implements InterfaceMonitor {
public InterfaceMonitorImpl() throws RemoteException {
}
#Override
public int counter() throws RemoteException {
return 10;
}
}
Client side
try {
Registry reg = LocateRegistry.getRegistry(null);
InterfaceMonitor im = (InterfaceMonitor) reg.lookup("imon");
int counter = im.counter();
System.out.println("Counter: " + counter);
} catch (NotBoundException | RemoteException ex) {
Logger.getLogger(MonitorGUI.class.getName()).log(Level.SEVERE, null, ex);
}
The InterfaceMonitor.java is also on the client side.
Thanks for your time!
Obviously you must have two copies of InterfaceMonitor: one in MonitorClient and one in what may be something like MonitorServer. That makes two different classes. Not two copies of the same class. The class name, package, method declarations, inheritance, ... all have to be the same.
I am trying to establish two-communication between one server and two clients. This works very well when all programs run on the same machine but it doesn't work when I try using LAN network.
I got the error :
java.rmi.ConnectException: Connection refused to host: 192.168.1.24; nested exception is:
java.net.ConnectException: Connection timed out: connect
Here is the server code :
public class Server{
private Game partie; // The class Game extends UnicastRemoteObject and implements ServerInterface
public Server() throws RemoteException {
System.setProperty("java.rmi.server.hostname", "192.168.1.24");
partie = new Game();
LocateRegistry.createRegistry(1099);
try{
Naming.rebind("Server", partie);
}
catch(Exception e){
e.printStackTrace();
}
}
public static void main(String argv[]) throws RemoteException{
new Server();
}
}
Here is the constructor of the client code :
public Client(String aName, String aServerAdress) throws RemoteException {
super();
name = aName;
ServerAdress = aServerAdress; // = "192.168.1.24"
theRegistry = LocateRegistry.getRegistry(ServerAdress);
try {
serverInterface = (ServerInterface) theRegistry.lookup("Server");
} catch (NotBoundException e1) {
e1.printStackTrace();
}
try {
theRegistry.bind(name, this); // For two-way communication
} catch (AlreadyBoundException e) {
e.printStackTrace();
}
serverInterface.registerClient(name);
}
Where registerClient(String name) code is approximately (in Game class) :
cd_client = (ClientInterface) Naming.lookup("rmi://127.0.0.1/" + name);
All firewalls are disabled.
I have been working on this problems for many hours and I have still not found what is wrong. I would really appreciate if you could help me a bit.
Thank you
Change all occurances of 127.0.0.1 (except registry binding) to your LAN IP address (192.168.1.24 in your case)
127.0.0.1 is a Loopback address:
"Loopback (loop-back) describes ways of routing electronic signals,
digital data streams, or flows of items from their originating
facility back to the receiving end of the source without intentional
processing or modification. This is primarily a means of testing the
transmission or transportation infrastructure."
-- from Wikipedia
I am trying to start/stop an Endpoint web service in a separate thread from my main program with the click of a button. Starting works fine, i am able to access all my WebMethods without issue. The problem is, when i click the stop button to try and stop the web service endpoint, i get an exception and i don't know what it is. I am new to Java as well.
Thanks in advance.
Excetion thrown at 'ep.stop()':
WebService Running On: http://0.0.0.0:9898/
Exception in thread "Thread-0" java.lang.NullPointerException
at com.sun.xml.internal.ws.transport.http.server.ServerMgr.removeContext(Unknown Source)
at com.sun.xml.internal.ws.transport.http.server.HttpEndpoint.stop(Unknown Source)
at com.sun.xml.internal.ws.transport.http.server.EndpointImpl.stop(Unknown Source)
at com.simba.Server.startWebSrv(Server.java:27)
at com.simba.Server.run(Server.java:13)
Server class:
import javax.xml.ws.Endpoint;
public class Server extends Thread {
public volatile boolean active = true;
private Endpoint ep;
private String ip = "0.0.0.0";
public void run(){
ep = Endpoint.publish("http://" + ip + ":9898/", new SWS());
startWebSrv();
}
private void startWebSrv(){
synchronized(this){
try {
while (active) {
System.out.println("WebService Running On: http://" + ip + ":9898/");
wait();
}
}catch (InterruptedException e) {
e.printStackTrace();
}finally{
if(!active){
ep.stop();
System.out.println("WebService Stopped!");
}
}
}
}
}
How i am attempting to stop the service/thread from my main program:
MenuItem mntmToggleWebservice = new MenuItem(menu_4, SWT.NONE);
mntmToggleWebservice.addSelectionListener(new SelectionAdapter() {
#Override
public void widgetSelected(SelectionEvent e) {
synchronized(srv){
srv.active = false;
srv.notifyAll();
}
}
});
mntmToggleWebservice.setText("Toggle WebService");
Problem solved!
Don't use '0.0.0.0'. For some reason, creating the service on '0.0.0.0' works (uses the machine's actual ip), but Endpoint.stop() doesn't not play well with it.
Instead I just used 'System.getEvn('COMPUTERNAME')' and create the service with the machine name.
You can use the "input" to block the run of program
public class ServiceMain {
private static void DoNothing() {
}
public static void main(String[] args) {
String address = "http://127.0.0.1:7775/hb";
Endpoint ep = Endpoint.publish(address, new ServiceImp());
Scanner scanIn=new Scanner(System.in);
System.out.println("Web Service Release Successfully!");
while(!scanIn.next().equals("stop")){
DoNothing();
}
scanIn.close();
ep.stop();
System.out.println("Web Service Close Successfully!");
}
}