【问题标题】:Bean interface and Bean implementation in different projects不同项目中的Bean接口和Bean实现
【发布时间】:2016-06-14 16:22:07
【问题描述】:

是否可以在一个项目中拥有一个 bean 接口,并在另一个项目中实现该 bean,该项目包含以前的项目作为依赖项?

我有如下界面:

package com.proj1.util;
import .....;

public interface Notification {

   addNotification();
   addError();    

}

在同一个项目(即 Proj1)中,我还有以下课程:

package com.proj1.util.exception;
import .....;

public class ExceptionHandler extends RuntimeException ... {
   private String errorMessage;

   @Override
   public void handle() {
      Util.getBeanInstance(Notification.class).addError(errorMessage);
   }    

}

现在在第二个项目中,我有Notification 的实际实现如下:

package com.proj2.beans;

@Named
@ConversationScoped
public class NotificationBean implements Notification, Serializable {
    private static final long serialVersionUID = 1L;

    ...
}

这种情况会导致 Tomcat 中出现异常,并显示消息“WebBeans context with scope type annotation @ConversationScoped does not exist within current thread

我的建议是添加一个工厂来生成我的 NotificationBean,但它似乎没有太大变化。

package com.proj2.beans.cdi;

import javax.enterprise.inject.New;
import javax.enterprise.inject.Produces;

import com.proj1.util.Notification;

public class NotificationBeanFactory {

    @Produces
    public Notification create(@New NotificationBean notificationBean) {
        return notificationBean;
    }
}

问题是如何在一个项目中使用一个 bean,在这个项目中我只有它的接口,而 bean 实现在另一个项目中。有可能吗?

【问题讨论】:

  • 异常表明有问题的线程(尝试获取 bean 的线程)不是 HTTP 请求线程。换言之,HTTP 会话和 HTTP 会话等 HTTP 相关范围不可用。这是真的?那为什么是@ConversationScoped呢?您究竟希望容器在哪里存储实际的 bean 实例?
  • 这是一个 JSF 应用程序,请求是从浏览器发出的,所以它是一个 HTTP 请求。虽然可能是因为还没有开始对话。 NotificationBean 实际上应该管理我所有应用程序的消息(错误、警告等)。将其设置为会话范围会更明智吗?

标签: java jakarta-ee cdi jboss-weld


【解决方案1】:

异常表明没有正在进行的对话,因此我将首先确定您何时尝试使用 @ConversationScoped bean 以及来自哪个类。

您的代码片段表明ExceptionHandler 类调用了一个神奇的公式,我们对此一无所知:

Util.getBeanInstance(Notification.class).add(...);

在没有活动对话时尝试使用它可能会导致您看到异常。因此,您可以将@Inject ExceptionHandler 转换为NotificationBean,这样您就只能在有活跃对话时使用它。

关于不同项目中接口和实现的焊接问题;有可能的。在你的proj2 Weld 中将简单地识别一个 bean NotificationBean 并且在它的类型中也会有Notification 因此你可以然后@Inject Notification。 但反过来它可能不起作用 - 在proj1 你不能@Inject Notification 因为proj1 本身没有任何可以实现该接口的bean。

【讨论】:

  • Util.getBeanInstance(...) 是我构建的一组实用方法,它们使用 BeanManager 获取 bean 并返回请求的 bean。事实上,除非没有打开对话,否则整个设计都是有效的。这正是正在发生的事情,因为我的应用程序在打开某个对话之前失败并尝试输出错误消息通知。
猜你喜欢
  • 1970-01-01
  • 2019-09-03
  • 1970-01-01
  • 2017-08-18
  • 2015-10-09
  • 2021-09-03
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多