I have a new Jakarta EE (Qurakus) application and some old code which has methods to register event listeners. I have made a wrapper for the event registry. Now I need some way to efficiently register a lot of event listeners. It looks something like this:
@ApplicationScoped
public class EventRegistry {
private Set<Listener<?>> listeners = Collections.synchronizedSet(new HashSet<>());
public void register(Listener l) {
}
public void unregister(Listener l) {
}
}
@ApplicationScoped
public class Listener1 implements Listener<MyEvent> {
@Override
public void onEvent(MyEvent e) {
}
}
So basically I need a way for the listeners to register. I thought about using a Jakarta EE event which I trigger in PostConstruct of the registry and listen to it in each listener which then registers itself. Is this a save way to do it? Or will the listener bean be destructed if not used through an Inject? Also is there generally a better way to execute an operation for specific beans (I have all the listeners in a single package).
A simple way to do exactly what you want would be the following:
You can ask CDI to do method injection; you can also ask it for an
Instanceof a type (in this case yourListener) and through theInstanceretrieve all implementations, as shown above. Methods annotated with@Injectget called when injection happens on the instance and before any@PostConstructmethods. You could do property injection (i.e.@Inject private Instance<Listener<?>> listenerInstance), but you only need this object during the initialization of theEventRegistry. There is no reason to keep it around in a property for any longer.Since you are in CDI and CDI supports the observer pattern you could consider changing your implementation to use that facility, as suggested in another answer.