1

I am building a small chat-room app in Java. What I am trying to do here is to send the current class ClientGUI instance (this) through a static ClientGUI reference member. The ServerApplication class is supposed to receive this current clientGUI reference through a regular static getter (done in ServerApplication.main).

After some tiresome debugging I still can't figure out how come the Server side reference remains null after receiving the ClientGUI ref (The getCurrentClientGuiReference() fails).

(Of course - the sent ref is initialized before it is being transferred to server side).

Is it not possible to transfer the current ref through a local static ref member? Perhaps I missed a something?

Bellow is the relevant code.

Thanks in advance.

Client side:

package chatApplication;

import java.net.*;
import java.awt.*;
import java.awt.event.*;
import java.io.BufferedReader;
import java.io.InputStreamReader;

import javax.swing.*;

public class ClientGUI implements StringConsumer, StringProducer 
{

//Graphic components
private JFrame frame;
private JButton btConnect,btSend;

private JTextField tfText, tfServerName, tfPort, tfNickName;
private JPanel north,south,center;
ActionListener listener;
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));

JLabel mainLable = new JLabel();

//Utilities and connection components
private ConnectionProxy consumer = null;
private ConnectionProxy producer = null;
private ClientDescriptor clientDescriptor = null;

//Connection creation switch
private boolean isConnection = false;

//Client details meant for ClientDescriptor 
static private String nickname = "Noname";
static private String serverAddress = "127.0.0.1";
static private String port = "1300";
static private ClientGUI currentClientGuiReference = null;

public ClientGUI()
{
    frame = new JFrame("Chit & Chat");
    listener = new ActionListener()
    {
        public void actionPerformed(ActionEvent event)
        {
            if (event.getSource() == btConnect)
            {

                if (isConnection == false)
                {
                    ClientGUI.nickname = tfNickName.getText();
                    ClientGUI.serverAddress = tfServerName.getText();
                    ClientGUI.port = tfPort.getText();
                    ClientGUI.currentClientGuiReference = ClientGUI.this;

                    clientDescriptor = new ClientDescriptor(nickname, serverAddress, port, currentClientGuiReference); // Identical though NOT related to serverapplication's clientdescriptor 
                    consumer = new ConnectionProxy(clientDescriptor, ClientGUI.this);

                    //Connecting client consumer as a producer
                    ClientGUI.this.addConsumer(consumer);                       

                    //Temporary text
                    mainLable.setText("Client consumer/producer thread is connected and running!");
                }

            }

            if (event.getSource() == btSend)
            {
                String outGoingMessageToChat = tfText.getText();
                producer.consume(outGoingMessageToChat); //sending outgoing msg to prducer.consume -->  writeutf
            }

        }       
    };

    btConnect = new JButton ("Connect to chat");
    btSend = new JButton ("Send Message");
    btConnect.addActionListener(listener);
    btSend.addActionListener(listener);

    tfText = new JTextField(50);
    tfPort = new JTextField(10);
    tfServerName = new JTextField(20);
    tfNickName = new JTextField(10);
    tfServerName.setText("127.0.0.1");
    tfPort.setText("1300");
    tfNickName.setText("Nickname");

    north = new JPanel();
    south = new JPanel();
    center = new JPanel();
    north.setBackground(Color.blue);
    south.setBackground(Color.gray);
    center.setBackground(Color.white);

    south.add(tfText);
    south.add(btSend);
    north.add(tfNickName,BorderLayout.WEST);
    north.add(tfServerName);
    north.add(tfPort);
    north.add(btConnect,BorderLayout.WEST);


    frame.addWindowListener(new WindowAdapter()
    {
        public void windowClosing (WindowEvent event)
        {
            ClientGUI.this.removeConsumer(clientDescriptor);
            frame.setVisible(false);
            frame.dispose();
            System.exit(0);
        }
    }
    );

    frame.add(north,BorderLayout.NORTH);
    frame.add(center,BorderLayout.CENTER);
    frame.add(south,BorderLayout.SOUTH);
}

public void go()
{
    ClientGUI.currentClientGuiReference = ClientGUI.this;
    frame.setSize(700,700);
    frame.setVisible(true);
    mainLable.setText("Hey! " +
            "Please enter a nickname, Server Address and a port in the text fields above" +
            " and press 'Connect to chat'"); 
    center.add(mainLable);
    frame.add(center, BorderLayout.WEST);
    if (isConnection == true)
    {
        mainLable.setText("Your details were sent.");
    }
}

