阻止方法调用,直到异步调用完成GWT-Platform

时间:2012-06-18 15:59:13

标签: gwt gwt-platform

在我的GWT-Platform应用程序中,我实现了一种方法,其中一步是从服务器获取数据,下一步是依赖于它。我想阻止我的方法进一步执行代码,直到异步调用完成。

应该是简单的事情,但我找不到办法。

4 个答案:

答案 0 :(得分:6)

我认为你错过了关于网络异步的观点。

在异步调用完成之前,阻止执行客户端代码并不是一种好的做法(它是一种反模式)。

因此,在完成异步代码之前,不要阻止执行,请执行以下操作:

  1. 创建在异步代码完成时在全局Eventbus上触发的事件
  2. 在其中一个演示者
  3. 中附加此事件的处理程序
  4. 启动异步代码
  5. 显示加载指示器
  6. 当异步调用完成后,隐藏加载指示符并触发Eventbus上的事件
  7. 处理您之前创建的处理程序中的下一步。

答案 1 :(得分:2)

我不是GWT大师,但我知道如何以简单的方式做到这一点。 如果有人告诉我如何以正确的方式做到这一点,我将非常感激,因为我也对它感兴趣。 您可以创建包含所需代码的方法并将其调用onSuccess或执行以下操作:

import com.google.gwt.core.client.EntryPoint;
import com.google.gwt.core.client.GWT;
import com.google.gwt.event.dom.client.ClickEvent;
import com.google.gwt.event.dom.client.ClickHandler;
import com.google.gwt.user.client.Timer;
import com.google.gwt.user.client.Window;
import com.google.gwt.user.client.rpc.AsyncCallback;
import com.google.gwt.user.client.ui.Button;
import com.google.gwt.user.client.ui.RootPanel;

public class Aaa implements EntryPoint {

    private final MyServiceAsync service = GWT
            .create(MyService.class);
    private Timer t;

    public void onModuleLoad() {
        t = new Timer() {
            @Override
            public void run() {
                // Make something or call function
                Window.alert("Next Step");
            }
        };
        final Button sendButton = new Button("Send");
        sendButton.addClickHandler(new ClickHandler() {

            @Override
            public void onClick(ClickEvent event) {
                service.sendInfo("Send First Step Info",
                        new AsyncCallback<String>() {
                            @Override
                            public void onSuccess(String result) {
                                Window.alert("Success Call");
                                // Call Next step code or function
                                t.schedule(1);

                            }

                            @Override
                            public void onFailure(Throwable caught) {
                                Window.alert("Failure Call");
                            }
                        });
            }
        });
        RootPanel.get().add(sendButton);
    }
}

答案 2 :(得分:1)

为什么要使用Timer

final Button sendButton = new Button("Send");
sendButton.addClickHandler(new ClickHandler() {

    @Override
    public void onClick(ClickEvent event) {
        service.sendInfo("Send First Step Info",
                new AsyncCallback<String>() {
                    @Override
                    public void onSuccess(String result) {
                        Window.alert("Success Call");
                          nextStep(result);
                    }

                    @Override
                    public void onFailure(Throwable caught) {
                        Window.alert("Failure Call");
                    }
                });
    }
});

private void nextStep(String data) {
}

答案 3 :(得分:0)

我不得不改变原始流程,基本上移动它并链接到Async调用的onSuccess()。

最初,流程是

  1. 用户单击一个poopup对话框的Ok按钮
  2. validate(everthing是前端验证),如果出现验证错误,则抛出异常并显示错误。 diaglog没有关闭。
  3. 成功验证后,继续进行数据处理并关闭对话框。
  4. 现在在一个新的scenaro中,#2验证被更改为需要异步调用回到后端。因此必须将#3移至链接到validate方法的回调。 “ 下面的代码片段

    public void onValidationDataReady(List<Long> existingTests) throws ValidationException {
    
        if (!existingTests.isEmpty()) {
            throw new ValidationException("The entered name has already been used.");
        }
    
        //only after  the validation do we proceed with the original OK click 
        proceedOkClick(testNameField.getValue());
    }
    
    public void proceedOkClick(String data) {
        // proceed only after the async call
    
        if (callback != null) {
            callback.onDialogResult(true, data);
        }
    
        clearDialog();
    }
    
    
    public boolean validateInputs() throws ValidationException {
        //async call to get data from back end.
                //pass in a Callback 
        testNameValidator.validate(testNameField.getValue(), new DataReadyCallback<List<Long>>() {
            @Override
            public void onDataReady(List<Long> existingTests) {
                onValidationDataReady(existingTests);
            }
        });
        return true;
    }
    
    //The call back interface. 
    public interface DataReadyCallback<T> {
    void onDataReady(T data);
    }