Foros Club Delphi

Foros Club Delphi (https://www.clubdelphi.com/foros/index.php)
-   PHP (https://www.clubdelphi.com/foros/forumdisplay.php?f=15)
-   -   Cómo implementar un límite de "intentos de acceso" (https://www.clubdelphi.com/foros/showthread.php?t=63957)

roman 12-03-2009 01:20:06

Haz la prueba David, no me digas nada más que no se puede. Sigue el flujo de lo que pasaría con el tal snoopy intentando acceder (#$@&%! perro, ¡cómo da lata! :D)

Caso A) Snoopy intenta acceder directamente a login.php. No importa si es la primera vez o la chorrocientas. Como el condenado perro cambia la sesión, para login.php será como si fuera la primera vez. Por tanto le da una patada.

Caso B) Snoopy intenta acceder primero a login-form.php. Ahí se establece la sesión, pero, como el condenado perro la cambia, al acceder a login.php estamos como en el caso (a) y le damos una patada.

La única posibilidad que tiene el animal, es preservando la sesión.

pd: Las patadas al perro son simuladas. En el desarrollo de este código no se ha lastimado a ningún cachorrito :D.

// Saludos

dec 12-03-2009 01:36:15

Hola,

Jodó con el perrito. :D

¡Pero no digas que no lo probé! Inicié este mismo hilo porque lo había probado y, para mi sorpresa, no funcionaba...

Cita:

Empezado por Román
Caso A) Snoopy intenta acceder directamente a login.php. No importa si es la primera vez o la chorrocientas. Como el condenado perro cambia la sesión, para login.php será como si fuera la primera vez. Por tanto le da una patada.

El punto está en que "Como el condenado perro cambia la sesión, para login.php será como si fuera la primera vez". No es que el condenado chucho cambie la sesión, sino que no la inicia nunca, o, dicho de otra forma (pero igual resultado), siempre inicia una nueva. Y no podemos darle la patada a alguien que llega por primera vez a nuestro sitio... ¡ni aunque sea un chucho, que los hay podencos! :D

Cita:

Empezado por Román
Caso B) Snoopy intenta acceder primero a login-form.php. Ahí se establece la sesión, pero, como el condenado perro la cambia, al acceder a login.php estamos como en el caso (a) y le damos una patada.

En el caso de Gesbit existe un formulario, un "script", que, junto con la clase GbUser (y GbDb, entre otras, pero, es otra historia) se encargan de la autenticación del usuario. Pero, a todos los efectos, es como si fuera un solo "script". Creo que esto puede confundirte Román.

En efecto, si hubiese que pasar por dos "script", incluso si hubiera que pasar por el mismo, dos veces, el asunto pintaría de otra forma, podríamos usar la sesión de usuario, y, en caso de no encontrarla en el segundo "script", denegar el acceso al can. Esto sería una solución ideal, acaso, pero, recuerda que el perrito rellena y envía el formulario en un mismo punto.

No ha de pasar por dos lugares, por tanto, no puede usarse el primero para establecer la variable de sesión que comprobar en el segundo. En realidad sólo ha de pasar por un lugar. Y podemos establecer la variable de sesión que queramos, porque, como cuando vuelva a pasar, lo hará con otra sesión de usuario diferente, dicha variable no existirá, no podremos usarla, no nos servirá de nada.

Ya digo. vBulletin lo implementa apoyándose en la base de datos. PhpBB ni siquiera lo implementa... si pudiera hacerse usando sesiones de usuario, de alguna manera, sería bastante sencillo de implementar, y, sin embargo, no se hace, porque no funciona. Funciona para personas, pero, con los cánidos parece que no pueden usarse sesiones de usuario, al menos no para lo que nos ocupa ahora. :(

dec 12-03-2009 01:51:00

Hola,

Hum... ¿y si forzáramos tanto a cuadrúpedos como a personas a pasar dos veces por el "script"? Dicho de otro modo, mirar si existe la variable de sesión cuando se envía el formulario, y, si no existe, mandar a quien sea a freír espárragos. Huy, huy, huy, que me parece que tú ibas por aquí y no lo he sabido captar hasta ahora...

Claro que habrá que pensar en los posibles inconvenientes... pero, da que pensar. :rolleyes:

roman 12-03-2009 01:54:28

Cita:

Empezado por dec
¡Pero no digas que no lo probé! Inicié este mismo hilo porque lo había probado y, para mi sorpresa, no funcionaba...

Lo que tú probaste no es lo mismo que yo propongo, ojo.

Cita:

Empezado por dec
Y no podemos darle la patada a alguien que llega por primera vez a nuestro sitio...

Claro que podemos, y lo haremos, si no llega por la puerta adecuada.

Cita:

Empezado por dec
En el caso de Gesbit existe un formulario, un "script", que, junto con la clase GbUser (y GbDb, entre otras, pero, es otra historia) se encargan de la autenticación del usuario. Pero, a todos los efectos, es como si fuera un solo "script". Creo que esto puede confundirte Román.

Al contrario, si hablo de dos scripts es sólo para facilitar la charla y no decir: el script en una petición GET y el script en una petición POST, por ejemplo :)

