Un genere di attacco particolarmente fastidioso, che fa parte della famiglia degli spam, è l’utilizzo automatizzato di form di registrazione o di contatto o commenti o altro. In questo caso, l’exploit avviene con l’utilizzo di appositi software che compilano in automatico i form. Come risultato vi potreste trovare 10000 pending user nella vostra applicazione, oppure 5000 richieste di contatto.
Per evitare questo genere di attacchi, il sistema più diffuso è quello dei CAPTCHA, ovvero delle immagini (quindi non leggibili direttamente) nelle quali figura una sequenza alfanumerica casuale. Viene quindi richiesto di inserire tale sequenza nel form a prova dell’intervento umano nel processo in corso.
Il web è pieno di tutorial su come implementare questa soluzione che per altro è abbastanza semplice, ma che contiene almeno due criticità.
- Con l’avvento di questi metodi, anche i software per gli attacchi sono diventati più raffinati ed a volte riescono a leggere, con sistemi simili ai software OCR degli scanner, le immagini captcha. Di riflesso, queste immagini diventano sempre più complesse: con meno contrasto, caratteri molto ruotati o deformati, sfondi con linee e puntini, eccetera. Tutto ciò crea dei problemi di accessibilità a volte anche al sottoscritto, la cui vista è perfetta.
- Un problema più specifico è inoltre la necessità di disporre della libreria GD, cosa purtroppo non scontata se siamo in hosting.
Quello che vi presento in questo articolo è un metodo meno raffinato ma che ha il pregio della semplicità, il metodo Q&A (question and answer).
Si tratta di chiedere all’utente di rispondere ad una semplicissima domanda e di verificare se la risposta è corretta.
Iniziamo a stilare una lista di domande e di risposte separate dal simbolo “:” e salviamole in file.txt
Come si chiama l'animale che abbaia?:cane Di che colore è l'erba?:verde Come si chiama l'animale che miagola?:gatto Come si dice sì in ingelse?:yes Cosa c'è all'opposto del sud?:nord
Naturalmente scrivetene il più possibile.
Ora prepariamo il file form.php. Prima di stampare a video il form, prepariamo la domanda.
<?php session_start(); $list = file("file.txt"); $index = rand(0,count($list) - 1); $row = $list[$index]; $question = explode(":", $row); $_SESSION['answer'] = $question[1]; ?>
Come vedete avvio una sessione. In seguito creo un array con le righe del file contenente le domande e le risposte.
Scelgo quindi una chiave casuale e registro in $row la riga corrispondente a quella chiave. Explodo sul “:” e inserisco la risposta in $_SESSION['answer'].
A questo punto posso stampare il form:
<form action="result.php" method="POST"> Nome:<br> <input type="text" name="nome" /><br><br> Cognome:<br> <input type="text" name="cognome" /><br><br> <?php echo $question[0]; ?><br> <input type="text" name="answer" /><br><br> <input type="submit" value="invia" /> </form>
Come vedete faccio passare la risposta nel campo answer.
Vi posto form.php completo
<?php session_start(); $list = file("file.txt"); $index = rand(0,count($list) - 1); $row = $list[$index]; $question = explode(":", $row); $_SESSION['answer'] = $question[1]; ?> <form action="result.php" method="POST"> Nome:<br> <input type="text" name="nome" /><br><br> Cognome:<br> <input type="text" name="cognome" /><br><br> <?php echo $question[0]; ?><br> <input type="text" name="answer" /><br><br> <input type="submit" value="invia" /> </form>
Ora vediamo il file result.php
<?php session_start(); if(trim(strtolower($_POST['answer'])) == trim($_SESSION['answer'])) { echo 'Ciao ' . $_POST['nome'] . ' ' . $_POST['cognome']; } else { echo 'errore nel controllo'; } ?>
Alla risposta applico trim per eliminare eventuali spazi e strtolower portando così la stringa tutta in minuscolo (nel caso in cui l’utente abbia utilizzato caratteri maiuscoli). Se corrisponde alla risposta che abbiamo precedentemente registrato in sessione, il controllo è superato.





