【问题标题】:Inject not working for nested objects[Jersey 2.22.1]注入不适用于嵌套对象[Jersey 2.22.1]
【发布时间】:2016-04-08 12:54:07
【问题描述】:

我有一个 Jersey 资源,其中注入了外观对象。这是在我的ResourceConfig 中配置的,并且外观可以很好地注入。外观包含一个 DAO 类,它也应该被注入并配置在相同的ResourceConfig 中。现在我的问题; DAO 类为空。因此,没有注入。

@ApplicationPath("/service")
public class SystemSetup extends ResourceConfig {

public SystemSetup() {
    packages(false, "com.foo.bar");
    packages("org.glassfish.jersey.jackson");
    register(JacksonFeature.class);

    final LockManager manager = getLockManager();
    final SessionFactory sessionFactory = getSessionFactory();
    register(new AbstractBinder() {
        @Override
        protected void configure() {
            bindFactory(InjectFactory.getDaoFactory(sessionFactory)).to(Dao.class).in(Singleton.class);
            bindFactory(InjectFactory.getFacadeFactory(manager)).to(Facade.class).in(Singleton.class);
        }
    });
}

 @Path("/")
 @Produces("text/json")
 public class ViewResource {

    @Inject
    private Facade logic;

public class Facade {

    @Inject
    private Dao dao; //Not injected

工厂实例相当简单。他们只需调用构造函数并将参数传递给它。

奇怪的是,当我使用 bind(Class object) 而不是 bindFactory 时,这绝对可以正常工作。

编辑

工厂

class InjectFactory {

    static Factory<Dao> getDaoFactory() {
        return new Factory<Dao>() {
            @Override
            public Dao provide() {
                return new Dao(new Object());
            }

            @Override
            public void dispose(Dao dao) {}
        };
    }

    static Factory<Facade> getFacadeFactory() {
        return new Factory<Facade>() {

            @Override
            public Facade provide() {
                return new Facade();
            }

            @Override
            public void dispose(Facade facade) {}
        };
    }
}

【问题讨论】:

  • 你能贴出重现问题所需的所有代码吗?
  • 嗨!我创建了一个非常基本的小项目来重现这个问题。请在 speedy.sh/qbsnJ/Dummy-Project.zip 下载它并使用“mvn clean install tomcat7:run-war”运行它并在浏览器中导航到 localhost:9090/dummy/service/test。
  • 基本上,您只需要复制一个带有注入字段(A)的对象。对象 A 应包含另一个注入字段 (B)。 A 和 B 都注册为 bindFactory(Factory instance)。

标签: java dependency-injection jersey inject hk2


【解决方案1】:

与大多数 Di 框架一样,当您开始自己实例化事物时,通常情况下您将框架排除在等式之外。这适用于 Factory 实例以及工厂创建的对象。因此,Facade 实例永远不会被框架接触,除非将其注入到资源类中。

您可以持有ServiceLocator,如果您想自己创建对象,您可以自己显式注入对象。这里有几个选项。

1) 将ServiceLocator 注入Factory 实例,然后注入Facade 实例。

static Factory<Facade> getFacadeFactory() {
    return new Factory<Facade>() {

        @Context
        ServiceLocator locator;

        @Override
        public Facade provide() {
            Facade facade = new Facade();
            locator.inject(facade);
            return facade;
        }

        @Override
        public void dispose(Facade facade) {}
    };
}

@Inject
public SystemSetup(ServiceLocator locator) {
    packages("foo.bar.rest");
    packages("org.glassfish.jersey.jackson");
    register(JacksonFeature.class);

    register(new AbstractBinder() {
        @Override
        protected void configure() {
            bindFactory(InjectFactory.getDaoFactory()).to(Dao.class);

            Factory<Facade> factory = InjectFactory.getFacadeFactory();
            locator.inject(factory);
            bindFactory(factory).to(Facade.class);
        }
    });
}

2) 或者绑定一个Factoryclass,让框架注入ServiceLocator

public static class FacadeFactory implements Factory<Facade> {

    @Context
    ServiceLocator locator;

    @Override
    public Facade provide() {
        Facade facade = new Facade();
        locator.inject(facade);
        return facade;
    }

    @Override
    public void dispose(Facade facade) {}
}

register(new AbstractBinder() {
    @Override
    protected void configure() {
        bindFactory(InjectFactory.getDaoFactory()).to(Dao.class);
        bindFactory(InjectFactory.FacadeFactory.class).to(Facade.class);
    }
});

【讨论】:

  • 感谢您的帮助。当你解释它时,它很有意义。我将阅读有关 ServiceLocator 的更多信息。通过遵循第一步,它可以正常工作,稍作改动。我删除了 SystemSetup 构造函数上的 Inject 注释(因为它不起作用)并将 @Context 添加到参数中。
  • 如果您曾经使用过 Spring,ServiceLocator 类似于 Spring 的 ApplicationContext。它是主要的 IoC 容器。
  • 这有助于解决我的问题。我可以使用@Inject 将服务注入到资源类中,但是当我在服务本身中使用@Inject 时,我总是得到NullPointerException。问题是我自己用工厂创建了服务,没有意识到从那时起不会发生任何注入。花了很多时间试图理解这一点。谢谢!
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-03-13
  • 1970-01-01
  • 2022-12-10
  • 1970-01-01
  • 2019-01-05
相关资源
最近更新 更多