EJB с сохранением состояния и один и тот же сеанс, реплицируемый между клиентами - PullRequest
5 голосов
/ 16 декабря 2011

У меня есть EJB с отслеживанием состояния, который я использую для хранения информации о текущем пользователе в моем приложении. Этот EJB-компонент внедряется в контроллер сервлета и используется для хранения последнего пользователя, вошедшего в систему. Однако на каждом клиенте сеанс выглядит одинаково.

Пример кода EJB:

Stateful
@LocalBean
public class CurrentUserBean {

private string Username;

public void setUser(String un)
{
    Username = un;
}

....

Пример кода сервлета:

public class MainController extends HttpServlet {
       @EJB private CurrentUserBean userBean;

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

                HttpSession session = request.getSession();
                String name = session.getAttribute("username");

                userBean.setUser(name);
                ......

Теперь, когда приложение развернуто на моем сервере, и у меня много разных людей, разговаривающих с сервером с нескольких разных клиентов, имя пользователя всегда задается последним вошедшим пользователем. Другими словами, создается впечатление, что Сессионный компонент с состоянием сохраняет одно и то же состояние для всех клиентов. Это очень смутило меня, когда я прочитал в уроке по java 6 ee следующую цитату со страницы 247:

В сессионном компоненте с состоянием переменные экземпляра представляют состояние уникального сеанса клиент / бин. Потому что клиент взаимодействует («Разговаривает») со своим бином, это состояние часто называют диалоговым государство. Как следует из названия, сессионный компонент похож на интерактивная сессия. Сессионный компонент не является общим; это может иметь только один клиент, так же, как интерактивный сеанс может иметь только один пользователь. Когда клиент завершает работу, его сессионный компонент отображается как завершить и больше не связан с клиентом.

Может ли кто-нибудь объяснить, почему это происходит, а также объяснить, как правильно использовать bean-компоненты с состоянием, которые не поддерживают одинаковое состояние для всех клиентов?

Спасибо.

Ответы [ 2 ]

6 голосов
/ 16 декабря 2011

Хотя у сессионного компонента statefull есть состояние на пользователя (на самом деле сессия), сервлет не имеет.Внедрив его, как вы делаете сейчас, этот сервлет использует один компонент, поскольку он вводится при создании сервлета (вероятно, компонент, принадлежащий первому посетителю).

Вы не должны внедрять компонент, а извлекать его из контекста в методе processRequest.

InitialContext ctx= new InitialContext();
CurrentUserBean userBean = (CurrentUserBean)ctx.lookup("CurrentUserBean");
1 голос
/ 12 июня 2013

Или вы используете

@Inject
Instance<CurrentUserBean> currentUserBeanInstance;

protected void processRequest(...
    CurrentUserBean currentUserBean = currentUserBeanInstance.get();

Только Java EE 6

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...