背景故事:
我正在开发一个 GWT 应用程序,使用标准的 MVP 设计模式,还使用 RPC 从我的自定义数据处理 servlet 中获取数据(在幕后做了很多工作)。无论如何,我的目标是创建一个非常简单的自定义缓存机制,将从 RPC 回调返回的数据存储在静态缓存 POJO 中。(回调还使用 SimpleEventBus 向所有注册的处理程序发送一个自定义事件。)然后当我再次请求数据时,我将在再次调用 RPC 服务器之前检查缓存。(并且还使用 EventBus 发送自定义事件)。
问题:
当我从 RPC 回调发送事件时,一切正常。问题是当我只发送缓存对象时,我在 RPC 回调之外发送事件。出于某种原因,此事件无法到达我注册的处理程序。这是一些代码:
public void callServer(final Object source)
{
if(cachedResponse != null)
{
System.err.println("Getting Response from Cache for: "+ source.getClass().getName());
//Does this actually fire the event?
eventBus.fireEventFromSource(new ResponseEvent(cachedResponse),source);
}
else
{
System.err.println("Getting Response from Server for: "+ source.getClass().getName());
service.callServer(new AsyncCallback<String>(){
@Override
public void onFailure(Throwable caught) {
System.err.println("RPC Call Failed.");
}
@Override
public void onSuccess(String result) {
cachedResponse = result;
eventBus.fireEventFromSource(new ResponseEvent(cachedResponse),source);
}
});
}
}
现在我有两个活动,HelloActivity 和 GoodbyeActivity(取自:GWT MVP 代码)
它们还会在调用处理程序时打印出消息。无论如何,这是我从日志中得到的输出:(不正确)
Getting Response from Cache for: com.hellomvp.client.activity.HelloActivity
Response in GoodbyeActivity from: com.hellomvp.client.activity.HelloActivity
Getting Response from Cache for: com.hellomvp.client.activity.GoodbyeActivity
Response in HelloActivity from: com.hellomvp.client.activity.GoodbyeActivity
我期望得到的是:
Getting Response from Cache for: com.hellomvp.client.activity.HelloActivity
Response in HelloActivity from: com.hellomvp.client.activity.HelloActivity
Getting Response from Cache for: com.hellomvp.client.activity.GoodbyeActivity
Response in GoodbyeActivity from: com.hellomvp.client.activity.GoodbyeActivity
如果我将上面的代码更改为以下代码,我将得到这个预期的输出:(这次是整个文件......)
package com.hellomvp.client;
import com.google.gwt.core.client.GWT;
import com.google.gwt.event.shared.EventBus;
import com.google.gwt.user.client.rpc.AsyncCallback;
import com.hellomvp.events.ResponseEvent;
public class RequestManager {
private EventBus eventBus;
private String cachedResponse;
private HelloServiceAsync service = GWT.create(HelloService.class);
public RequestManager(EventBus eventBus)
{
this.eventBus = eventBus;
}
public void callServer(final Object source)
{
if(cachedResponse != null)
{
System.err.println("Getting Response from Cache for: "+ source.getClass().getName());
service.doNothing(new AsyncCallback<Void>(){
@Override
public void onFailure(Throwable caught) {
System.err.println("RPC Call Failed.");
}
@Override
public void onSuccess(Void result) {
eventBus.fireEventFromSource(new ResponseEvent(cachedResponse),source);
}
});
}
else
{
System.err.println("Getting Response from Server for: "+ source.getClass().getName());
service.callServer(new AsyncCallback<String>(){
@Override
public void onFailure(Throwable caught) {
System.err.println("RPC Call Failed.");
}
@Override
public void onSuccess(String result) {
cachedResponse = result;
eventBus.fireEventFromSource(new ResponseEvent(cachedResponse),source);
}
});
}
}
}
所以指出,唯一的变化是我创建了一个新的 RPC 调用,它什么都不做,并在其回调中发送事件,而不是缓存数据,它使应用程序按预期工作。
所以问题:
我做错了什么?我不明白为什么 'eventBus.fireEvent(...)' 需要在 RPC 回调中才能正常工作。我认为这是一个线程问题,但我在谷歌搜索任何有用的东西都是徒劳的。
我有一个完整的 Eclipse 项目来展示我遇到的这个问题,可以在以下位置找到它:Eclipse 问题项目示例
编辑:请注意 usingeventBus.fireEventFromSource(...)
仅用于调试目的,因为在我的实际 GWT 应用程序中,我有多个注册的事件处理程序。那么如何正确使用 EventBus呢?