Search code examples
javajtableclient-serverabstracttablemodel

How to organise a Server architecture with a GUI


I'm developing a Banking Client-Server architecture.

I want to know what is the most convenient way to organize the Server side. Does the Bank need to be the Server and the GUI in the same file ?

Because currently I have the server GUI which instantiates a Bank. This Bank has a list of Customer and each Customer has several Account.

  1. My first problem concerns a JTable in the server GUI. In fact a Bank store an ArrayList of every operations previously done by the clients. I wrote an implementation of AbstractTableModel which also store an ArrayList. The problem is that the Server instantiate a Bank and a TableModel for the JTable. So, when the Bank adds an Operation in its ArrayList, the TableModel is not aware of that. How can I link these two without giving the TableModel to the Bank ?

  2. The second problem concerns the connection with the Client. The Server pass a Session interface to the Client when login/password are correct. Session contains Banking operations that a Client can do. Is it a security problem if the SessionImpl encapsulate the Bank instance ? Because in reality Session methods call the Bank ones. Session is the only remote Object between the Client and the Server but encapsulating the Bank gives me the impression that the Client can access to the Bank directly.


Solution

  • 1) You want your AbstractTableModel to take a Bank object in the constructor. The AbstractTableModel methods then delegates to the underlying list of operations on the Bank object.

    There are two ways to solve the what happens if the bank object changes problem.

    a) Assuming a Bank object with a method:

    public List<Operation> getOperations();
    

    You can just call getOperations() each time a request is made to the table model. For instance:

    public Object getValueAt(int row, int column) {
      return bank.getOperations().get(row)...
    }
    

    This is slow but a simple way to get updates.

    b) In the more complicated way you would have the AbstractTableModel register with the Bank object to receive an event when a new operation is added to the Bank. This would look like:

    public class BankTableModel extends AbstractTableModel {
      private List<Operation> operations;
    
      public BankTableModel(Bank bank) {
        operations = bank.getOperations();
        bank.addOperationEventListener(...);
      }
    
      public Object getValueAt(int row, int column) {
        return operations.get(row)...
      }
    }
    

    The problem with this is that RMI does not provide a mechanism for the server to talk to the client so both the server and client need to be RMI endpoints. See RMI Events.

    2) The whole point of RMI is you get a stub of the remote object that resides on the server. The stub allows you to call methods on the remote object as if that object was local. Don't worry about the security at this level especially in an academic setting.

    I would get rid of the Session object and just return the Bank object directly. If you are forwarding all your calls to the Bank object then you really just want to interact with the Bank object directly. In a more complicated system you may have justifiable reason for adding Proxy or Facade layers but I would keep it simple in this case.

    3) Your GUI and your Server should be two different objects. Your GUI is your client and there should be no GUI code at all on your server side.