java - 除了构造函数 @Inject 注解之外,还有其他方式实现 GWTP placeManager

标签 java gwt dependency-injection gwtp gwt-platform

我使用 GWTP 和 RestyGWT。我想在restyGWT DispatcherCallback中使用placeManager,当我的休息服务器将回答401 unauthorized时,我想将应用程序重定向到登录页面,用户可以应用凭据并重试他的请求。

为此,我必须以某种方式获取 PlaceManager 的实例(来自 gwtp 框架)。我无法使用 @Inject 注释,因为我手动调用构造函数,如下所示:

public class ForbiddenDispatcherFilter implements DispatcherFilter {
    @Override
    public boolean filter(Method method, RequestBuilder builder) {
        builder.setCallback(new ForbiddenDispatcherCallback(method));
        return true;
    }
}


public class ForbiddenDispatcherCallback implements RequestCallback {
    protected RequestCallback requestCallback;

    public ForbiddenDispatcherCallback(Method method) {
        this.requestCallback = method.builder.getCallback();
    }

    @Override
    public void onResponseReceived(Request request, Response response) {
    if (response.getStatusCode() == Response.SC_FORBIDDEN || response.getStatusCode() == Response.SC_UNAUTHORIZED) {
        // make a hard redirect to login page
        // TODO change redirect to GWTP native
        Window.Location.assign("#login");
        // PlaceRequest placeRequest = new
        // PlaceRequest.Builder(placeManager.getCurrentPlaceRequest()).nameToken(Routing.Url.login).build();
        // placeManager.revealPlace(placeRequest);
    } else {
        requestCallback.onResponseReceived(request, response);
    }

}


public class RestyDispatcher extends DefaultFilterawareDispatcher {

    public RestyDispatcher() {
    addFilter(new ForbiddenDispatcherFilter());
    addFilter(new BasicAuthHeaderDispatcherFilter());
    }

    @Override
    public Request send(Method method, RequestBuilder builder) throws RequestException {
    return super.send(method, builder);
    }
}

请帮忙。

<小时/>

编辑

public class ClientModule extends AbstractPresenterModule {
    @Override
    protected void configure() {
    bind(RestyGwtConfig.class).asEagerSingleton();

    install(new DefaultModule.Builder()//
        .defaultPlace(Routing.HOME.url)//
        .errorPlace(Routing.ERROR.url)//
        .unauthorizedPlace(Routing.LOGIN.url)//
        .tokenFormatter(RouteTokenFormatter.class).build());
    install(new AppModule());
    // install(new
    // GinFactoryModuleBuilder().build(AssistedInjectionFactory.class));

    bind(CurrentUser.class).in(Singleton.class);
    bind(IsAdminGatekeeper.class).in(Singleton.class);
    bind(UserLoginGatekeeper.class).in(Singleton.class);

    // Google Analytics
    // bindConstant().annotatedWith(GaAccount.class).to("UA-8319339-6");

    // Load and inject CSS resources
    bind(ResourceLoader.class).asEagerSingleton();

    }

}

和:

public class RestyGwtConfig {

    static {

    // GWT.log("--> RestyGwtConfig -> setDispatcher");
    Defaults.setDispatcher(new RestyDispatcher());

    // GWT.log("--> RestyGwtConfig -> setServiceRoot");
    Defaults.setServiceRoot(new Resource(GWT.getModuleBaseURL()).resolve(ServiceRouting.SERVICE_ROOT).getUri());
    UserCredentials.INSTANCE.setUserName("ronan");
    UserCredentials.INSTANCE.setPassword("password");
    }

}

最佳答案

如何以及在何处创建 ForbiddenDispatcherFilter

您可以使用 guice 的 AssistedInjectionPlaceManager 注入(inject)到您的 ForbiddenDispatcherCallback 中。

public class ForbiddenDispatcherCallback implements RequestCallback {
    protected RequestCallback requestCallback;
    protected PlaceManager placeManager;

    @Inject
    public ForbiddenDispatcherCallback(PlaceManager placeManager, @Assisted Method method) {
        this.placeManager = placeManager;
        this.requestCallback = method.builder.getCallback();
    }
}

您需要定义一个工厂接口(interface):

public interface AssistedInjectionFactory {
    ForbiddenDispatcherCallback createForbiddenCallback(Method method);
}

ClientModuleconfigure 方法中,您需要调用:

install(new GinFactoryModuleBuilder().build(AssistedInjectionFactory.class));

然后你可以这样实例化你的类:

public class ForbiddenDispatcherFilter implements DispatcherFilter {
    AssistedInjectionFactory factory;

    @Inject
    public ForbiddenDispatcherFilter(AssistedInjectionFactory factory) 
    {
        this.factory = factory;
    }

    @Override
    public boolean filter(Method method, RequestBuilder builder) {
        builder.setCallback(factory.AssistedInjectionFactory(method)) 
        return true;
    }
}

当然,这还需要您注入(inject)ForbiddenDispatcherFilter

编辑:

您可以尝试将 RestyDispatcher 传递给 RestyGWTConfig 的构造函数:

public class RestyGwtConfig {

    @Inject
    public RestyGwtConfig(RestyDispatcher dispatcher) {
        Defaults.setDispatcher(dispatcher);
    }

    static {
    // GWT.log("--> RestyGwtConfig -> setServiceRoot");
    Defaults.setServiceRoot(new Resource(GWT.getModuleBaseURL()).resolve(ServiceRouting.SERVICE_ROOT).getUri());
    UserCredentials.INSTANCE.setUserName("ronan");
    UserCredentials.INSTANCE.setPassword("password");
    }
}

RestyDispatcher 看起来像这样:

public class RestyDispatcher extends DefaultFilterawareDispatcher {

    @Inject
    public RestyDispatcher(ForbiddenDispatcherFilter filter) {
      addFilter(filter);
      addFilter(new BasicAuthHeaderDispatcherFilter());
    }

    @Override
    public Request send(Method method, RequestBuilder builder) throws RequestException {
      return super.send(method, builder);
    }
}

关于java - 除了构造函数 @Inject 注解之外,还有其他方式实现 GWTP placeManager,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35770706/

相关文章:

.net - 依赖注入(inject)启动性能

java - 楼梯问题: How to print the combinations?

java - 如何解释导致 OutOfMemoryError 的 G1 GC 日志?

java - Hibernate @Proxy(lazy = false) 注解有什么作用?

java - 如何在java中检测文档的确切类型

c# - .NET 核心 - 依赖注入(inject)、工厂和 IDisposable

java - 如何在 GWT 中获取一年中的星期数

gwt - 如何在 GWT RPC 调用中的 session 过期后重定向到登录页面

java - 获取剪贴板粘贴缓冲区

c# - 为什么使用 AddScoped() 而不是 AddSingleton()?