Hi,

I've written a simple interface for using recaptcha, based on the
existing textcha code and interfaces. I'm using the python-recaptcha
code from Google, and it seems to work fine for me. I've only plumbed
into newaccount.py so far, just to stop spammers creating new accounts
easily. Patch attached, against 1.9.3.

In future, it might be a good plan to add a generic security/captcha
interface. But I'm not doing that today! :-)

If there's a better place to send this patch, please let me know...

-- 
Steve McIntyre, Cambridge, UK.                                st...@einval.com
"Further comment on how I feel about IBM will appear once I've worked out
 whether they're being malicious or incompetent. Capital letters are forecast."
 Matthew Garrett, http://www.livejournal.com/users/mjg59/30675.html
diff -uNrBb --exclude support --exclude _tests --exclude i18n ./action/newaccount.py /usr/share/pyshared/MoinMoin/action/newaccount.py
--- ./action/newaccount.py	2010-06-26 22:46:40.000000000 +0100
+++ /usr/share/pyshared/MoinMoin/action/newaccount.py	2011-08-11 14:15:25.698398024 +0100
@@ -10,6 +10,7 @@
 from MoinMoin.Page import Page
 from MoinMoin.widget import html
 from MoinMoin.security.textcha import TextCha
+from MoinMoin.security.sec_recaptcha import ReCaptcha
 from MoinMoin.auth import MoinAuth
 
 
@@ -26,6 +27,9 @@
     if not TextCha(request).check_answer_from_form():
         return _('TextCha: Wrong answer! Go back and try again...')
 
+    if not ReCaptcha(request).check_answer_from_form():
+        return _('ReCaptcha: Wrong answer! Go back and try again...')
+
     # Create user profile
     theuser = user.User(request, auth_method="new-user")
 
@@ -143,6 +147,17 @@
             td.append(textcha.render())
         row.append(td)
 
+    recaptcha = ReCaptcha(request)
+    if recaptcha.is_enabled():
+        row = html.TR()
+        tbl.append(row)
+        row.append(html.TD().append(html.STRONG().append(
+                                      html.Text(_('ReCaptcha (required)')))))
+        td = html.TD()
+        if recaptcha:
+            td.append(recaptcha.render())
+        row.append(td)        
+
     row = html.TR()
     tbl.append(row)
     row.append(html.TD())
diff -uNrBb --exclude support --exclude _tests --exclude i18n ./security/sec_recaptcha.py /usr/share/pyshared/MoinMoin/security/sec_recaptcha.py
--- ./security/sec_recaptcha.py	1970-01-01 01:00:00.000000000 +0100
+++ /usr/share/pyshared/MoinMoin/security/sec_recaptcha.py	2011-08-11 14:41:42.806456419 +0100
@@ -0,0 +1,69 @@
+# -*- coding: iso-8859-1 -*-
+"""
+    MoinMoin - recaptcha support
+
+    Based heavily on the textcha support in textcha.py
+
+    @copyright: 2011 by Steve McIntyre
+    @license: GNU GPL, see COPYING for details.
+"""
+
+from MoinMoin import log
+from recaptcha.client import captcha
+import sys
+
+logging = log.getLogger(__name__)
+
+from MoinMoin import wikiutil
+
+class ReCaptcha(object):
+    """ Recaptcha support """
+
+    def __init__(self, request):
+        """ Initialize the Recaptcha setup.
+
+            @param request: the request object
+        """
+        self.request = request
+        self.user_info = request.user.valid and request.user.name or request.remote_addr
+        cfg = request.cfg
+
+        if cfg.recaptcha_public_key:
+            self.public_key = cfg.recaptcha_public_key
+        if cfg.recaptcha_private_key:
+            self.private_key = cfg.recaptcha_private_key
+
+    def is_enabled(self):
+        """ check if we're configured, i.e. we have a key
+        """
+        if (self.public_key and self.private_key):
+            return True
+        return False
+
+    def check_answer_from_form(self, form=None):
+        if self.is_enabled():
+            if form is None:
+                form = self.request.form
+            challenge = form.get('recaptcha_challenge_field')
+            response = form.get('recaptcha_response_field')
+            captcha_result = captcha.submit(challenge, response, self.private_key, self.request.remote_addr)
+            if captcha_result.is_valid:
+                logging.info(u"ReCaptcha: OK.")
+                return True
+            else:
+                logging.info(u"ReCaptcha: failed, error code %s." % captcha_result.error_code)
+                return False
+        else:
+            return True
+
+    def render(self, form=None):
+        """ Checks if ReCaptchas are enabled and returns HTML for one,
+            or an empty string if they are not enabled.
+
+            @return: unicode result html
+        """
+        if self.is_enabled():
+            result = captcha.displayhtml(self.public_key, use_ssl = True)
+        else:
+            result = u''
+        return result
------------------------------------------------------------------------------
Get a FREE DOWNLOAD! and learn more about uberSVN rich system, 
user administration capabilities and model configuration. Take 
the hassle out of deploying and managing Subversion and the 
tools developers use with it. 
http://p.sf.net/sfu/wandisco-dev2dev
_______________________________________________
Moin-user mailing list
Moin-user@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/moin-user

Reply via email to