【问题标题】:Is it possible to @Inject a @RequestScoped bean into a @Stateless EJB?是否可以将@RequestScoped bean @Inject 到@Stateless EJB 中?
【发布时间】:2012-02-01 18:33:40
【问题描述】:

是否可以将请求范围的 CDI bean 注入到无状态会话 bean 中?

我提出了一个相关问题,并认为特定的 CDI @RequestScoped 到 @Stateless 问题值得单独发布。

Passing state between EJB methods / @RequestScoped and @Stateless

我还问了一个关于 JMS @MessageDriven bean 的类似问题——基本上想知道关于 @Stateless 的相同问题。

@RequestScoped CDI injection into @MessageDriven bean

【问题讨论】:

  • 你可以,反正它是一个代理,但它在概念上有意义吗?你不是宁愿反其道而行之吗?这最终会产生更自然和自我记录的代码。
  • 公平点 - 即使它有效,第一眼也很难判断发生了什么。
  • @BalusC 我也持怀疑态度,但查找范围内请求的 CDI 定义。它不仅是 http 请求范围,还包括对异步方法、远程方法、处理 msg 的 mdb 等的请求的范围。所以从这个意义上说,它可以作为 TLS 数据的一种替代品。

标签: jakarta-ee java-ee-6 cdi ejb-3.1 stateless-session-bean


【解决方案1】:

你绝对可以做你提到的事情,并在 @Stateless 会话 bean 和 @MessageDriven bean 中使用 @RequestScoped bean。这是 CDI 规范和 TCK 的核心部分,保证可移植。

关于 MDB 的注意事项

请注意,有一个使用@RequestScoped bean 的@Stateless bean 的测试,但是没有保证@MessageDriven bean 可以引用@RequestScoped bean 的测试。这只是一个疏忽,是already fixed for the Java EE 7 TCK。所以请注意,如果它不适用于 MDB 案例,那可能不是你的错 :)

解决方法是简单地将您的 MDB 委托给任何类型的 SessionBean,例如 @Stateless@Stateful@Singleton 都具有 @RequestScoped 测试。

使 EJB 本身具有范围

虽然@Stateless@Singleton@MessageDriven 可以通过@Inject 注入作用域引用,但它们不能成为 @RequestScoped 或任何其他作用域。只有@Stateful 模型足够灵活以支持范围。换句话说,您可以将@Stateful bean 类本身注释为@RequestScoped@SessionScoped 等。

简单来说@Stateless@Singleton 已经固定了“范围”。 @Singleton 本质上是 @ApplicationScoped@Stateless 可能是一些像 @InvocationScoped 这样的虚构范围,如果存在的话。 @MessageDriven bean 的生命周期完全取决于驱动它的连接器,因此也不允许有用户定义的范围。

【讨论】:

  • David,在 MDB 范围内注入某些请求是如何工作的?假设我的 MDB 在 cron 计时器触发时由 Quartz RA 触发。那时没有活动的http请求。范围从何而来?如果从来没有任何真正的请求开始,它什么时候结束?
  • 没关系,刚刚发现 @RequestScoped 在 CDI 中的定义比 HTTP 请求更广泛。
  • 这个文档说@Stateless beans 只能是@Dependent:docs.oracle.com/cd/E24329_01/web.1211/e24368/cdi.htm#CHDFHBCI我猜这只是他们的说法@Stateless beans 有自己的生命周期,没有别的(@RequestScoped, @SessionScoped,等)在应用于它们时是有意义的。
猜你喜欢
  • 2012-07-03
  • 2013-12-07
  • 1970-01-01
  • 1970-01-01
  • 2013-12-31
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2017-04-13
相关资源
最近更新 更多