Ожидаемое поведение EJB с сохранением состояния и без сохранения состояния

Я пытаюсь привести очень простой пример Stateful и Stateless EJB, и я получаю очень неожиданное поведение: как вы можете видеть ниже, stateful bean-компоненты, похоже, создаются каждый раз, в то время как stateless-бины, кажется, вызываются через один единственный пример.

Хотя это каким-то образом имеет смысл, это прямо противоречит тому, что говорится в книге EJB, которую я читаю, поэтому я действительно ошеломлен.

Насколько я понимаю, EJB без состояния используются для выполнения простых запросов без памяти ( такие как вычисления, например), в то время как EJB с отслеживанием состояния должны поддерживать «состояние» во всех клиентских запросах (например, корзина электронной коммерции в Интернете).

Что меня смущает, так это режим экземпляра, так как каким-то образом целое число «count», кажется, отслеживается в bean-компонентах без состояния. Что само по себе не является проблемой, так как этот bean-компонент - теоретически - не нужно повторно создавать экземпляр при каждом вызове, поскольку он выполняет задачу без памяти, в отличие от bean-компонента с состоянием. Тем не менее, книга, которую я читаю ("Веб-разработка EJB 3 на основе примеров", Селинио Фернандес, для протокола), кажется, утверждает обратное, когда дело доходит до инстанцирования: "Один единственный экземпляр компонента с отслеживанием состояния создается для всех вызовов от клиента, тогда как для каждого клиентского вызова вызывается другой экземпляр без сохранения состояния».

Это действительно так? Что мне здесь не хватает? Это утверждение в книге, похоже, не соответствует моему пониманию в приведенном ниже коде.

HelloStatelessEJBRemote lbean0 = doLookup1();
HelloStatelessEJBRemote lbean1 = doLookup1();
HelloStatelessEJBRemote lbean2 = doLookup1();

System.out.println(lbean0.sayHello());
System.out.println(lbean1.sayHello());
System.out.println(lbean2.sayHello());

HelloStatefulEJBRemote fbean0 = doLookup2();
HelloStatefulEJBRemote fbean1 = doLookup2();
HelloStatefulEJBRemote fbean2 = doLookup2();

System.out.println(fbean0.sayHello());
System.out.println(fbean1.sayHello());
System.out.println(fbean2.sayHello());

Консольный вывод:

Hello Stateless World n° 0 !!!
Hello Stateless World n° 1 !!!
Hello Stateless World n° 2 !!!

Hello Stateful World n° 0 !!!
Hello Stateful World n° 0 !!!
Hello Stateful World n° 0 !!!

Код EJB без сохранения состояния:

@Stateless
@LocalBean
public class HelloStatelessEJB implements HelloStatelessEJB Remote {

    int count = 0;

    @Override
    public String sayHello() {
        return "Hello Stateless World n° " + count++ + " !!!";
    }
}

Код StatefulEJB:

@Stateful
@LocalBean
public class HelloStatefulEJB implements HelloStatefulEJB Remote {

    int count = 0;

    @Override
    public String sayHello() {
        return "Hello Stateful World n° " + count++ + " !!!";
    }
}

person Mehdi LAMRANI    schedule 03.01.2017    source источник
comment
спасибо BalusC. Именно это я и подозревал, но не был уверен. Последний абзац о том, что термины клиент и сеанс в контексте EJB абсолютно не совпадают с терминами в контексте WAR, — это различие, которое я упустил.   -  person Mehdi LAMRANI    schedule 03.01.2017