Cita:

Empezado por dec
En efecto, si hubiese que pasar por dos "script", incluso si hubiera que pasar por el mismo, dos veces, el asunto pintaría de otra forma, podríamos usar la sesión de usuario, y, en caso de no encontrarla en el segundo "script", denegar el acceso al can. Esto sería una solución ideal, acaso, pero, recuerda que el perrito rellena y envía el formulario en un mismo punto.

No es el mismo punto. Aunque uses un mismo archivo user-login.php, se trata de momentos distintos:

1. Cuando se despliega el formulario (y se establece la variable de sesión)
2. Cuando se procesa el formulario (y se checa la existencia de la variable)

Ya también te puse el ejemplo de ese caso (un sólo script)

Cita:

Empezado por dec
No ha de pasar por dos lugares

Que sí, hombre, que sí.

Esto es como el espacio-tiempo (¿recuerdas a Carl Sagan?). La puerta de tu casa hoy no es el mismo lugar que la puerta de tu casa mañana. En términos del espacio-tiempo son dos ubicaciones distintas. No es lo mismo el script en una petición GET que el script en una petición POST, son dos ubicaciones distintas en el HTTP-tiempo :D

Cita:

Empezado por dec
vBulletin lo implementa apoyándose en la base de datos.

// Saludos

dec 12-03-2009 01:59:08

Hola,

Que sí, que sí, ahora lo veo un poco más claro. No sé si es que me he ofuscado en contra del uso de variables de sesión, pero, en efecto, como has explicado, se trataría de no aceptar en nuestra casa a nadie que entrara a trompicones. ¿No te limpiaste los pies en el felpudo de la entrada? Pues no entras. ¿Te los limpiaste? Deja que lo vea... vale, pasa pa'dentro.

Tiene cierta lógica y, en efecto, le encuentro sentido. Ahora, lo que me llama la atención es que sistemas populares no implementan algo así, si, como parece, es bastante sencillo... (aunque no evidente) ¿acaso habrá alguna razón que se nos escapa? Pero, sea como sea, es cierto, tengo que probarlo de nuevo teniendo todo lo que has explicado en cuenta. ¡Gracias Román! :)

dec 12-03-2009 02:12:24

Hola,

Estoy haciendo pruebas, no me quiero ilusionar, pero, ¡parece que podría valer! :D

roman 12-03-2009 02:36:22

Mmmm.

Se me ocurre que podemos amaestrar un perro y hacer que se comporte mordiendo sólo tres veces. Pero, podemos amaestrar más de un perro ¿no?

