bennidi / mbassador

Powerful event-bus optimized for high throughput in multi-threaded applications. Features: Sync and Async event publication, weak/strong references, event filtering, annotation driven
MIT License
955 stars 146 forks source link

Q: How to create a blocking wait for messages programmatically ? #162

Open Gerry33 opened 5 years ago

Gerry33 commented 5 years ago

Hi all, this sounds a bit weird, but I need something like a blocking calls that waits for a message to arrive. Just like the plain JAVA concurrent queues, but with all the PROs of mbassador.

Background is that my msg receiver must run in a specific (thread) environment, that must be the same from one handler call to the other. I have no influence on that enviroment.

Thanks for any hint.

Regards Gerry

bennidi commented 5 years ago

I am not sure if I understand correctly but if you are trying to implement logic in which the publisher and handler run in the same thread context then this is hard to do with async messages. Definitely requires custom synchronization logic. One direction would be to provide Mbassador with the ThreadFactory for the async handlers and implement it in such a way that the handler has access to it. However, this smells like bad design. Can you elaborate your use case a bit more? Maybe there is a better way to achieve what you have in mind.

Gerry33 commented 5 years ago

Hi Benjamin and thanks for taking care (with my apologies for the late reply due to heavy work load)

The problem is that I'm bound to some framework. I start my servlet with a Callable/Runnable like this:

class myClass {

// this is my framework call . I have to stick with this. 
Future <?> myfuture = Application.getContext()-> ()     

 // now herein I'm happy within my framework and can do what I need 

});
// but it stops here 

@Handler
public void MyHandler ( ...) {
    // here I'm outside  and I have no access to the  framework 
}
} // end class 

What I want:

class MyClass {

public void MyClass() {

Future <?> myfuture = Application.getContext()-> () 

    @Handler
    public void refresh ( final GUIUpdates msg) {

    }
});
}

OR:

class MyClass {
public void MyClass() {

Future <?> myfuture = Application.getContext()-> () 
        // something like  a blocking call 
        Message m = net.engio.mbassy.WaitForMessage (); 
    }

});
}

I agree with your remark that the latter is bad design, lets call it ugly.

Problem is that a handler can only be defined on class level. I will therefore try to remove the lambda call and replace it with a runnable class and try to place the handler there. If you have some better idea, I would be very happy to hear from you.

Thanks for your work on 'mbassador'.

Gerry