我有两个类可以触发两个事件(代码来自带有私有内部类的junit测试):
55|32|11
在我的测试中,EventData类很简单:
private static class EventEmitter1 { @Inject private Event<EventData1> event; }
private static class EventEmitter2 { @Inject private Event<EventData2> event; }
在接收器类中,我想等到收到两个事件,所以我尝试了这样的事情:
private class EventData1 { }
private class EventData2 { }
在我的测试方法中,我手动为两个发射器类选择一个实例,并为每个实例触发一个事件。此外,我手动选择一个Receiver实例。
private static class EventReceiver {
private boolean eventData1Received = false;
private boolean eventData2Received = false;
private void receiveEventData1(@Observes EventData1 eventData) {
LOGGER.debug("received " + eventData.getClass().getName());
eventData1Received = true;
handleReceivedEvents();
}
private void receiveEventData2(@Observes EventData2 eventData) {
LOGGER.debug("received " + eventData.getClass().getName());
eventData2Received = true;
handleReceivedEvents();
}
private void handleReceivedEvents() {
LOGGER.debug("eventData1Received: " + eventData1Received + ", eventData2Received: " + eventData2Received);
}
}
通过CDI.current.select(...)手动选择应确保CDI机制有效。
我现在的问题是这三种方式! EventReceiver实例初始化。他们都没有将eventDataXReceived字段都设置为true。将事件传递到同一个EventReceiver实例的正确方法是什么?理想情况下,EventReceiver不应该是(应用程序作用域)单例。
Thanx求助。
答案 0 :(得分:1)
这是一个对我有用的解决方案:
public abstract class EventDispatcher<E>
{
private Set<Consumer<E>> consumers = new HashSet<>();
public Set<Consumer<E>> getConsumers() { return consumers; }
protected void observe(@Observes E event)
{
consumers.forEach(consumer -> consumer.accept(event));
}
}
注意:EventDispatcher 提供 getConsumers()
允许注册对 E 感兴趣的消费者。
Event
)创建一个非抽象 EventDispatcher 并为其指定范围(以下示例中的 Singleton
): @Singleton private static class Dispatcher extends EventDispatcher<Event> { }
注意:private static
类型完全满足它的小任务。
@Inject
) 您的 Dispatcher
: @Inject private Dispatcher dispatcher;
dispatcher
并在 Event
出现时执行您认为合适的操作,例如onEvent(event)
: dispatcher.getConsumers().add(event -> onEvent(event));
答案 1 :(得分:0)
为EventReceiver提供适当的范围。如果没有范围,则为@Dependend,因此对于每个事件都会创建一个新实例。
@ApplicationScoped应该可以正常工作。
答案 2 :(得分:0)
我担心你需要为EventReceiver
添加一个范围,而@ApplicationScoped
通常会成为这里的首选。
你可以添加一个辅助逻辑层来帮助你确定这个事件的来源,从而确定你是否已经注册了所有必需的事件(我想这就是你所追求的)。
一种可能的方法是将此类信息存储在事件有效负载中。然后,一旦您观察事件,提取此信息并保留已注册事件的集合。添加到此集合中后,您可以检查是否已经有两个给定“类型”的事件。
我希望你能得到基本的想法,更确切地说,我需要了解更多关于代码的知识。
最后但同样重要的是,define your own scope还有一个(疯狂)选项,您可以根据自己的需要进行定制。然而,这需要一些认真的奉献和工作。