Jersey和Google Guice的整合

时间:2016-04-11 17:17:21

标签: java dependency-injection jersey integration guice

我的问题是:在创建部署在某种servlet容器(如jetty或tomcat)上的应用程序时,为什么在执行JavaSE应用程序和ServletModule时需要创建AbstractModule?它们之间有什么区别?

我需要将泽西与Guice整合。是否有必要为泽西岛注册Guice的存在以某种方式使用它?我不能只是启用注射并在我想要的任何地方(普通类,过滤器,处理程序,服务,DAO等)执行它们吗?为什么我不能像在JavaSE应用程序中那样配置guice,而是需要使用ServletModule?

据我在网上看到,有许多使用Guice的HK2服务的例子,反之亦然,所以我认为它很重要? (必要?)

由于

1 个答案:

答案 0 :(得分:5)

AbstractModule是Guice的bootstrap(配置)阶段的基本构建块。你总是需要一个或多个。另一方面,ServletModule是一个特殊化,它为你做了一些配置,因为它在servlet容器中运行。

来自Guice documentation

  

该模块设置请求和会话范围,并提供一个   从中配置过滤器和servlet的地方。

关于Guice-Jersey集成,您当然需要进行设置。它不会一帆风顺。 Guice和任何其他依赖注入框架一样,当它可以控制构建对象时。如有疑问,请问自己是谁创造了这个对象。

使用Jersey和JAX-RS,谁创建了对象?不是你,你只是定义它们。容器创建它们。 JAX-RS运行时。在您的情况下,Jersey运行时。而泽西在内部使用HK2依赖注入框架。所以你需要桥接这两个框架,以便注入你用一些Guice资源定义的JAX-RS类。或者相反!这就是HK2-guice bridge的原因。因此,Jersey将使用HK2构建您的对象,而HK2也会在Guice上查找您的资源,这要归功于桥梁。

一个简单的例子。 I use this code初始化我想要注入Guice资源的REST API。

@ApplicationPath("api")
public class ApiRest extends ResourceConfig {  
    private static final Logger log = LoggerFactory.getLogger(ApiRest.class);

    @Inject
    public ApiRest(ServiceLocator serviceLocator, ServletContext servletContext) {
        log.debug("Inicialitzant Jersey.");
        packages("net.sargue.app.api");

        GuiceBridge.getGuiceBridge().initializeGuiceBridge(serviceLocator);
        GuiceIntoHK2Bridge guiceBridge = serviceLocator.getService(GuiceIntoHK2Bridge.class);
        Injector injector = (Injector) servletContext.getAttribute(Injector.class.getName());
        if (injector == null)
            throw new RuntimeException("Guice Injector not found");
        guiceBridge.bridgeGuiceInjector(injector);
    }
}

请注意,上面的示例需要注册ServletModule,因为它会从ServletContext中提取Guice注入器。或者您可以将注射器添加到其他地方的ServletContext。或者只是在初始化REST API时创建注入器,它取决于您的首选项和应用程序。