Бобы Java предприятия с сохранением информации и не сохраняющие состояние

Я прохожу учебное руководство по Java EE 6, и я пытаюсь понять различие между бобами сессии с сохранением информации и не сохраняющими состояние. Если сеансовые объекты без сохранения состояния не сохраняют свое состояние промежуточные вызовы метода, почему моя программа действует способ, которым это?

package mybeans;

import javax.ejb.LocalBean;
import javax.ejb.Stateless;

@LocalBean
@Stateless
public class MyBean {

    private int number = 0;

    public int getNumber() {
        return number;
    }

    public void increment() {
        this.number++;
    }
}

Клиент

import java.io.IOException;
import javax.ejb.EJB;
import javax.servlet.*;
import javax.servlet.http.*;
import javax.servlet.annotation.WebServlet;
import mybeans.MyBean;
import java.io.PrintWriter;

@WebServlet(name = "ServletClient", urlPatterns = { "/ServletClient" })
public class ServletClient extends HttpServlet {
    private static final long serialVersionUID = 1L;

    @EJB
    MyBean mybean;

    protected void doGet(HttpServletRequest request,
            HttpServletResponse response) throws ServletException, IOException {

        PrintWriter out = response.getWriter();
        mybean.increment();
        out.println(mybean.getNumber());
    }

}

Я ожидал, что getNumber возвратится 0 каждых раз, когда но он возвращается 1, и перезагрузки сервлета в моем браузере увеличивают его больше. Проблема с моим пониманием того, как сеансовые объекты без сохранения состояния работают а не с библиотеками или сервером приложений, конечно. Кто-то может дать мне простое привет мировой пример типа сеансового объекта без сохранения состояния, который ведет себя по-другому, когда Вы изменяете его на с сохранением информации?

89
задан dieter 6 September 2016 в 11:17
поделиться

3 ответа

Важным отличием являются не приватные переменные-члены, а ассоциирование состояния с конкретным пользователем (подумайте о "корзине").

Государственная часть stateful session bean похожа на сессию в сервлетах. Stateful session beans позволяет вашему приложению сохранять сессию, даже если нет веб-клиента. Когда сервер приложений извлекает stateless session bean из пула объектов, он знает, что его можно использовать для удовлетворения ЛЮБОГО запроса, поскольку он не связан с конкретным пользователем.

Сессионный боб с состоянием должен быть выдан пользователю, который получил его в первую очередь, потому что информация о его корзине должна быть известна только ему. Сервер приложений гарантирует, что это так. Представьте, насколько популярным было бы ваше приложение, если бы вы могли начать делать покупки, а затем сервер приложений отдал бы ваш stateful session bean мне, когда я приду!

Итак, ваш приватный член данных действительно "state", но это не "shopping cart". Попробуйте переделать ваш (очень хороший) пример так, чтобы увеличивающаяся переменная была связана с конкретным пользователем. Увеличьте ее, создайте нового пользователя и посмотрите, может ли он по-прежнему видеть увеличенное значение. Если все сделано правильно, каждый пользователь должен видеть только свою версию счетчика.

90
ответ дан 24 November 2019 в 07:11
поделиться

Сессионные компоненты без сохранения состояния (SLSB) не привязаны к одному клиенту, и нет никакой гарантии , что один клиент получит тот же экземпляр. при каждом вызове метода (некоторые контейнеры могут создавать и уничтожать bean-компоненты с каждым сеансом вызова метода, это решение зависит от реализации, но экземпляры обычно объединяются в пул - и я не упоминаю кластерные среды).Другими словами, хотя bean-компоненты без состояния могут иметь переменные экземпляра, эти поля не относятся к одному клиенту, поэтому не полагается на них между удаленными вызовами.

В отличие от этого, сеансовые компоненты с отслеживанием состояния (SFSB) предназначены одному клиенту на всю жизнь, нет обмена или объединения экземпляров (он может быть удален из памяти после пассивации для экономии ресурсов, но это другая история) и поддерживают состояние разговора . Это означает, что переменные экземпляра компонента могут хранить данные относительно клиента между вызовами методов. И это позволяет иметь взаимозависимые вызовы методов (изменения, внесенные одним методом, влияют на последующие вызовы методов). Многоэтапные процессы (процесс регистрации, корзина покупок, процесс бронирования ...) являются типичными вариантами использования SFSB.

Еще одно. Если вы используете SFSB, то вы должны избегать внедрения их в классы, которые по своей природе многопоточные, такие как сервлеты и управляемые bean-компоненты JSF (вы не хотите, чтобы они были общими для всех клиентов). Если вы хотите использовать SFSB в своем веб-приложении, вам необходимо выполнить поиск JNDI и сохранить возвращенный экземпляр EJB в объекте HttpSession для будущих действий. Примерно так:

try {
    InitialContext ctx = new InitialContext();
    myStateful = (MyStateful)ctx.lookup("java:comp/env/MyStatefulBean");
    session.setAttribute("my_stateful", myStateful);
} catch (Exception e) {
    // exception handling
}
134
ответ дан 24 November 2019 в 07:11
поделиться

Без сохранения состояния и с отслеживанием состояния в этом контексте не совсем то, чего вы могли ожидать.

Состояние с EJB относится к тому, что я называю диалоговым состоянием . Классический пример - бронирование авиабилетов. Если он состоит из трех шагов:

  • Резервное место
  • Списание средств с кредитной карты
  • Запрос на выдачу

Представьте, что каждый из них является вызовом метода для сеансового компонента. Сессионный компонент с отслеживанием состояния может поддерживать такого рода диалог , поэтому он запоминает, что происходит между вызовами.

Сессионные компоненты без сохранения состояния не имеют такой возможности для разговорного состояния.

Глобальные переменные внутри сессионного компонента (без состояния или с сохранением состояния) - это нечто совершенно иное. Сессионные бины с сохранением состояния будут иметь пул бинов (поскольку бин может использоваться только в одном диалоге за раз), тогда как сеансные бины без сохранения состояния часто будут иметь только один экземпляр, что заставит глобальную переменную работать, но я не думаю это обязательно гарантировано.

18
ответ дан 24 November 2019 в 07:11
поделиться
Другие вопросы по тегам:

Похожие вопросы: