【问题标题】:EJB Injection between EAR's on JBoss7JBoss7 上 EAR 之间的 EJB 注入
【发布时间】:2013-08-26 09:39:12
【问题描述】:

是否可以在不进行 JNDI 查找的情况下从同一应用服务器中的另一只耳朵注入 StatelessBean?作为应用服务器,我们使用的是 JBoss 7.2。

我有以下设置:

EAR1
│   services1-0.1.jar
│   web-0.1.war
│
├───lib
│       EAR2-SERVICES-api-0.1.jar
│
└───META-INF
        application.xml
        beans.xml


EAR2
│   EAR2-SERVICES-impl-0.1.jar
│
├───lib
│       EAR2-SERVICES-api-0.1.jar
│
└───META-INF
        application.xml
        beans.xml

EAR2 包含例如以下服务:

@Named
@Stateless
public class ServiceBean implements Service { }

和界面:

@Remote
interface Service { }

来自 EAR1 的调用者应该只考虑 API 而不是实现。我如何实现,这是有保证的。当我必须使用 JNDI 名称时,我必须知道实现的位置。

为了将 Service 注入 EAR1,我尝试了 @Inject@EJB。但我总是得到Caused by: org.jboss.weld.exceptions.DeploymentException: WELD-001408 Unsatisfied dependencies for type [Service] with qualifiers [@Default] at injection point [[field] @Inject package.ServiceBean.service]

MANIFEST.MF 依赖于 deployment.EAR2.ear

【问题讨论】:

  • 类加载器隔离了两只耳朵,所以它们看不到对方。

标签: java jakarta-ee jboss cdi


【解决方案1】:

由于应用程序服务器的类加载器隔离了两个应用程序,EAR1 无法看到服务接口的实现,这就是它抱怨依赖关系不满足的原因。我建议您在 EAR1 中实现一个生产者方法来查找,并在 EAR2 中实现将调用远程 ejb 的 ejb 代理。这个page 描述了如何查找远程ejb。生产者方法应如下所示:

 @Produces
 public Service produceService() {
   Properties jndiProps = new Properties();
   jndiProps.put(Context.INITIAL_CONTEXT_FACTORY,"org.jboss.naming.remote.client.InitialContextFactory");
   jndiProps.put(Context.PROVIDER_URL,"remote://localhost:4447");
   // create a context passing these properties
   Context ctx = new InitialContext(jndiProps);
   // lookup
   Service service = (Service) ctx.lookup("<jndi name of the ejb>");
   return service;
}

这将满足 CDI 抱怨的依赖关系。

【讨论】:

  • 我可以使用 @EJB(lookup = ) 而不是生产者,它工作正常,但我总是必须知道实现的位置。这就是我难过的地方。如果 Service 的用户只需要了解 API 而无需了解实现,这将是一个很好的模式。
  • 您不能使用@EJB(lookup=...),因为您必须提供部署实现的远程服务器的地址。服务的用户必须知道实际服务在哪里,因为它可能不仅在同一台服务器上,而且可能在任何地方。您可以使用某种外部配置,甚至环境属性来提供远程实现的地址。
猜你喜欢
  • 2014-08-09
  • 2016-11-11
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多