|
PmForm /
Basic Email Form with Honeypot & Captcha(by Crisses - "Xes") This is a basic walkthrough that uses PmForm, Captcha and a HoneyPot to set up a relatively simple "email me" form that is hardy against spambots. I've been using these webforms on over 30 websites spanning the last 5 years and the spambots still don't "get it" on the honeypot so I only get "human spam" i.e. a real person spammed me, not a bot, and there's very very few spams that get through these forms (by 2011). PreparationInstall PmForm and the Captcha recipe. config.phpAs stated on the main PmForm page, I recommend having a separate library directory for any recipes that you use. You will put your Site.PmFormTemplates into this directory. To let PmWiki know to look in this directory for missing pages, modify config.php directly after the $WikiLibDirs = array(&$WikiDir,new PageStore('$FarmD/xeslib.d/{$FullName}'),new PageStore('$FarmD/wikilib.d/{$FullName}'));
When a page is not found in your wiki.d directory, PmWiki will look in xeslib.d (or whatever you named it) for the page. When a page is edited in the wiki, it will not overwrite the file in your xeslib.d directory, it will be saved in the wiki.d directory. Next you may put Put your include statements for pmform.php and captcha.php: include_once('cookbook/pmform.php');
include_once('cookbook/captcha.php');
Define your form in config.phpI use the form reference "mailme" for my email forms. This is the word I will use in the PmWiki directive, directly in the wiki web pages later on to say "Put My Form Here". In the example the email will be sent TO criss@example.com, and will seemingly come "from" mywiki@example.com. Keep in mind that some services don't like an email that comes "from" the same email address it is going "to" -- it's more likely to be marked as SPAM. PmWiki doesn't care what email address it comes from so you can fake the From address as long as it's a valid email address. Whatever you choose for your "From" address, add it to your email program's address book (or whitelist if you have one). I need 2 other pieces of information that relate to defining the actual form itself, and defining the format of the email that gets sent to me. I call the form definition #mailmeform and the email format definition #mailmepost. This is what my PmForm definition statement looks like in config.php: $PmForm['mailme'] = 'subject="Email from '.$WikiTitle.'" mailto=criss@example.com form=#mailmeform fmt=#mailmepost from=mywiki@example.com'; If you aren't using $PmForm['mailme'] = 'subject="Email from my website" mailto=criss@example.com form=#mailmeform fmt=#mailmepost from=mywiki@example.com'; Review config.phpThis is what the top of your config.php file might look like: <?php if (!defined('PmWiki')) exit();
$WikiLibDirs = array(&$WikiDir,new PageStore('$FarmD/xeslib.d/{$FullName}'),new PageStore('$FarmD/wikilib.d/{$FullName}'));
$WikiTitle = 'Your New Website'; //wiki title
/******* PmForm ********/
include_once('cookbook/pmform.php');
include_once('cookbook/captcha.php');
//$EnableCaptchaImage=1;
$PmForm['mailme'] = 'subject="Email from '.$WikiTitle.'" mailto=criss@example.com form=#mailmeform fmt=#mailmepost from=mywiki@example.com';
Defining FormsCreate or edit the page called Site.LocalTemplates on your wiki. When you're creating your forms, you may want to refer to Site/PageListTemplates and Site.PmFormTemplates for ideas on forms, code examples, and variations. I use a horizontal rule The first line that is mandatory starts the form definition. We defined this in "form=" in our The next line sets the value of "successpage" for the form. If the form is submitted, this is where the website visitor will go next. Whatever the value is, you will want to put a "Thank You" page here. So I use the directive If you make a mistake when submitting a form, you don't want to re-enter all your information again. We need a line to tell the form to "remember" the information in case the web visitor has made a mistake. This line tells it to remember the data submitted and pre-fill out the form when there's an error: Just before creating your form itself, you want the visitor to know when they make a mistake. We have a directive that will print PmForm error messages. I like to "cheat" and make the messages red, because time & time again people don't see these messages unless they stand out. Let's take care of it here, although it might be more elegant to take care of this in css elsewhere: >>red<< (:messages:) >><< HoneypotLet the games begin! Here we play a very simple game to "fool" spambots into filling in an extra line on the form that most users cannot even see. The "comment" wikistyle uses css to hide the line. The line is given the ultra-V1ag4a-tempting title "Subject" (your language may vary: the %comment% $[Subject]: (:input text Subject size=30:) Later we will tell the PmForm NOT to send an email if the "Subject" is filled in. It will send a message to the browser asking the "person" to leave "Subject" blank. This message is for accessibility purposes -- if the person is a real human using an alternative browser that cannot handle css, they will get a message and be able to remove text from the Subject line and re-submit. Spam-bots do not wait for error messages, and can't understand them. Email FormI use a "simple table" to make my form pleasing to the eye, but otherwise this is pretty standard. Again for "Comments" we see the language translation feature. It's a hold-over from me copying the form from PM, but you might want to make the entire form language-sensitive. ||width='' || Name:||(:input text name size=30:) || || Phone:||(:input text phone size=30:) || || Email:||(:input text email size=30:) || $[Comments]:\\ (:input textarea comments rows=8 cols=60:) Ok, that's the form body. Next we have to put the captcha information in before we end the form: Enter code: {$Captcha} (:input captcha:)
The code Then we end the form: (:input submit name=post value='$[Send]':) (:input end:) And last we have to end the PmForm form template definition: [[#mailmeformend]]
Congratulations, you now have a basic form template. :) But we now need the end that processes the data sent in the form. Review form definitionHere's what I have: ----
[[#mailmeform]]
(:template defaults successpage='Email/ThankYou' :)
(:input pmform target={$$target} successpage={$$successpage} :)
(:input default request=1:)
>>red<<
(:messages:)
>><<
%comment% $[Subject]: (:input text Subject size=30:)
||width=''
|| Name:||(:input text name size=30:) ||
|| Phone:||(:input text phone size=30:) ||
|| Email:||(:input text email size=30:) ||
$[Comments]:\\
(:input textarea comments rows=8 cols=60:)\\
Enter code: {$Captcha} (:input captcha:)
(:input submit name=post value='$[Send]':)
(:input end:)
[[#mailmeformend]]
Email Format DefinitionNow we need to define the format for the email we receive, as well as process information from the form. First tell PmWiki that the definition is starting. This is defined in the Next we want lines telling PmForm which data is required. Each line will have an associated error statement that will print in the (:template require name errmsg="$[Please enter your name]" :) (:template require Subject match="" errmsg="$[Please leave the subject field blank]" :) (:template require comments errmsg="$[Comments required]" :) We also require that the captcha is completed properly: (:template requires if="captcha" errmsg="Please re-enter the message code" :) Now if all those tests are passed, a text message will be generated and sent to the TO email we defined in config.php. In the form we define input variables. In the form we print them out by enclosing them in Name: {$$name}
Phone: {$$phone}
Email: {$$email}
{$$comments}
I like to have a footer that tells me which page they found the form on. This is basically for marketing purposes, because I can put my email form anywhere I want on my website . Were they on my contact page? Were they on a page for a specific service or event? Knowing where they were can put their questions or comments into context for me. ==========
Sent via {$$PageUrl}
And then we end the definition with Review post-form processing & email formatSo here's the 2nd template that I've defined in LocalTemplates: ----
[[#mailmepost]]
(:template require name errmsg="$[Please enter your name]" :)
(:template require Subject match="" errmsg="$[Please leave the subject field blank]" :)
(:template require comments errmsg="$[Comments required]" :)
(:template requires if="captcha" errmsg="Please re-enter the message code" :)
Name: {$$name}
Phone: {$$phone}
Email: {$$email}
{$$comments}
==========
Sent via {$$PageUrl}
[[#mailmepostend]]
Place the form on a page for testingNow to actually USE your new form. You can put it on Main/ContactUs, or you can put it in Test/TestEmailForm -- it doesn't matter. What you need is a PmForm directive and the reference you gave the form in your config.php file. In this case, I used mailme in the config.php file. (:pmform mailme:)
I can place this directive anywhere in my wiki and it will pull in the form to email me. So instead of a link to "Email Criss" that sends them to my Contact Us page, I can just drop the whole form in with a little preamble: For more information and amazing feats by Criss please email me below. (:pmform mailme:) Happy emailing! :) Troubleshooting:If you test out your form and have any problems, you can email me at http://eclectictech.net/wiki/Info/Contact and I'll add to this page. No captcha imageOnce you test the form (later), you might require a line ![]() Best PracticesSecurityIf you're going to use PmForm you probably want to turn $HandleAuth['source'] ='edit';
And now people can't see the wiki code unless they're already able to edit a page anyway. |