:(

// Saludos

dec 12-03-2009 02:42:16

Hola,

Yo ahora mismo estoy probando, y, con alguna que otra "dificultad inesperada" parece que podría valer, ¿por qué dices ahora esto último? ¿Has averiguado algo? :rolleyes:

roman 12-03-2009 02:48:08

Pues que a final de cuentas, tienes razón. A usar la base coño :D

Es cierto, con el mecanismo que propongo, el perro tiene que preservar la sesión para siquiera poder intentar el login. Pero ¿y eso qué? En cuanto reciba el ok o not ok de la autenticación, el condenado cánido cambia la sesión. Ya es otro perro y vueve a intentar, una y otra vez. Mientras no se amarre la IP (debo repetirme esto cien veces), no tiene ningún caso.

// Saludos

dec 12-03-2009 02:55:04

Hola,

¡Pero cómo que no! ¡¡Si acabas de convencerme de lo contrario!! :D :D :D

Lo estoy ahora mismo probando Román, y, parece que funciona... Este es el código que de momento está ejecutándose al "entrar" al formulario:

Código PHP:

  public function AssertAccessRetries(){
    global 
$gbInput;
    if(isset(
$_SESSION[GBUSER_SESSION_ACCESS_RETRIES])){
      if(
$_SESSION[GBUSER_SESSION_ACCESS_RETRIES
       >= 
GBUSER_MAX_ACCESS_RETRIES_NUM){
         return new 
GbError(array(
           
ra('Maximum user access retries detected.'),
           
ra('Please, close your session and try again.')
         ));
      }
    }else{
      if(
$gbInput->IsHttpGetRequest()){
        
$_SESSION[GBUSER_SESSION_ACCESS_RETRIES] = 0;
      }
    }
  } 

Y, este otro, se ejecutaría sólo cuando se enviase el formulario:

Código PHP:

  if(!isset($_SESSION[GBUSER_SESSION_ACCESS_RETRIES])){
    return new 
GbError(ra('Invalid user session. Please, try again.'));
  }else{
    
$_SESSION[GBUSER_SESSION_ACCESS_RETRIES]++;
  } 

El primero me parece más curioso que el segundo: fíjate que si no existe la variable de sesión, no la establece sin más: sólo lo hace si la petición es HTTP GET. Como pulgoso manda el formulario vía HTTP POST... se va a encontrar (y de hecho se encuentra) con el segundo código...

Ya digo, el asunto parece funcionar, aunque, no dudo de que pudiera "complicarse" lo que quisiese, guardando IPs, fechas, etc. Sin embargo, creo que podría valer tal cual, sin tantas complicaciones, pues, los problemas no los tendría el usuario normal y corriente, sino los caniches "roba contraseñas"... y de eso se trata, ¿no?

¡¡¡Ahora vas a decirme que no!!! :D :D :D

Lo que hay que hacer es pruebas y más pruebas... suponiendo varias posibilidades, cuantas más mejor, y ver si el invento aguanta o qué. :)

roman 12-03-2009 03:09:56



No sirve.

A ver, tú mismo dijiste desde el principio, que si el usuario accede como gente bien desde un navegador, sólo puede hacer tres intentos y no podrá volver hasta que no cierre su sesión. Ahora el perro hace lo mismo: manda la cookie de sesión (que lee en el primer acceso al formulario) y queda como perro bueno y tu script intenta la autenticación. Ni siquiera vuelve a intentarlo, simplemente cambia -ahora sí- la sesión e intenta de nuevo, bien portado, y es como si fuera la primera vez.

Tiene que amarrarse la IP.

// Saludos

dec 12-03-2009 03:17:34

Hola,

Bueno. Mientras hacía las pruebas, algunas mejoras he añadido, de todas formas. Y sigo haciendo pruebas... porque chico, ¡ahora parece que sí que sirve! Estoy intentándome poner en la piel del pitbull, a ver qué tendría que hacer, según tú dices... Estoy aquí con Snoopy y ya no puede enviar, directamente, el formulario, eso está claro. Se me había saltado antes comprobar si se enviaba el formulario mediante HTTP POST, esto ahora se comprueba. De modo que no puede hacer una petición HTTP GET, porque, aun con datos buenos, no funcionaría.

Ahora tú dices que podría hacer primero una petición, y luego otra, manteniendo la sesión, enviando la cookie correspondiente, pero, si lo hace así, ¿no estaríamos consiguendo lo que queremos? Tengo un lío de espanto, ahora mismo. De todas formas, lo siento sólo por ti, pues, como digo, entre pitos y flautas he hecho algunos cambios y mejoras que ya no me las quita nadie. Y sigo probando a ver... :)

dec 12-03-2009 03:23:51

Hola,

Sigo probando, Román, y, enviando la cookie de sesión, lo que obtengo con el "script" es que al cabo supero el número de intentos... ¿no se cumple ya con esto el objetivo? El pitbul puede pasarse por caniche, pero, entonces jugará con las reglas, y sólo tendrá un número de intentos posibles, dificultando el ataque por fuerza bruta. O sea, que, bien. ¿O tengo que probar de otra manera? :rolleyes:

roman 12-03-2009 03:26:55

Ya te caerá el veinte, ya te caerá :p

A ver. Estás de acuerdo que con un navegador normalito puedo hacer tres intentos y ya, ¿no es cierto? Aún con el mecanismo de ahora.

Pero también estás de acuerdo que si cierro el navegador puedo realizar otros tres intentos ¿no?

Pues esto es lo que hace el perro. Luego de sus tres intentos, "cierra" el navegador cambiando la cookie de sesión (de hecho, simplemente no mandándola), y va de vuelta la mula al trigo...

// Saludos

dec 12-03-2009 03:29:00

Hola,

Sí; acabo de caer del guindo, como suele decirse. Je je je... ¿ves como no era tan sencillo?

¡Te lo he dicho desde un principio! Y tú erre que erre... :D :D :D

¡Fail! :D

PD. De todas maneras, insisto, he hecho algunos cambios por el camino bastante útiles. ;)

Código:

1.3 - 12/3/2009

 [?] Better recognition of HTTP POST form submitted in admin forms
 [?] Change GBCACHE_EXPIRE_SESSION_CHECK for more descriptive value
 [?] GbError class send now an HTTP 404 error code to clients
 [+] GbInput IsPostFormSubmit, IsHttpGetRequest, IsHttpPostRequest

No está mal para empezar el día, digo la noche, bueno, allí el día, o la tarde, aquí la noche, madrugada. ¡Eh! :D

roman 12-03-2009 03:29:53

Vamos a ver si cuando te convenza de esto no ya me convenciste tú a mi de lo contrario, y así ad infinitum, o, como se dice, ad nauseum :D

// Saludos

roman 12-03-2009 03:31:39

Tengo que volver a leer acerca de los token, porque es seguro que se usan mucho. Incluso el vBulletin los usa (mira el formulario de inicio de sesión y verás un campo con un valor bastante rarito).

Bueno, creo que es mejor irse a descansar :)

// Saludos


La franja horaria es GMT +2. Ahora son las 08:27:01.

Powered by vBulletin® Version 3.6.8
Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
Traducción al castellano por el equipo de moderadores del Club Delphi