1

Im currently trying to set up some netty client/server application. I know how to send messages and handle them via the netty classes. My only problem is, how can i receive messages out of the messageReceived() method. For Example, i send an message via the ChannelHandlerContext from a method getUserInformations() and want to wait until i get the result to work with them. This is what i have tried so far.

I only post the client side. The netty server is the standard way to build it, nothing speciel.

Thats my main class, here i press a button on my UI and send an messages via the sender Thread.

public class FXMLDocumentController implements Initializable {

    public static ChannelHandlerContext handler=null;

    @FXML
    private TextArea txt;


    @FXML
    private void handleButtonAction(ActionEvent event) throws InterruptedException, ExecutionException {
        Sender s = new Sender();
        Thread th = new Thread(s);
        th.start();
        txt.setText(s.get());
    }

    @Override
    public void initialize(URL url, ResourceBundle rb) {
        // TODO
    }    

}

Thats my sender thread:

public class Sender extends Task<String> implements DataChangeListenter{

    DataChangeEvent event;

    @Override
    protected String call() throws Exception {
        DataChangedHandler.registerDataChangeListener(this);
        ChannelFuture f = handler.writeAndFlush("TestMessage");
        return null;
    }

    @Override
    public void dataChangeEvent(DataChangeEvent event) {
        System.out.println("Listener: "+event.getMessage());
    }
}

In my sender Thread you can see the method dataChangeEvent. I used the event system from this stackoverflow post: Netty - How to get server response in the client. It works well, when i print out: System.out.println("Listener: "+event.getMessage()); - The right messages get printet, but i cant get the result in my main class where i call the sender thread to start.Could you explain me how i can get the response in the handleButtonAction() method in my main class?

Community
  • 1
  • 1
Steinliiippp
  • 373
  • 4
  • 20
  • I don't know Netty that well but you probably want to return the `ChannelFuture` you get in your `call()` method and use it to check for task completion and to get the result (it it operates like the standard futures which I assume it does). Besides that you could also link something to the sender (e.g. pass some sort of result receiver) that the sender hands over the result when the event is caught. – Thomas Feb 26 '16 at 08:33
  • 1
    I'd like to warn you off one probable mistake though: you probably shouldn't blockingly wait for the sender thread `th` to finish (i.e. not call `th.join()` or something like that) as this might block your entire UI. – Thomas Feb 26 '16 at 08:35
  • @Thomas: How could i receive the messages and work with them if i dont wait until i get the result? The Future has an get() mehtod: public V get() throws InterruptedException, ExecutionException Waits if necessary for the computation to complete, and then retrieves its result. Returns: the computed result But the return-typ is void .... – Steinliiippp Feb 26 '16 at 08:37
  • Could you post my some code, that i konw what you mean with linker? – Steinliiippp Feb 26 '16 at 08:39
  • 1
    I didn't say you shouldn't wait for the result, I said you shouldn't block the the UI thread until the result is available but rather use some other means. You'd normally wait for the result by either using the listener you already have or periodically querying the future to check whether the result is available yet. – Thomas Feb 26 '16 at 08:39
  • With "linker" I mean some object that the listener could pass the result to. It might be anything, just pass that instance in the constructor and pass the result when receiving the event. I don't know your UI code or what your actually trying to do so you'd have to think of something yourself. I just used "linker" in lack of a better term. – Thomas Feb 26 '16 at 08:42
  • I have one questions to the listener approach: If i register one class to listen for an message, the event get allways thrown if a message is read. How can i check if the class needs this message and which class dont need it if i have all my classes registered to the event? For example i send a message from class 1 and want the result there, but class 2 is also registered to the event. How to check if class 1 or 2 needs the message – Steinliiippp Feb 26 '16 at 08:58
  • 1
    That would probably depend on the type of the event, a consumer hierarchy or something else. If multiple listeners registered for the same type of event then probability is high that they all want to be notified (except one "consumes" the event, i.e. marks it as not relevant anymore). You probably should read up on [listeners](https://docs.oracle.com/javase/tutorial/uiswing/events/generalrules.html) or the observer pattern. – Thomas Feb 26 '16 at 09:22

0 Answers0