Search code examples
javaapachehttpclientblock

Java Apache httpclient blocking GUI


I am currently developing an HTTP application using Apache's http API and I am using a GUI. After after every GET or POST request I want to update a GUI TextArea with some messages. The problem is that those messages appear after all the requests are done.

I also noticed that if I write messages on the console after every request, the message appear, but if I write on the GUI all the messages appear on the end.

Here is some code snippets:

GUI constructor:

public GUI() {
        initComponents();
        SetMessage.gui = this;
}

SetMessage class:

public class SetMessage implements Runnable{

    public static GUI gui;
    private String msg;

    public SetMessage( String msg){
        synchronized(gui){
            this.msg = msg;
        }
    }

    public void run() {
        gui.setText(msg);
    }

}

The GET request class (every request is made by a thread):

public class SendGetReq extends Thread {

private HttpConnection hc = null;
private DefaultHttpClient httpclient = null;
private HttpGet getreq = null;
private int step = -1;
private String returnString = null;

public SendGetReq(HttpConnection hc, DefaultHttpClient httpclient, HttpGet getreq, int step) {
    this.hc = hc;
    this.httpclient = httpclient;
    this.getreq = getreq;
    this.step = step;
}

@Override
public void run() {
   // CODE
}

And HttpConnection Class (the instance of this class is created when I press a button on the GUI):

    public class HttpConnection {
        private DefaultHttpClient httpclient = null;
        private HttpGet getreq = null;
        private HttpPost postreq = null;
private SendGetReq tempGet = null;
         // More fields
        private void RandomMethod(){
//Initialize getreq
(tempGet = new SendGetReq(this, httpclient, getreq, 0)).start();
new SetMessage("Message").run();

}

Oh! And the GUI's SetText method:

public synchronized void setText(String msg){
        if(!"".equals(msg)){
            Date currentDate = new Date();
            Calendar calendar = GregorianCalendar.getInstance();
            calendar.setTime(currentDate);
            jTextArea1.append(calendar.get(Calendar.HOUR_OF_DAY)+":"+calendar.get(Calendar.MINUTE)+":"+calendar.get(Calendar.SECOND)+" --- "+msg+"\n");                        
        }
    }

Can anyone help me with this problem? Thanks! }


Solution

  • Yup, pretty standard behaviour for a GUI. You will need to do the HTTP requests in another thread, then notify the GUI thread to update the UI. Swing in particular demands that the UI is updated from a single thread, the event dispatching thread to be precise.

    See SwingUtilities#isEventDispatchThread(), SwingUtilities#invokeLater() and the SwingWorker class.