¿Cómo puedo obtener una lista de todos los objetos HttpSession en una aplicación web?
Digamos que tengo una aplicación web basada en Java en ejecución con 0 o más objetos HttpSession
válidos asociados a ella. Quiero una forma de acceder a la lista actual de objetos HttpSession
válidos. Estaba pensando que podría implementar un HttpSessionListener
y usarlo para agregar a una lista de valores de id de sesión que se almacenan en un atributo de ámbito de aplicación, pero luego estoy en el gancho para actualizar la lista a medida que las sesiones se invalidan y quién sabe qué más.
Antes de empezar a hornear mi propia solución pensé que debe hacer la pregunta:
¿La API servlet proporciona algún medio para obtener acceso a la lista completa de objetos de sesión no invalidados?
Estoy usando Tomcat 6.x como contenedor de mi aplicación web, y MyFaces 1.2.biblioteca x (JSF).
SOLUCIÓN
Seguí un enfoque similar a lo que BalusC discutió en estas preguntas existentes:
- Cómo implementar fácilmente " quién es online " en Grails o Java Aplicación ?
- JSF: Cómo invalidar un sesión de usuario cuando se registra dos veces con las mismas credenciales
Modifiqué por la clase SessionData
para implementar HttpSessionBindingListener
. Cuando ocurre un evento de enlace, el objeto se agregará o eliminará del conjunto de todos los objetos SessionData
.
@Override
public void valueBound(HttpSessionBindingEvent event) {
// Get my custom application-scoped attribute
ApplicationData applicationData = getApplicationData();
// Get the set of all SessionData objects and add myself to it
Set<SessionData> activeSessions = applicationData.getActiveSessions();
if (!activeSessions.contains(this)) {
activeSessions.add(this);
}
}
@Override
public void valueUnbound(HttpSessionBindingEvent event) {
HttpSession session = event.getSession();
ApplicationData applicationData = getApplicationData();
Set<SessionData> activeSessions = applicationData.getActiveSessions();
if (activeSessions.contains(this)) {
activeSessions.remove(this);
}
}
Lo único que me sigue irritando es lo que sucede cuando se reinicia Tomcat. A menos que Tomcat se haya configurado correctamente para NO serializar las sesiones en el disco, haciéndolo. Cuando Tomcat se inicia de nuevo, los objetos HttpSession
(y los objetos SessionData
junto con ellos) se deserializan y las sesiones se vuelven válidas de nuevo. Sin embargo, la serialización/deserialización deja totalmente de lado los eventos de escucha HttpSession
, por lo que no tengo la oportunidad de poner la referencia deserializada a SessionData
de nuevo en mi Conjunto administrado de objetos después del reinicio.
No tengo ningún control sobre la configuración de producción de Tomcat en la organización de mi cliente, por lo que No puedo asumir que se hará de la manera que espero.
Mi solución es comparar el tiempo de creación de HttpSession
con el tiempo de inicio de la aplicación cuando se recibe una solicitud. Si la sesión se creó antes de la hora de inicio de la aplicación, entonces llamo a invalidate()
y el usuario es enviado a una página de error/advertencia con una explicación de lo que sucedió.
Obtengo el tiempo de inicio de la aplicación implementando un ServletContextListener
y almacenando el tiempo actual dentro de un objeto de ámbito de aplicación desde dentro del método contextInitialized()
de mi oyente.
3 answers
No, la API de Servlet no proporciona una forma. Usted realmente tiene que conseguir el asimiento de todos con la ayuda de un HttpSessionListener
. Puede encontrar varios ejemplos en las siguientes respuestas:
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-05-23 11:46:46
No hay un camino directo. Depende del despliegue. Lo anterior fallará una vez que decida introducir la implementación distribuida y el equilibrio de carga.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2010-09-24 14:01:40
No es realmente una respuesta, pero en los viejos tiempos había "javax.servlet.http.HttpSessionContext", pero fue eliminado a partir de la versión 2.1, explícitamente sin reemplazo: https://tomcat.apache.org/tomcat-5.5-doc/servletapi/javax/servlet/http/HttpSessionContext.html
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2015-12-07 19:05:50