Captcha en PERL


Perl es un lenguaje de programación altamente optimizado para el procesado de texto. Toma caracteristicas de lenguajes como C, AWK y bourne shell(sh) ente otros. Mi experiencia en el mismo no ha sido muy amplia ya que la mayoría de las aplicaciones web no lo utilizan, es más usado hoy en día en pequeños scripts, tareas de mantenimiento a servidores entre otros aunque reconozco que su rapidez es a la hora de tratar con archivos de texto o bases de datos en ficheros y no en los gestores convencionales.

El Captcha es una prueba desafío-respuesta utilizada para determinar cuando el usuario es humano o no, controlada totalmente por la máquina. Normalmente lo vez en todo tipo de formularios en la internet, formularios de contacto, de registro o autenticación. Su amplia proliferación es debido al crecimiento de los correos basura, robots (spambots) entre otros.

Aunque existen varias implementaciones normalmente el Captcha consiste en que el usuario introduzca correctamente un conjunto de caracteres que se muestran en una imagen distorsionada que aparece en pantalla. Se supone que una máquina no es capaz de comprender e introducir la secuencia de forma correcta por lo que solamente el humano podría hacerlo.

En todos los lenguajes existe alguna implementación para esta funcionalidad. Hoy hablaremos de como implementarlo en Perl. Hace poco tuve que desarrollar un pequeño sitio de gestión de usuarios de un servicio X en el que las credenciales y los datos de los usuarios se guardaban en ficheros dentro del servidor. Ya existía un sistema en Perl y el requisito principal era desarrollarlo en el mismo lenguaje que ya estaba, Perl.

Para una mejor seguridad el sistema necesita autenticación inicial y es donde entra el Captcha. Para su implementación utilizaremos la extensión Authen::Captcha descargable desde http://search.cpan.org/search?dist=Authen-Captcha . Como se usa? pues es sencillo.

Instalación

    tar -zxvf Authen-Captcha-1.xxx.tar.gz
    perl Makefile.PL
    make
    make test
    make install

Implementación

Una vez instalado empezamos a programar. En el cgi que genera los HTML necesarios para mostrar el formulario de autenticación.

    use Authen::Captcha;
    # creamos el objeto captcha y establecemos las propiedades iniciales
    my $captcha = Authen::Captcha->new(
    data_folder => 'captcha/data/', # directorio donde se guarda la base de datos de los captcha que los relaciona con las imagenes creadas a partir de estos
    output_folder => 'captcha/output/', # directorio donde se guardan las imágenes generadas a partir de la base de datos
    );
    # creamos el captcha de nombre "$md5sum.png"
    my $md5sum = $captcha->generate_code(6); # genera un captcha de 6 caracteres, este valor es modificable

    print "<center>n";
    print "
        <form action='auth.cgi' method='POST'>
        <fieldset>
        <legend>Formulario de autenticación</legend>
        <label>Usuario</label>
        <input type='text' placeholder='Teclee su usuario...' required=true id='inputUser' name='inputUser'>
        <label>Contrase&ntilde;a</label>
        <input type='password' placeholder='Teclee su contrase&ntilde;a...' required=true id='inputPassword' name='inputPassword' autocomplete='off'>
        <span class='help-block'>Teclee sus credenciales de administrador.</span>";
        print "
        <img src='captcha/output/".$md5sum.".png'></img>
        <label>Teclee c&oacute;digo de verificaci&oacute;n</label>
        <input type='text' placeholder='Captcha...' required=true id='inputCaptcha' name='inputCaptcha'>
        <input type='hidden' value='".$md5sum."' id='md5sum' name='md5sum'>
        <p><button type='submit' class='btn'>Aceptar</button></p>
        </fieldset>
        </form>n";    
    print "</center>n";

Fíjense que se crea una imagen a partir de un fichero con el codigo binario, y dicha imagen es mostrada en <img src='captcha/output/".$md5sum.".png'></img> para el usuario. Una vez llenados los datos necesarios y el Captcha el fichero auth.cgi es el encargado de procesar, chequear las credenciales y validar que el Captcha sea correcto. En este ejemplo solo validaremos el Captcha pues es el tema principal de articulo.

    $inputCaptcha = $in{"inputCaptcha"};  # Obtengo el captcha insertado por el usuario en el formulario de autenticacion
    $md5sum = $in{"md5sum"};              # md5sum de la imagen mostrada
    
    sub captchaRev()
    {
    use Authen::Captcha;

    # creamos el objeto captcha y establecemos las propiedades iniciales
    my $captcha = Authen::Captcha->new(
        data_folder => 'captcha/data/',
        output_folder => 'captcha/output/',
    );

    return $captcha->check_code($inputCaptcha, $md5sum); 
    #      1 : Captcha satisfactorio
    #          0 : Error en los ficheros captcha, código no chequeado
    #         -1 : Código captcha expirado
    #         -2 : Código invalido, no existe en la base de datos
    #         -3 : Código invalido, no coincide con el $md5sum
    }

Excepto el retorno 1 todos los demás causan la re autenticación del usuario por invalidez del código.

Conclusión

Existen muchas implementaciones de Captchas en los diferentes lenguajes, todos con el mismo propósito y algunas mucho mejores que otras. Los Captchas sirven en gran medida para combatir el SPAM. Puesto que, aunque existen robots que intentan rellenar formularios de manera sistemática para insertar, en foros y páginas webs, enlaces de lo que desean promocionar, los Captcha anulan en gran medida su efectividad. No son la solución definitiva pues no son infalibles ¿que lo es en este mundo de hoy?, pero si proporcionan un nivel más de seguridad en nuestros sistemas, como siempre la opción existe, la selección queda en sus manos.

Latest posts by Leroy Ley (see all)