使用bindFactory时没有可用于注入错误的对象

时间:2015-06-12 14:56:28

标签: java dependency-injection jersey jersey-2.0 hk2

我对Jersey(2.18)应用程序有以下实现:

public class RootApplication extends ResourceConfig {

    public RootApplication() {
        packages("com.foo.bar");

        register(new AbstractBinder() {

            @Override
            protected void configure() {       
                bindFactory(RepositoryFactory.class).to(Repository.class);

                // if I use following line instead of bindFactory it works
                // bind(OracleRepository.class).to(Repository.class);
            }
        });
    }

    public class RepositoryFactory implements Factory<Repository> {

        private final Repository repo;

        public RepositoryFactory() {
            this.repo = new OracleRepository();
        }

        @Override
        public Repository provide() {
            return repo;
        }

        @Override
        public void dispose(Repository repo) {
        }
    }
}

并在点击注入存储库

的服务时获取以下异常
javax.servlet.ServletException: A MultiException has 3 exceptions.  They are:
1. org.glassfish.hk2.api.UnsatisfiedDependencyException: There was no object available for injection at SystemInjecteeImpl(requiredType=Repository,parent=MeasureService,qualifiers={},position=-1,optional=false,self=false,unqualified=null,56464420)
2. java.lang.IllegalArgumentException: While attempting to resolve the dependencies of com.fidelity.pi.dashboard.rest.MeasureService errors were found
3. java.lang.IllegalStateException: Unable to perform operation: resolve on com.fidelity.pi.dashboard.rest.MeasureService

如果我注释掉bindFactory并使用注释掉的绑定,这一切都有效。我在工厂实施方面遗漏了什么吗?即使在命中RepositoryFactory构造函数之前,似乎也会发生异常。我需要工厂,因为我在OracleRepository实例上进行了一些其他初始化。

1 个答案:

答案 0 :(得分:2)

我能够重现问题的唯一方法(使用不完整的信息 - 即缺少注入点)是尝试注入OracleRepository而不是Repository。我不知道注射失败的确切原因,但我想这是因为你绑定了Repository而不是OracleRepository。如果这是问题,最简单的解决方法是将工厂绑定到OracleRepository,或者只需注入Repository

对于Repository的注入,如果要对不同的实现进行限定,可以通过将namedqaulifiedBy链接到绑定来实现,如下例所示(我使用{ {1}}并使用named注释注入点。

在示例中,我使用了Jersey Test Framework

@Named

这是完整的测试。您可以更改<dependency> <groupId>org.glassfish.jersey.test-framework.providers</groupId> <artifactId>jersey-test-framework-provider-inmemory</artifactId> <version>${jersey2.version}</version> <scope>test</scope> </dependency> @Named之间的"Sql"以查看差异。

"Oracle"

如果您仍然遇到问题,请发布一个完整的单一类测试案例,就像我上面所说的那样,证明了这个问题。