@Override
public void addConsumer(StringConsumer consumer) 
{
    this.producer = (ConnectionProxy)consumer;

    //All actions completed - client thread producer/consumer is running.
    isConnection = true;
}

@Override
public void removeConsumer(StringConsumer sc) 
{
    consumer.removeConsumer(clientDescriptor);
}

@Override
public void consume(String inComingMessageFromChat) 
{
    //Temporary code
    mainLable.setText(inComingMessageFromChat);
}


public ConnectionProxy getConsumer() 
{
    return consumer;
}

public void setConsumer(ConnectionProxy consumer) 
{
    this.consumer = consumer;
}

/**
 * @param args
 */
public static void main(String[] args) 
{
    ClientGUI clientGUI = new ClientGUI();
    clientGUI.go();
}

public static String getNickname() {return nickname;}

public static String getServerAddress() {return serverAddress;}

public static String getPort() {return port;}

public static ClientGUI getCurrentClientGuiReference() {return currentClientGuiReference;}

}

Server side:

package chatApplication;

import java.net.*; 
import java.io.*;

public class ServerApplication {

public static int port = 1300;
public static int backlog = 5;

/**
 * @param args
 */
public static void main(String[] args) 
{


    //Server side network variables
    ServerSocket serverSocket = null;

    //MessageBoard object
    MessageBoard messageBoard = new MessageBoard(); 

    //Client side network variables
    Socket clientSocket = null;
    ClientDescriptor clientDescriptor = null;
    ConnectionProxy clientConnectionProxy = null;

    //Client details meant for ClientDescriptor 
    String clientNickname = "Noname";
    String clientServerAddress = "127.0.0.1";
    String clientPort = "1300";
    ClientGUI clientCurrentGuiReference = null;


    try //Creating Server
    {
        serverSocket = new ServerSocket(port,backlog); //ServerSocket(int port, int backlog) 
    }
    catch(IOException e)
    {
        e.printStackTrace();
    }

    while (true)
    {
        try
        {
            System.out.println("Server is waiting for Client requests...");
            clientSocket = serverSocket.accept(); // A new thread is created for the new client
            System.out.println("Client connection request accepted, creating client connection proxy...");

            clientConnectionProxy = new ConnectionProxy(clientSocket); //connecting client socket to server
            clientConnectionProxy.addConsumer(messageBoard); //Applying specific server system network utilities and connecting proxy to the messageboard

            System.out.println("Requesting Client details from Client side...");

            clientNickname = ClientGUI.getNickname();
            clientServerAddress = ClientGUI.getServerAddress();
            clientPort = ClientGUI.getPort();
            clientCurrentGuiReference = ClientGUI.getCurrentClientGuiReference();

            System.out.println("Creating Client Descriptor...");
            clientDescriptor = new ClientDescriptor(clientNickname, clientServerAddress, clientPort, clientCurrentGuiReference);

            clientDescriptor.addConsumer(messageBoard); 

            messageBoard.addConsumer(clientDescriptor);  

            clientConnectionProxy.start();//Start client connection's thread running
            System.out.println("Client thread started...");
        }
        catch (IOException e)
        {
            e.printStackTrace();
        }
    }
}
}
Adi BB
  • 11
  • 1

3 Answers3

1

I think static doesn't do what you think it does. If Client and Server are running separately--as in two different processes and two different JVMs--then no amount of assigning any variable to anything will make the same value/object visible to both Client and Server. You'll have to use some way of communicating between the processes.

Once you manage to get a ClientGUI to the Server, I doubt you'll be able to use it the way you want. The ClientGUI is also just an object with no ability to communicate between the Client and Server. You'll have to manage that yourself, too.

Ryan Stewart
  • 126,015
  • 21
  • 180
  • 199
  • Yea, I think you got me there. Can you tell me in short, or perhaps refer me to some online info I can read about this multi processes data transfer issue? I am completely new to the subject. Thanks :) – Adi BB Jul 28 '11 at 16:28
1

The server and client are in different processes, as far as I can see. They're completely separate - setting a static variable in the client process won't change the same static variable in the server process.

Jon Skeet
  • 1,421,763
  • 867
  • 9,128
  • 9,194
0

The only way I can think of that might work for what you are trying to do is using Serialization that can be used to represent an object as a sequence of bytes and then that can be sent using ObjectOutputStream and received by using ObjectInputStream as they are required in sending/receiving Object. Although I have worked on a similar project, i didn't require doing something like this.

Ankur Kumawat
  • 446
  • 5
  • 21