I'm writing an application which uses sshj library for SSH connections. User opens Connect Dialog from menu, types login data and clicks Connect button to establish a connection. Then the user performs various operations from different panels and frames. My question is: where should I keep this connection to make it available to every panel and frame that needs it until the user clicks Disconnect button? I thought about static field in some custom class but I'm not convinced to do so. What are your ideas?
-
Keeping a ssh connection alive is not quite the same as asking where to store the connection instance.. :-) – Patrick Oct 28 '11 at 00:14
-
what's the framework do you use? – Njax3SmmM2x2a0Zf7Hpd Dec 10 '13 at 03:58
3 Answers
It sounds like you are interested in some type of pool.
You can do this in different ways. One way is to have a class that handles all the connections, which is a singleton, sort of. Then you simply ask the pool for a connection, for instance
SSHConnection con = ConnectionPool.getConnection(host, port);
You could also use a proxy for this. In a proxy, you actually get a placeholder instead of the actual connection. The proxy shares information with other instances, sort of like
class ConnectionProxy {
private static SSHConnection connection;
}
the connection variable is shared, and when you create a new ConnectionProxy, you will actually get the old connection, but it looks like you get a new connection.
Another option is to simply pass the instance around to all classes that needs it. This will allow you to keep track of who does what, but you will loose the flexibility of getting a connection from wherever you want.
Passing an instance around will help if you are debugging though, think of it like this. You are in a crowded room and you have a some money laying in a box that needs a key to open. If you hand that key to one person (the class that needs it) and leave the room and come back and the money is gone, you can blame that person. If instead you just leave the key on the table next to the box (the instance is global) and leave the room, come back and the money is gone, then good luck finding out who took it.
References:
*] Proxy pattern - WikiPedia
Proxy example
More specifically, it could look something like this:
public class ConnectionProxy implements Connectable {
// where Connectable is some shared interface between ConnectionProxy
// and SSHConnection. The proxy should "look like" a connection, it just
// hides the actual connection behind the scenes.
private static SSHConnection connection;
public ConnectionProxy() { }
public ConnectionProxy(String host, int port) {
connection = new SSHConnection(host, port);
}
public void connect(String host, int port) {
if (isConnected()) {
return;
}
connection = new SSHConnection(host, port);
}
public void reconnect() {
connection = new SSHConnection(connection.getHost(), connection.getPort());
}
public boolean isConnected() {
return connection != null && connection.isConnected();
}
}
You use the class by either instantiating it or connecting it.
class Program {
public void sendMessage() {
ConnectionProxy proxy = new ConnectionProxy();
if (!proxy.isConnected()) {
// I guess noone connected it
return;
}
proxy.sendBytes();
}
}
And in your connection dialog you instantiate or connect the ConnectionProxy. You could add support for several connections, i.e. different hosts and ports, just by making the variable connection a list instead, and checking the host and port for the right connection. You basically create a pool of connections, but to the client class it looks like it is creating the connection.

- 17,669
- 6
- 70
- 85
-
So the use of proxy pattern would look like this: after user clicks connect I create instance of SSHConnection class and then use this instance to set connection field in ConnectionProxy class, right? Then I create instances of ConnectionProxy wherever I need to. When user clicks disconnect I close connection and set connection to null. – Radek Wyroslak Oct 28 '11 at 11:27
-
Doesn't matter where you put it, so long as you provide a getter
method for retrieving it, and that getting method is public
.
I think it's more a question of where it logically belongs. If it's a property of the application (as opposed to a window, frame, profile, whatever) put the getter in the main application class.

- 33,527
- 7
- 88
- 126
Design-wise, I'd recommend wrapping the operations you can perform over SSH in a separate class (RemoteCommands
or some such), and injecting (setting as a property) an instance of this class everywhere you need to perform a remote command from.
If this seems like a lot of extra boilerplate code because every single frame and panel needs it, this shouldn't say "I need a global variable" to you. It should say "I should reduce the number of components that directly execute remote commands".

- 39,073
- 9
- 82
- 134