#1 di gabriel81mi il 19 marzo 2010 - 03:01
Io la penso come te riguardo il captcha. Mi da fastidio inserire il codice nel portale, sopra tutto quando sono illeggibili, mentre il sistema che proponi può andar bene quando non hai a che fare con portali di un certo spessore.
Sarebbe poco elegante far domande banali ad utenti che magari non capiscono nemmeno la motivivazione, ma anche proporre un sistema del genere al cliente non lo trovo ottimo.
E comunque io come tutti mi sono ritrovato a dover combattere contro lo spam.
Il mio sistema è questo:
inserisco nel form un input che lo rendo invisibile con lo stile
Come noti il value è vuoto, ma potrei riempirlo con un valore, anche a casaccio tipo “xyz”.
Adesso la parte php:
<?php if(!$_REQUEST['controllo']){ // codice valido, l'input nascosto è rimasto vuoto e quindi procedo //con l'inserimento dei dati nel db o dell'invio della mail }else{ // spam! l'input è stato riempito }Cosa succede:
Solitamente questi software che compilano i form a differenza dell’occhio umano notano un input in più, che è quello visibile e lo riempono.
Il controllo in php invece non vuole che quel campo venga riempito, perché sa può farlo solo un sistema automatizzato e non un essere umano, quindi blocca l’esecuzione dello script e dello spam.
Notare che comunque anche se è un antispam non intrusivo non da mai la garanzia al 100% però io non ho mai avuto problemi di spam da quando utilizzo questo sistema.
#2 di gabriel81mi il 19 marzo 2010 - 03:04
Questa è forte, mi ha reso invisibile l’input
scrivo qui nuovamente l’input senza il tag di interpretazione codice
#3 di gabriel81mi il 19 marzo 2010 - 03:05
a quanto pare non lo prende.. divido il codice:
all’interno dopo controllo inserire lo style:
style=” visibility:hidden”
#4 di gabriel81mi il 19 marzo 2010 - 03:07
litigo con i sistemi di sicurezza di word press..
ci provo ancora senza tag
input type=”text” name=”controllo” value=”" style=”visibility:hidden”
#5 di Maurizio il 19 marzo 2010 - 10:47
Ciao Gabriele
nonti funziona se fai così:
Perchè non ho capito molto. al limite, se non funziona così, mandamelo per email che lo pubblico io
#6 di Antonio il 15 maggio 2010 - 09:13
Ciao Maurizio
Innanzi tutto complimenti per gli articoli, me li sto leggendo un pò tutti e mi sto facendo una cultura più vasta sul PHP… ancora non ero riuscito a trovare nulla di simile e di perfetto
Riguardo a questo articolo, conosci reCAPTCHA? Il codice si capisce molto di più, ma nonostante questo sembra sia abbastanza efficiente e molto più potente di quei codici tutti strani e completamente illeggibili.
Però non lo conosco molto, lo uso su un forum phpbb frequentato da molti utenti e nei fatti ho notato che mettendo un modulo CAPTCHA illegibile, qualche attacco di spam è capitato, mentre inserendo reCAPTCHA non ho più visto spam da mesi.
Magari tu lo conosci e mi sai dire meglio
#7 di Maurizio il 15 maggio 2010 - 12:03
Ciao Antonio, benvenuto e grazie.
Non ho mai utilizzato reCAPTCHA quindi non saprei dire.
In questo articolo, volevo solo mostrare un metodo altrenativo. Non ho nulla in contrario a captcha (lo dico perché si potrebbe avere l’impressione), solo comincia a mostrare dei limiti.
#8 di Arquen il 12 giugno 2010 - 11:03
Ciao Maurizio!
Mi stavo leggendo gli articoli nuovi e sono arrivato qui!
Io ho fatto una cosa simile a quella di gabriele. Uso un campo reso invisibile tramite Css. Questo campo deve restare obbligatoriamente vuoto altrimenti genera un errore di invio. Gli utenti non lo compilano essendo nascosto, invece i bot automatici sì, bloccondoli.
In più per lo spam umano, uso una funzione che censura un elenco di parole e url. Chi le utilizza nel campo testo o sito web genera un errore di invio.
Manca solo di creare la moderazione dei commenti o l’approvazione dell’email.
#9 di Maurizio il 12 giugno 2010 - 13:01
Ciao Arquen.
n effetti il metodo proposto da gabriele e che anche tu utilizzi sembra funzionare. Non so fino a quando visto che mi sembra facilmente aggirabile, ma fino a quando funziona va benissimo.
#10 di Arquen il 13 giugno 2010 - 09:48
Se sai che uso questi due metodi, allora si possono aggirare, ma teoricamente non dovresti saperlo.
E’ da quasi un anno che li uso e, a differenza di prima, mi arrivano solo uno o due messaggi a settimana di esseri umani stardi che si fanno pubblicità inserendo il loro link, che poi provvedo ad inserire tra gli url da bloccare. Infatti ora è solo un problema di url (ne esce sempre qualcuno nuovo). Le parole spammose le ho bloccate tutte.
Ma poi sono due dei metodi utilizzati anche da Wordpress o no? Sto anche tentando di utilizzare akismet sulla mia creazione casareccia. Ma è ancora fuori dalla mia portata.
Comunque prima usavo un sistema simile a quello che hai spiegato, solo che facevo fare un’addizione. Funzionava bene, però poi ho voluto provare altro.