How to Protect HTML Form from Spammers

How to protect html form from spammers?

Update: The answer was accepted because I recommended KeyCAPTCHA. From my hard-earned painful expereince, KeyCAPTCHA is a scam by professional spammers. I removed my recommendations of KeyCAPTCHA


Note that most professional spambots are integrated with sweatshops (1 USD a 1000 solutions) human captcha solvers API. When a spambot cannot pass captcha itself it (spam bot), keeping hundreds of open connections, sends screenshot (or webpage code) with CAPTCHA for solving by sweatshop human. This is legal and big business. In order to be legal and integrate with bots through APIs the human solvers can not directly interact with cracked web boards (blog comments, registration pages, chats, wiki, forums, etc.).

Another problem is that anti-spam programs cannot detect context-based spamming by professionally made bot. There are many approaches. The simplest one is web scraping multi-author human dialogs from other web boards and posting them CONTEXT-SENSITIVELY (bots can detect topics) from different IP addresses of different countries at different times, so even (a weblog) owner (human) cannot detect that dialogs are posted by bots(they are really from stored in database human dialogs).

This is only the matter of interest to your website from professional spammers or time+qualified persistence of amateurs to automatically circumvent most (if not all) CAPTCHAs.

Prevent php web contact form spam

A simple trick is to create a honeypot field:

html

<!-- within your existing form add this field -->
<input type="text" id="website" name="website"/>

css

/*in your css hide the field so real users cant fill it in*/
form #website{ display:none; }

php

//in your php ignore any submissions that inlcude this field
if(!empty($_POST['website'])) die();

How to prevent spam on a form

You could do something like this,

function validEmail($email){
if (filter_var($email, FILTER_VALIDATE_EMAIL)){
list($user,$domain) = explode('@',$email);
return checkdnsrr($domain, 'MX');
}
return false;
}

it may not pick up every fake email, but I always validate their email by sending them a validation email with a link.

EDIT:

As for spam on a form use CSRF, that should prevent most spam (at least in my experience)

How to protect a contact form without captcha?

So the options:

  1. Maximize query/IP
  2. Add security question
  3. Captcha (even if you don't like it)
  4. Sending e-mail to validate it
  5. Submitting data via JavaScript

Details on these and my opinion on them.

  1. It works well to prevent sending many messages, but a few copies of them will still get in. If you think that's affordable, this might work. Note: a spammer can use proxies or dinamic IP, but that might be slow. Perhaps consider not blocking the user but adding a captcha if they send too many e-mails.
  2. What is this exactly? These are questions like "10+1" or "ten plus 1" or "What day is it?". They might work well - if your website will be in only very few languages. Captchas are still better but this works well in case.
  3. You don't like it, but I still say it's the best. Adding one reCAPTCHA isn't that hard but it will prevent 90% of the spammers - or more. But there are 2 problems with this: 1. sometimes human can't read it as well, 2. spammers could use people to solve it for a minimal (like $0.001/captcha) amount and sometimes they do. But that stands for case 2 as well.
  4. Could be good, but if spammers note this, they can generate random email addresses and validate it via SMTP. But they usually go to the easiest target and leave.
  5. Good, spammers can't make bots act like a click, but they can make codes which makes click non-required. But the easiest target rule stays.

In my opinion, the best is solution 3, then solution 2, then solution 1, then solution 4 and 5.

Better Honeypot Implementation (Form Anti-Spam)

Concept

By adding a invisible field to your forms that only spambots can see, you can trick them into revealing that they are spambots and not actual end-users.

HTML

<input type="checkbox" name="contact_me_by_fax_only" value="1" style="display:none !important" tabindex="-1" autocomplete="off">

Here we have a simple checkbox that:

  • Is hidden with CSS.
  • Has an obscure but obviously fake name.
  • Has a default value equivalent 0.
  • Can't be filled by auto-complete
  • Can't be navigated to via the Tab key. (See tabindex)

Server-Side

On the server side we want to check to see if the value exists and has a value other than 0, and if so handle it appropriately. This includes logging the attempt and all the submitted fields.

In PHP it might look something like this:

$honeypot = FALSE;
if (!empty($_REQUEST['contact_me_by_fax_only']) && (bool) $_REQUEST['contact_me_by_fax_only'] == TRUE) {
$honeypot = TRUE;
log_spambot($_REQUEST);
# treat as spambot
} else {
# process as normal
}

Fallback

This is where the log comes in. In the event that somehow one of your users ends up being marked as spam, your log will help you recover any lost information. It will also allow you to study any bots running on you site, should they be modified in the future to circumvent your honeypot.

Reporting

Many services allow you to report known spambot IPs via an API or by uploading a list. (Such as CloudFlare) Please help make the internet a safer place by reporting all the spambots and spam IPs you find.

Advanced

If you really need to crack down on a more advanced spambot, there are some additional things you can do:

  • Hide honeypot field purely with JS instead of plain CSS
  • Use realistic form input names that you don't actually use. (such as "phone" or "website")
  • Include form validation in honeypot algorithm. (most end-user will only get 1 or 2 fields wrong; spambots will typically get most of the fields wrong)
  • Use a service like CloudFlare that automatically blocks known spam IPs
  • Have form timeouts, and prevent instant posting. (forms submitted in under 3 seconds of the page loading are typically spam)
  • Prevent any IP from posting more than once a second.
  • For more ideas look here: How to create a "Nuclear" honeypot to catch form spammers

PHP Form Spam Prevention

Check this out as an alternative to a captcha. Then you could use your existing class to validate the field. Say your hidden field has a name "fakeField" You could validate it with your validateSTR method via..

$v->validateStr($fakeField, "fakeField",0,0);

Since your str check is checking > and < instead of >= and <= this will return true when the length is exactly 0. This might be an easier solution for someone with little code knowledge to integrate.

Alternatively, if you're stuck on using a captcha of sort, and you know what you expect the value to be, you could add a method to check against the value you're expecting.

The method:

public function validateCaptcha( $value,$name, $expectedValue) {
if(trim($value) != $expectedValue) {
$this->setError($name, "Captcha Incorrect");
}
}

then change the line of code

$v->validateStr($spamcheck, "spamcheck");

to

$v->validateCaptcha($spamcheck, "spamcheck", '6');

This isn't the best solution since there are so many powerful captchas out therebut it's easy to use.

Can I prevent spam bots from submitting a form if its hidden?

A spam bot is usually a script that is executed and run automatically. It's not an actual human being so the bot would not care if it is actually hidden by the style or not. You could add it to the DOM in the moment the user clicks a button if you wanted to prevent a "spam bot" to abuse it.



Related Topics



Leave a reply



Submit