Retardo progresivo trar error en identificación Struts

Buenas de nuevo!
Ya he hecho lo de los tiempos y te comento.
En un principio utilicé simplemente un "Thread.sleep(intentos * 2000)", consiguiendo así
un retardo progresivo de 2 segundos por cada intento fallido a costa de "dormir" la ejecución, y funcionaba muy bien. El único inconveniente es que cuando provocaba un "timeout" (establecí el valor de web.xml a 60 segundos) metiendo muchos fallos consecutivos, se creaba automáticamente una nueva sesión y perdía la cuenta de los intentos, por lo que el siguiente fallo de acceso de usuario comenzaba de nuevo en 0 segundos de retardo. Quizá no es demasiado grave, porque el "timeout" suele ser mucho mayor, pero no es exactamente lo que quería.
Pensé que la solución que me diste de hacer un redirect hacia ella misma evitaría este
problema, ya que sólo dormía la ejecución en intervalos de 2 segundos entre cada redirect,
pero sin embargo funciona de la misma manera. El "timeout" se produce, se crea una nueva sesión, y pierdo los datos de la sesión anterior por lo que pierdo el conteo de los
intentos fallidos.
Aparentemente a mí me parece que el comportamiento no es el que preveíamos, puesto que no considera el redirect como una acción que anule el tiempo de inactividad en la aplicación.
¿Qué me dices al respecto?

1 Respuesta

Respuesta
1
No es eso lo que te pretendía proponer...
A ver si soy capaz de explicártelo brevemente sin entrar en código.
"login": login, password --> submit --> accion "validar".
"validar" :
Usuario válido . forward a página de entrada de la aplicación.
Usuario inválido. Almacena en sesión :
* numero de intentos hechos hasta ahora
* hora:min:seg de ultimo intento de acceso.
--> Forward a acción "esperar".
"esperar" : Esperar es una página que muestra un mensaje del tipo "validando usuario..." que cada dos segundos hace un redirect hacia ella un numero de veces dependiendo del tiempo que haya pasado desde el último acceso y el numero de intentos.
Así si para un intento la espera es de 2 seg, para dos intentos 4 segundos...
Una vez haya hecho esas redirecciones... vuelve a "login" indicando que es un usuario no válido...
Otra opción es en lugar de guardarlo en la sesión es tener en base de datos una columna para el login de usuario con el numero de intentos fallidos y la fecha del último intento fallido (que se borra al hacer un acceso exitoso) y hacer lo mismo pero evitando la sesión.
No se si me explico así mejor.
Esa es la solución que se me ocurre. Lo que tu haces puede provocar más problemas que solucionarlos...
Pues... no entiendo nada! Sí que entiendo lo que me quieres decir, pero es lo que he hecho!, o al menos eso creo yo. Te explico más detalladamente sin meterme demasiado en código.
El usuario hace el login con su identificador y password, me voy a la action correspondiente, y ahí verifico su identidad. Si es correcta le doy paso a la aplicación, y si es errónea... vamos con ello que ahí está la miga.
En la action de identificación guardo en sesión 2 atributos. Uno representa el número de intentos de acceso, que con cada login erróneo es una unidad mayor, y otro representa el número de redirecciones a la página de espera, que con cada login erróneo comienza siempre de 0. Yo no entiendo la razón de guardar el momento del último acceso. Es indiferente para aplicar el retardo puesto que multiplico segundos por intentos, es decir, 2 segundos de retardo por 3 intentos igual a 6 segundos de espera, por ejemplo.
El forward a la action esperar la hago con "return mapping.findForward(wait);", donde en struts-config.xml tengo:
Como ves, "solicitarEspera.do" no es una página jsp sino una llamada a otra action (EsperaAction), que es la que implementa la espera. Ahí, obtengo de la sesión los 2 atributos guardados
anteriormente, hago un "Thread.sleep(2000);" porque se ha producido un fallo de login, y
seguidamente comparo el número de redirects realizados con el número de intentos fallidos
de acceso. Si el primero es menor hay que aplicar otros dos segundos más de retardo, por lo que incremento en una unidad el número de redirects guardándolo en sesión y redirecciono a ella misma con "return mapping.findForward(wait);", y si ya son iguales, redirecciono a la
página de login con return "mapping.findForward(success);" para que el usuario lo intente
de nuevo si quiere.
Yo es que tampoco veo la diferencia entre hacer esperar al usuario en una página jsp llamada "esperar" mostrándole "validando usuario..." como tú me sugieres, que hacerle esperar en la propia página jsp del formulario de login. De todos modos lo he intentado, y he acabado usando el mismo código pero en una página jsp en vez de en una action, con la salvedad de que desde la página jsp "esperar" no he sabido redireccionar a ella misma, y desde la action sí que sé con el mapping.findForward
Todo esto es lo que yo he sacado en claro de tu explicación, pero ahora tú me dirás en qué no te he entendido :)
Otro saludo
Perdona que no te haya contestado antes, el maldito editor nuevo de todoexpertos no me dejaba enviar.
El problema es el "Thread.sleep". Debes de evitarlo a toda cosa, el navegador responderá con un "el servidor no responde". No mostrará nada al cliente y te puede dejar el servidor "frito" con peticiones que se quedan en espera.
Desde el JSP puedes hacer un "redirect" usando"response.sendRedirect("pag.jsp");
La diferencia entre "esperar en la página de login" y "esperar en validando usuario" es la tendencia casi enfermiza del usuario a darle al F5. Si el servidor te muestra un "validando usuario", el usuario sabe que está siendo validado, por eso tarda.. voy a darle al f5 a ver si tarda un poco menos... pero tardará siempre "lo mismo", puesto que solo ha hecho una petición de login.
... si al usuario no le dices nada, simplemente piensa "está roto vaya mierda siempre me pasa lo mismo a mi la culpa de todo lo tiene el gobierno ojalá me toque la lotería" mientras le va dando al f5 y te está mandado varias peticiones de login simultaneas con lo que cada vez tarda más, puesto que la última es la que vale.
No se si me explico mejor así.
Mi consejo es que no hagas al usuario esperar, si quieres limitar el numero de intentos por un tiempo lo mejor es mostrar un mensaje cuando haga tres (o más) intentos fallidos diciendo "has intentado acceder tres veces con contraseña invalida, cuenta bloqueada durante 10 minutos". Guardas en base de datos el ultimo acceso inválido y al hacer login si la cuenta está bloquea, no dejas acceder aunque de una password válida.
Lo miraré detenidamente y te comentaré, ¿ok?
Saludos
Finaliza la pregunta.

Añade tu respuesta

Haz clic para o

Más respuestas relacionadas