56

状态会话bean定义如下:何时使用无状态会话Bean来使用有状态会话Bean?

状态会话Bean对象的状态由它的值的实例变量的 的。在有状态会话Bean中,实例 变量表示唯一客户端Bean会话的状态。因为 客户端与其bean交互(“会谈”),这个状态通常被称为会话状态 。

无状态会话bean定义如下:

无状态会话Bean无状态会话Bean不维护与客户端的 会话状态。当客户端调用无状态bean的 方法时,bean的实例变量可能包含特定于该客户端的状态 ,但仅在 调用的持续时间内。该方法完成后,不应保留客户端特定状态 。但是,客户端可能会更改共用无状态bean中的实例变量 的状态,并且此状态将保留为 ,直到下一次调用共用无状态bean。除方法调用期间的 以外,无状态bean的所有实例均为 等效,允许EJB容器将实例分配给任何 客户端。也就是说,无状态会话bean的状态应该适用于所有客户端的 。

它也提到无状态会话bean的优点如下:

因为无状态会话bean可以支持多个客户端,他们可以为需要大量客户端的 应用 提供更好的可扩展性。通常,应用程序需要比有状态会话Bean更少的无状态会话 bean来支持相同数量的 客户端。

所以我想到的问题是什么时候应该使用有状态会话bean?为了我对这个问题的天真理解,我们应该坚持尽可能地使用无状态会话bean。

应该使用有状态会话bean的应用程序是什么?任何好的例子?

Session Bean

+0

相关:http://stackoverflow.com/questions/8887140/jsf-request-scoped-bean-keeps-recreating-new-stateful-session-beans-on-every-req – BalusC

回答

95

首先,你必须了解如何把咖啡豆创建并在服务器上进行处理。

对于无状态会话bean服务器可以在池中维护可变数量的实例。每次客户请求这样一个无状态bean时(例​​如通过一种方法),选择一个随机实例来提供该请求。这意味着如果客户端执行两个后续请求,那么有可能两个不同的无状态bean实例为请求提供服务。事实上,两个请求之间没有会话状态。此外,如果客户端消失,无状态bean不会被销毁,并且可以服务来自其他客户端的下一个请求。

另一方面,有状态会话bean与客户端紧密连接。每个实例都被创建并绑定到一个客户端,并仅提供来自该特定客户端的请求。所以如果你对一个有状态bean执行了两个后续请求,那么你的请求将始终来自该bean的同一个实例。这意味着您可以在请求之间保持对话状态。客户端在生命周期结束时调用一个remove方法,这个bean被销毁/准备好进行垃圾回收。

当使用无状态还是有状态的?

这主要取决于你是否想保持会话状态。例如,如果您有一个方法可以合计数字并返回结果,那么您使用无状态bean是因为它只有一次操作。如果您再次使用其他号码调用此方法,则您不再对以前的添加结果感兴趣。

但如果你想例如计算客户端已经完成的请求数,你必须使用一个状态bean。在这种情况下,重要的是知道如何往往是客户端请求过这个bean的方法,所以你必须在bean(例如,用一个变量)来维护会话状态。如果你在这里使用无状态bean,那么客户端的请求将会每次从不同的bean中获得,从而导致你的结果混乱。

+13

“*如果客户端消失bean也被摧毁*“。事实上,有状态会话bean没有得到自动销毁,除非'@ Remove'('javax.ejb')饰的方法是显式调用(该方法甚至不需要编码。它可以简单地空/空因为它是用@ @ Remove'注解)。如果关联客户忘记销毁有状态会话bean,这个bean将被保留在服务器上晃来晃去,直到容器本身决定利用自己的策略将其删除。我错了吗? – Tiny

+3

当然你是对的。在bean的生命周期的更多信息可以在这里找到:http://docs.oracle.com/javaee/6/tutorial/doc/giplj.html – tobiasdenzler

27

我觉得用一个有状态会话bean最大的例子是一个购物车,您存储哪个用户希望购买的所有产品。