0

我想使用 Enterprise Java Beans 创建一个 Web 日历。所以我编写了一个有状态的 CalendarBean 类(@Stateful)。作为一个属性,我使用双端队列来存储所有日期。或者,我可以在最后或开始时添加新的一年。在 JSP 中,我使用<jsp:useBean>-Tag。在每次调用 JSP 时,都会创建一个新的 Bean 实例。每次它创建一个新的双端队列。

我该如何预防?我只想要一个像 Singleton 一样的 Bean 实例。

4

2 回答 2

0

在有状态会话 Bean 中,实例变量表示唯一客户端 bean 会话的状态。因此,每个客户端都有自己的实例。如果你想要 Bean 的实例,你可以使用 Statefull Session bean 或 Singleton Session bean。你可以看到:http ://docs.oracle.com/javaee/5/tutorial/doc/bnbly.html

于 2013-07-16T05:56:37.900 回答
0

请参阅Java EE 6 中的上下文和依赖注入一文。它说:

@Stateful在注入过程中,容器会创建一个bean。

因此,当您的 JSP 编译运行时,容器将注入一个新的CalenderBean.

如果您希望您的 bean 成为单例,最好将其声明为@Stateless,并使其无状态:它的行为不应依赖于任何实例变量的状态。这意味着,如果两个线程同时访问 bean,它们不应该能够通过修改实例变量来影响 bean 对彼此的行为方式。

例如,如果您的 CalenderBean 有一个实例变量private Calendar calendar,并且您的实例方法执行以下操作:

this.calendar.set(Calendar.YEAR, input.getYear()); // where input is a parameter
                                                   // to the method you were calling
return calendar.get(Calendar.ERA);

现在想象两个访问者在完全相同的实例中访问您的网页,但他们有不同的输入:

  • 用户 1 拥有input.getYear()的是2000
  • 用户 2 拥有input.getYear()的是-5

由于我们不能保证这两个线程将被顺序处理,因此可能会发生以下情况:

  • 为用户 1 服务的线程将年份设置为2000
  • 为用户 2 服务的线程将年份设置为-5
  • 为用户 1 服务的线程设置 ERA 并返回GregorianCalendar.BC

这显然是错误的:用户 1 影响了CalendarBean用户 2 的工作方式,这样,bean 就不是无状态的。

于 2013-07-16T06:00:38.097 回答