2014-12-23 2 views
0

В нашем веб-приложении JAVA мы поддерживаем сеанс пользователей в таблице базы данных active_sessions. И мы не разрешаем несколько сеансов для каждого пользователя. что это означает, если вы уже вошли в систему с определенной учетной записью пользователя, вы не можете открыть новый сеанс с той же учетной записью. В случае, если кто-то это делает, мы выводим сообщение об ошибке «Пользователь уже имеет активный сеанс». Когда пользователь нажимает на Logout, его запись из таблицы active_sessions удаляется. Но в случае, если пользователь закрывает окно без выхода из системы, его запись остается в таблице active_sessions. Поэтому любая попытка входа в систему в будущем приводит к ошибке «Пользователь уже имеет активный сеанс». Любые советы о том, как уничтожить сеанс пользователя в базе данных, если он закрывает окно браузера без выхода из системы.Уничтожить сеанс пользователя, хранящийся в базе данных при закрытии окна

Редактировать: После прочтения всех сообщений, похоже, нет чистого способа ограничить один сеанс на пользователя.

+2

Это так опасно! – SMA

+0

Согласен с @almasshaikh. Сессии должны автоматически закрываться по истечении тайм-аута (независимо от того, как пользователь выходит из webapp). Если пользователь не был активным в течение определенного периода времени, убейте их сеанс. Это позволит пользователю снова войти в систему. EDIT: альтернативный метод, следующая попытка входа автоматически аннулирует первый сеанс, носящий этот сеанс. – Dave

+1

Что случилось с несколькими одновременными сеансами? Это ограничение вашего дизайна веб-приложений или проблема лицензирования/права? Я лично ненавижу любое веб-приложение, которое ограничивает мою свободу. –

ответ

2

Используйте событие «onbeforeonload» JavaScript, которое может выполнять вызов AJAX на ваш сервер, чтобы удалить запись. Это событие будет выполняться каждый раз, когда страница будет выгружена, поэтому, если у вас нет SPA, вам нужно проигнорировать событие для href и т. Д.

Согласитесь с Алмасом, однако, что ваш подход опасен в том смысле, что на 100% невозможно обеспечить его соблюдение. Например. если пользователь убивает процесс браузера, тогда даже это событие JS не будет опубликовано. Кроме того, пользователь может просто использовать другой браузер для обхода вашей защиты.

+0

Опасные рекомендации! Что делать, если в качестве злоумышленника я вижу JS, который может вызвать завершение сеанса и случайным образом прерывать сеансы пользователя для других пользователей? – Dave

+1

@Dave, прочитайте вопрос OP; это не закончило бы сессию, а просто удалит ее из БД +, очевидно, что вы не передадите sessionId в вызове AJAX! –

+0

Я прочитал вопрос, и я полагаю, что удаленная запись из таблицы «active_sessions» могла бы эффективно убить сеанс в остальной части webapp (иначе, почему бы просто не оставить Tomcat и т. Д. Для управления сеансом?). Можете ли вы гарантировать, что весь сетевой путь защищен? Если нет, злоумышленник может увидеть sessionId и выполнить требуемые вызовы, чтобы выгнать активного пользователя. Управление сеансами на стороне клиента - это всегда плохая идея. – Dave

1

У пользователей на стороне сервера HTTP-сеанс обычно недействителен после определенного периода простоя. Вы можете реализовать http://docs.oracle.com/javaee/6/api/javax/servlet/http/HttpSessionListener.html и зарегистрировать его в web.xml для получения уведомлений о создании сеанса/уничтожении и т. Д. В реализации вашего слушателя вы можете удалить запись таблицы в событии session destroy.

+0

Если OP может жить с этим, это, безусловно, путь. –

+0

как насчет в случае закрытия вкладки браузера. Его сеанс не будет признан недействительным мгновенно. Но после определенного периода простоя. Поэтому, если кто-то другой откроет новую вкладку в течение тайм-аута сессии, он сможет продолжить сеанс пользователя. Моя основная забота об этом подходе заключается в том, что уведомление из «HttpSessionListener» не будет мгновенным в случае закладки браузера. Таким образом, существует вероятность скомпрометирования учетной записи пользователя. –

0

Основная проблема HTTP заключается в том, что это протокол запроса/ответа. То есть, изменения изменяются или получаются только путем подачи запроса на сервер. Это «ограничение» делает ваше требование интересным. Для этого могут быть два обходных пути: -

  1. Опрос сервера через многократный интервал через вызов AJAX. До тех пор, пока ваше приложение продолжает получать запрос на опрос AJAX, вы можете предположить, что окно открыто.

  2. Используйте javascript (window.onunload), чтобы запустить событие, чтобы уничтожить сеанс пользователя при закрытии браузера.

Using onuload

Смежные вопросы