【问题标题】:How to inject an interface implementation? [duplicate]如何注入接口实现? [复制]
【发布时间】:2014-11-16 22:37:18
【问题描述】:

我有如下界面

public interface IMyMapper<T> {}

和实现

public class MyMapper implements IMyMapper<MyClazz> {}

现在我想将 MyMapper 类注入到无状态 bean 中:

@Stateless
public class MyService {

    @Inject
    MyMapper mapper; //<-- does not work

    @Inject
    IMyMapper<MyClazz> mapper; //<-- also does not work
}

我的问题是注入不起作用。我得到一个例外:

org.jboss.weld.exceptions.DeploymentException: WELD-001408: Unsatisfied dependencies    for type MyMapper with qualifiers @Default
at injection point [BackedAnnotatedField] @Inject mypackage.MyService.mapper
at mypackage.MyService.mapper(MyService.java:0)

at org.jboss.weld.bootstrap.Validator.validateInjectionPointForDeploymentProblems(Validator.java:370)
at org.jboss.weld.bootstrap.Validator.validateInjectionPoint(Validator.java:291)
at org.jboss.weld.bootstrap.Validator.validateGeneralBean(Validator.java:134)
at org.jboss.weld.bootstrap.Validator.validateRIBean(Validator.java:165)
at org.jboss.weld.bootstrap.Validator.validateBean(Validator.java:529)
at org.jboss.weld.bootstrap.Validator.validateBeans(Validator.java:515)
at org.jboss.weld.bootstrap.Validator.validateDeployment(Validator.java:490)
at org.jboss.weld.bootstrap.WeldStartup.validateBeans(WeldStartup.java:419)
at org.jboss.weld.bootstrap.WeldBootstrap.validateBeans(WeldBootstrap.java:90)
at org.glassfish.weld.WeldDeployer.event(WeldDeployer.java:225)
at org.glassfish.kernel.event.EventsImpl.send(EventsImpl.java:131)
at org.glassfish.internal.data.ApplicationInfo.load(ApplicationInfo.java:328)
at com.sun.enterprise.v3.server.ApplicationLifecycle.deploy(ApplicationLifecycle.java:496)
at com.sun.enterprise.v3.server.ApplicationLifecycle.deploy(ApplicationLifecycle.java:219)
at org.glassfish.deployment.admin.DeployCommand.execute(DeployCommand.java:491)
at com.sun.enterprise.v3.admin.CommandRunnerImpl$2$1.run(CommandRunnerImpl.java:539)
at com.sun.enterprise.v3.admin.CommandRunnerImpl$2$1.run(CommandRunnerImpl.java:535)
at java.security.AccessController.doPrivileged(Native Method)
at javax.security.auth.Subject.doAs(Subject.java:360)
at com.sun.enterprise.v3.admin.CommandRunnerImpl$2.execute(CommandRunnerImpl.java:534)
at com.sun.enterprise.v3.admin.CommandRunnerImpl$3.run(CommandRunnerImpl.java:565)
at com.sun.enterprise.v3.admin.CommandRunnerImpl$3.run(CommandRunnerImpl.java:557)
at java.security.AccessController.doPrivileged(Native Method)
at javax.security.auth.Subject.doAs(Subject.java:360)
at com.sun.enterprise.v3.admin.CommandRunnerImpl.doCommand(CommandRunnerImpl.java:556)
at com.sun.enterprise.v3.admin.CommandRunnerImpl.doCommand(CommandRunnerImpl.java:1464)
at com.sun.enterprise.v3.admin.CommandRunnerImpl.access$1300(CommandRunnerImpl.java:109)
at com.sun.enterprise.v3.admin.CommandRunnerImpl$ExecutionContext.execute(CommandRunnerImpl.java:1846)
at org.glassfish.deployment.autodeploy.AutoOperation.run(AutoOperation.java:164)
at org.glassfish.deployment.autodeploy.AutoDeployer.deploy(AutoDeployer.java:597)
at org.glassfish.deployment.autodeploy.AutoDeployer.deployAll(AutoDeployer.java:484)
at org.glassfish.deployment.autodeploy.AutoDeployer.run(AutoDeployer.java:412)
at org.glassfish.deployment.autodeploy.AutoDeployer.run(AutoDeployer.java:403)
at org.glassfish.deployment.autodeploy.AutoDeployService$1.run(AutoDeployService.java:233)
at java.util.TimerThread.mainLoop(Timer.java:555)
at java.util.TimerThread.run(Timer.java:505)
]]

我该如何解决这个问题?

【问题讨论】:

  • 绝对不是骗人的,但它可能已经被回答过。
  • 从我的角度来看没有重复。当然,我在开始提问之前已经搜索过 SO,但找不到令人满意的答案。
  • 我认为@KumarAbhinav 是正确的(可能重复)。 CDI1.1 默认使用注解来发现 bean。由于指定的 beans 不包含任何作用域注释,因此我们也不会被告知 beans.xml 文件是否存在。
  • 你能提供你的项目结构吗?它是如何包装的?你声明了BeanManger 吗?
  • 可能是重复的,但属于哪个问题?如果我正在寻找有关该主题的信息并找到此页面,我会很生气地看到这个没有链接的重复提及...

标签: java jakarta-ee cdi java-ee-7


【解决方案1】:

您可能处于 annotated bean 发现模式 (the default mode in CDI 1.1+),这就是为什么您的类 MyMapper 不被视为 bean 类。在这种模式下,要被发现的 bean 类应该有一个bean defining annotation@Stateless 是一个定义注解的 bean,因此您的 EJB 也是一个 CDI bean,但它的注入点无法满足,因为 MyMapper 没有发现一个 bean 类。

为了让您的代码正常工作,请尝试将@Dependent 放在您的班级中

@Dependent    
public class MyMapper implements IMyMapper<MyClazz> {}

或者,您可以将项目的发现模式更改为stated in the specification

【讨论】:

    猜你喜欢
    • 2019-10-28
    • 2019-04-09
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-07-25
    • 1970-01-01
    • 2015-04-26
    相关资源
    最近更新 更多