How to create a Captcha in zk ce version?
Creating an own Captcha component while it’s not in the zk community version.
As i work on the ‘forgotten password?’ module in openTruuls™ i would use a Captcha component for the user verification and i’m wondering that such a component is not in the zk community version. So openTruuls™ will be opensourced i need a Captcha component that developers can using without registering for a personal or commercial zk version.
After a few searching in the zk forum and the WWW i became a hint from Maik, the developer behind the jease cms ( www.jease.org ) to using the simpleCaptcha framework.
Argh, the biggest problem was to find a repository where a not corupted version is downloading via the maven2 build system. And let me talk that i’m do it at last by a manual downloading in the linux shell on our web server because i don’t find a runing version.
Okay, after done this, the result is a little Captcha Controller who creates the Captcha which we can call in a static way. In the forgottenPassword Controller we use this Captcha and get the image from it which we assign to a zk image.
pieces of the zul-template
. . . <!-- Captcha / Captcha --> <row> <space width="0" /> <hbox> <image id="img_Captcha" /> <toolbarbutton id="btnReCaptcha" image="/images/icons/sync_16x16.gif" tooltiptext="${c:l('common.ReCaptcha')}" /> </hbox> </row> . . .
The complete dialog should looks like in this picture:
- ForgottenPasswordController
the FDCaptchaUtils.java
/** * EN: Utility class for creating a CAPTCHA.<br> * Captcha can be direct loaded into a org.zkoss.zul.Image<br> * DE: Hilfsklasse zur Erzeugung eines CAPTCHA.<br> * Captcha kann direkt in ein org.zkoss.zul.Image eingelesen werden. * * <pre> * Image img = new org.zkoss.zul.Image(); * img.setContent(CaptchaUtils.getCaptcha().getImage()); * * String verifyStr = captcha.getAnswer(); * </pre> * * @author Stephan Gerth */ public class FDCaptchaUtils { public FDCaptchaUtils() { } /** * Create a 5 digits captcha. * * @return */ public static Captcha getCaptcha() { Captcha captcha = new Captcha.Builder(170, 50).addText(new ColoredEdgesWordRenderer()).addNoise().addBackground(new GradiatedBackgroundProducer()).addBorder().build(); return captcha; } }
In the forgotten password controller we create the Captcha and insert it in the zk Image and handles the verify logic.The needed methods in the controller code looks like this:
pieces of the ForgottenPassword controller
. . . private Captcha captcha; // + getter/setter . . . /** * Do a re-Captcha.<br> * * @param event */ private void doReCaptcha(Event event) { // init: disable the send password button btnReset.setDisabled(true); setCaptcha(FDCaptchaUtils.getCaptcha()); img_Captcha.setContent(getCaptcha().getImage()); } /** * 1. Checks if the email address is entered.<br> * 2. Verify the created captcha digits against the users input from a textbox.<br> * 3. Enable/disable the 'reset password' button.<br> * * @param event */ private void doVerifyCaptcha(Event event) { // init: disable the reset password button btnReset.setDisabled(true); // check if the tenant ID is entered if (StringUtils.isEmpty(longb_TenantID.getValue().toString().trim())) { throw new WrongValueException(longb_TenantID, Labels.getLabel("message.Error.CannotBeEmpty")); } // check if the email address is entered if (StringUtils.isEmpty(txtb_EmailAddress.getValue())) { throw new WrongValueException(txtb_EmailAddress, Labels.getLabel("message.Error.CannotBeEmpty")); } // check if the captcha is verified correctly if (StringUtils.equals(txtb_VerifyCaptcha.getValue(), getCaptcha().getAnswer())) { btnReset.setDisabled(false); } }
Have fun with it.Stephan Gerth
Dipl.rer.pol.
PS: Help to prevent the global warming by writing cool software