Blogless: Blog of Design Less Better.

Making the reCAPTCHA Wordpress Plugin Validate

If you are like us, you want to harness the awesome power of reCAPTCHA for your Wordpress blog and you also want valid XHTML. Before now, this was impossible. DLB is pleased to offer you a fix, and continue doing our bit to make the web a more standardized place.

Background

reCAPTCHA is a free CAPTCHA service that helps to digitize books.

A CAPTCHA is a program that can tell whether its user is a human or a computer, by asking the user to copy some distorted text. You’ve probably seen them, either here, or elsewhere on the web. If not, just click here for an example.

Reading Spidey
The Internet Archive is going to help Spidey enter "the digital age".

reCAPTCHA gets these words from books that the Internet Archive is digitizing. Digitizing books is done by photographically scanning the book’s pages, and then transforming these scans into text using “Optical Character Recognition” (OCR).

All this together means that when you leave a comment, in addition to contributing to the discussion, you are both proving you are a person, not a spambot, and helping humanity’s effort to archive it’s knowledge digitally.

The Problem

Which is all milk and honey, but there’s a problem. As good citizens of the web, and as Wordpress users, BlogLESS utilizes reCAPTCHA’s handy Wordpress Plugin. But, as good citizens, BlogLESS is further committed to web standards. This means that all our HTML and CSS needs to be valid. Unfortunately, the Wordpress reCAPTCHA plugin doesn’t validate XHTML out of the box. (As it turns out, this is not its fault. It actually can’t validate out of the box, which we’ll see.)

The good news is, the fix is easy, once you understand the problem. You don’t need to be a pro to make your Wordpress comments template valid again.

The Fix

First, you’ll need to find the php files that write the reCAPTCHA to your comments template. They are two, although the file names changed between versions. I’ve checked against the lastest (v2.91), and the oldest version I could find (v2.5). If your version is somewhere in the middle of the two, you’ll have to extrapolate a little, but it shouldn’t be hard.

Anyhow, both versions have a file called recaptchalib.php. Version 2.5 has a second file called recaptcha.php, which changed to wp-recaptcha.php by 2.91. In any case, they should both be found in a directory that looks something like this:

[blog root]/wp-content/plugins/recaptcha-wordpress-[version]

Error the first

By 2.6, reCAPTCHA fixed this first error, so if you’re up-to-date, you can skip this step and move on to Error the second below. However, if you’re using 2.5, the fix is very easy. Open recaptchalib.php, and locate lines 126 to 130. These lines contain a complete <noscript> block. Find it and replace it with the following:

	<noscript>
  		<iframe src="'. $server . '/noscript?k=' . $pubkey . $errorpart . '" height="300" width="500" frameborder="0"></iframe><br />
  		<textarea name="recaptcha_challenge_field" rows="3" cols="40"></textarea>
  		<input type="hidden" name="recaptcha_response_field" value="manual_challenge" />
	</noscript>';

Error the second

That one was just sloppy, and again, was fixed early in the plugin’s development. Unfortunately, the second validation failure is quite a bit more insidious. It takes place in the main plugin file ([wp-]recaptcha.php). In 2.5, find line 57. In 2.91 it’s line 431. In any case it looks like this:

	<style type='text/css'>#submit {display:none;}</style>

The w3c tells us that this error is because "The element named above was found in a context where it is not allowed. This could mean that you have incorrectly nested elements — such as a ’style’ element in the ‘body’ section instead of inside ‘head’…" Jackpot.

As it turns out, this puts us in a bit of a jam. Why? First, we’re in a noscript block, so we can’t apply this definition with Javascript (the most obvious choice). Second, the purpose of this definition is to hide a submit button that occurs in our Wordpress comments template and replace it with the one that we create on the following line (59,432) of our plugin file. This means we can’t use an plugin-scope PHP conditional.

So, the somewhat counter-intuitive way to handle this — but the only valid way you’re going to get — is to make two alterations. First, comment out the line that’s causing the trouble:

	<!--<style type='text/css'>#submit {display:none;}</style>-->

Now, open your comments template, usually:

[blog root]/wp-content/themes/[theme name]/comments.php

and find the submit button (any input with id="submit"). Now what we’re going to do is actually only write the submit button for browsers that support javascript. Instead of your defacto submit button, use something like this:

	<script type="text/javascript">
		//<![CDATA[
		/* Cf. http://www.designlessbetter.com/blogless/posts/making-recaptcha-validate */
		document.write('<input name="submit" type="submit" id="submit" tabindex="5" value="Post this Comment" />');
		//]]>
	</script>

Awesome!

These icons link to social bookmarking sites where readers can share and discover new web pages.
PaulJul 21, 2008
 

Comments on this post

1.

Paul,

Thanks for your comment on my blog post about this same issue.

I’m interested in knowing more about how your Javascript addition to comments.php solves the problem. It seems to me that since most browsers have Javascript enabled, this solution outputs multiple ’submit’ buttons in most cases.

I’m glad others are trying to tackle this issue also.

Tom Distler at 9:17am on Tue, Jul 22nd.

2.

Tom,

You’ll notice that I’m not suggesting that you add a submit button to your comments.php. I’m suggesting that you replace the normal one with one that is output by Javascript. If you think about it, this means that the submit button will now display only for those users with Javascript enabled.

The net effect of this is that users with Javascript enabled get one submit button, and users without get zero. This is identical to the effect created by writing a submit button for all browsers and then setting the ‘display’ style to ‘none’ for browsers with Javascript disabled.

You can see for yourself by disabling Javascript in your browser.

Hope this clears things up,
Paul

Paul at 9:59am on Tue, Jul 22nd.

3.

Post updated. I still have some tweaking to do to prevent a rogue input field from showing up w/ scripts disabled, but that’s a lower priority. Thanks again!

Tom Distler at 1:08pm on Tue, Jul 22nd.

4.

Awesome, thanks for the information man, I really appreciate it. I will link to this page from the plugin description page. Hopefully the reCAPTCHA developers eventually fix this problem. Thanks for the solution in the meantime though.

Blaenk at 4:07pm on Tue, Jul 22nd.

5.

@Blaenk - Glad to be of service, and thanks for your hard work maintaining this useful plugin. Thanks for the link also.

@Tom - Thanks for the link and good luck with your rogue field.

Paul at 6:51am on Wed, Jul 23rd.

6.

[…] have to admit, I’m a little jealous of Paul’s wonderful programming posts. Not only does he get to show off his great solutions to common web design problems, but he […]

7.

[…] - bookmarked by 5 members originally found by jangelle13 on 2008-08-20 Making the reCAPTCHA Wordpress Plugin Validate http://www.designlessbetter.com/blogless/posts/making-recaptcha-validate - bookmarked by 6 members […]

Bookmarks about Plugin at 2:46pm on Wed, Sep 10th.

Post a comment

Name
Email
Url
Comment
  Please feel free to use these tags: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <code> <em> <i> <strike> <strong>
Validate
Close this
E-mail It