图片验证:jcaptcha
ImageEngine:
package com.sky;
import java.awt.Font;
import com.octo.captcha.component.image.backgroundgenerator.BackgroundGenerator;
import com.octo.captcha.component.image.backgroundgenerator.FunkyBackgroundGenerator;
import com.octo.captcha.component.image.color.RandomRangeColorGenerator;
import com.octo.captcha.component.image.fontgenerator.FontGenerator;
import com.octo.captcha.component.image.fontgenerator.RandomFontGenerator;
import com.octo.captcha.component.image.textpaster.RandomTextPaster;
import com.octo.captcha.component.image.textpaster.TextPaster;
import com.octo.captcha.component.image.wordtoimage.ComposedWordToImage;
import com.octo.captcha.component.image.wordtoimage.WordToImage;
import com.octo.captcha.component.word.wordgenerator.RandomWordGenerator;
import com.octo.captcha.component.word.wordgenerator.WordGenerator;
import com.octo.captcha.engine.image.ListImageCaptchaEngine;
import com.octo.captcha.image.gimpy.GimpyFactory;
public class ImageCaptchaEngine extends ListImageCaptchaEngine {
protected void buildInitialFactories() {
// 随机生成的字符
WordGenerator wgen = new RandomWordGenerator(
"abcdefghijklmnopqrstuvwxyz123456789");
RandomRangeColorGenerator cgen = new RandomRangeColorGenerator(
new int[] { 0, 100 }, new int[] { 0, 100 },
new int[] { 0, 100 });
// 文字显示的个数
TextPaster textPaster = new RandomTextPaster(new Integer(6),
new Integer(6), cgen, true);
// 图片的大小
BackgroundGenerator backgroundGenerator = new FunkyBackgroundGenerator(
new Integer(150), new Integer(50));
// 字体格式
Font[] fontsList = new Font[] { new Font("Arial", 0, 10),
new Font("Tahoma", 0, 10), new Font("Verdana", 0, 10), };
// 文字的大小
FontGenerator fontGenerator = new RandomFontGenerator(new Integer(15),
new Integer(30), fontsList);
WordToImage wordToImage = new ComposedWordToImage(fontGenerator,
backgroundGenerator, textPaster);
this.addFactory(new GimpyFactory(wgen, wordToImage));
}
}
=====================================================================
ImageCaptchaServlet:
public class ImageCaptchaServlet extends HttpServlet {
private static final long serialVersionUID = 3258417209566116145L;
private Log logger = LogFactory.getLog(this.getClass());
public void init(ServletConfig servletConfig) throws ServletException {
super.init(servletConfig);
}
protected void doGet(HttpServletRequest httpServletRequest,
HttpServletResponse httpServletResponse) throws ServletException,
IOException {
byte[] captchaChallengeAsJpeg = null;
// the output stream to render the captcha image as jpeg into
ByteArrayOutputStream jpegOutputStream = new ByteArrayOutputStream();
try {
// get the image captcha service defined via the
//SpringFramework
ApplicationContext ctx = WebApplicationContextUtils
.getRequiredWebApplicationContext(getServletContext());
Object bean = ctx.getBean("jcaptchaService");
ImageCaptchaService imageCaptchaService = (ImageCaptchaService) bean;
// get the id that will identify the generated captcha.
// the same id must be used to validate the response
String captchaId = httpServletRequest.getParameter("captchaId");
logger.debug("captchaIdParameter: "
+ httpServletRequest.getParameter("captchaId"));
if (captchaId == null) {
// If a captcha id is not passed in, use the session id
captchaId = httpServletRequest.getSession().getId();
logger.debug("httpServletRequest.session.id: "
+ httpServletRequest.getSession().getId());
}
logger.debug("captchaId: " + captchaId);
// call the ImageCaptchaService getChallenge method
BufferedImage challenge = imageCaptchaService
.getImageChallengeForID(captchaId,
httpServletRequest.getLocale());
// a jpeg encoder
JPEGImageEncoder jpegEncoder = JPEGCodec
.createJPEGEncoder(jpegOutputStream);
jpegEncoder.encode(challenge);
} catch (IllegalArgumentException e) {
httpServletResponse.sendError(HttpServletResponse.SC_NOT_FOUND);
return;
} catch (CaptchaServiceException e) {
httpServletResponse
.sendError(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
return;
}
captchaChallengeAsJpeg = jpegOutputStream.toByteArray();
// flush it in the response
httpServletResponse.setHeader("Cache-Control", "no-store");
httpServletResponse.setHeader("Pragma", "no-cache");
httpServletResponse.setDateHeader("Expires", 0);
httpServletResponse.setContentType("image/jpeg");
ServletOutputStream responseOutputStream = httpServletResponse
.getOutputStream();
responseOutputStream.write(captchaChallengeAsJpeg);
responseOutputStream.flush();
responseOutputStream.close();
}
}
=============================================================
ValidateJcaptchaAction (struts2 action):
private ImageCaptchaService jcaptchaService;
private String jcaptchaResponse;
public String validateJcaptcha() {
//getRequest() 是我自己写的get request 对象方法 在父类里实现了的
String id = getRequest().getSession().getId();
if (StringUtils.isNotBlank(jcaptchaResponse)) {
Boolean flag = jcaptchaService.validateResponseForID(id,
jcaptchaResponse);
if (flag) {
return SUCCESS;
}
}
return INPUT;
}
public void setJcaptchaService(ImageCaptchaService jcaptchaService) {
this.jcaptchaService = jcaptchaService;
}
public String getJcaptchaResponse() {
return jcaptchaResponse;
}
public void setJcaptchaResponse(String jcaptchaResponse) {
this.jcaptchaResponse = jcaptchaResponse;
}
=====================================================
captcaha.jsp页面:
<%@ page language="java" contentType="text/html; charset=GBK"
pageEncoding="GBK"%>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
<head>
<title>jcaptcha 使用</title>
<meta http-equiv="pragma" content="no-cache">
<meta http-equiv="cache-control" content="no-cache">
<meta http-equiv="expires" content="0">
<meta http-equiv="keywords" content="java,jcaptcha,验证码,更换图片">
<meta http-equiv="description" content="java 验证码 javascript">
<!--
<link rel="stylesheet" type="text/css" href="styles.css">
-->
</head>
<body>
<script language="javascript" type="text/javascript">
function changeImage() {
//下面两种方法都可以用
//document.photo.src='jcaptcha?id=' + Math.random();
document.getElementById('kaptchaImage').src = 'jcaptcha?id=' + Math.random();
}
</script>
<table>
<tr>
<td>
<img src="jcaptcha" width="200" id="kaptchaImage" name="photo" οnclick="changeImage();">
</td>
</tr>
<tr>
<td>
<a href="javascript:changeImage();" title="看不清,换一张" tabindex="-2"
style="color: gray; width: 130px">看不清,换一张</a>
</td>
</tr>
<tr>
<td valign="top">
<form method="POST" action="verify.action" name="jcaptcha">
<br>
请输入验证码:
<input type="text" name="j_captcha_response" value=''>
<br>
<input type="submit" name="submit">
</form>
</td>
</tr>
</table>
</body>
</html>
=================================================
web.xml:
<servlet>
<servlet-name>jcaptcha</servlet-name>
<servlet-class>com.radicasys.signup.jcaptcha.ImageCaptchaServlet</servlet-class>
<load-on-startup>3</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>jcaptcha</servlet-name>
<url-pattern>/jcaptcha</url-pattern>
</servlet-mapping>
====================================================
pom.xml设定:
<dependency>
<groupId>com.octo.captcha</groupId>
<artifactId>jcaptcha-all</artifactId>
<version>1.0-RC6</version>
</dependency>
===================================================
在spring 配置文件里 设定下ValidateJcaptchaAction 和jcaptchaService
applicationContext-service.xml
<bean id="jcaptchaService"
class="com.octo.captcha.service.multitype.GenericManageableCaptchaService">
<constructor-arg index="0">
<ref bean="imageEngine" />
</constructor-arg>
<constructor-arg index="1">
<value>1</value>
</constructor-arg>
<constructor-arg index="2">
<value>180000</value>
</constructor-arg>
</bean>
<!-- coding way to set imageEngine-->
<bean id="imageEngine" class="com.radicasys.signup.jcaptcha.ImageEngine">
</bean>
applicationCotext-struts.xml
<bean name="jcaptchaAction" class="com.radicasys.signup.jcaptcha.ValidateJcaptchaAction">
<property name="jcaptchaService" ref="jcaptchaService"/>
</bean>
=======================================================
struts2 配置页面(struts.xml)
<action name="" class="">
<result>你自己的页面</result>
<result name="input">你自己的页面</result>
</action>
基本上就是这样了,不过最好是在spring那里配置图片样式,自己写代码(上面的ImageCaptchaEngine 类)对以后的更改不方便,这里有个参考:你也可以对着那个ImageCaptchaEngine去配置
<bean id="imageEngine"
class="com.octo.captcha.engine.GenericCaptchaEngine">
<constructor-arg index="0">
<list>
<ref bean="CaptchaFactory" />
</list>
</constructor-arg>
</bean>
<bean id="CaptchaFactory"
class="com.octo.captcha.image.gimpy.GimpyFactory">
<constructor-arg>
<ref bean="wordgen" />
</constructor-arg>
<constructor-arg>
<ref bean="wordtoimage" />
</constructor-arg>
</bean>
<bean id="wordgen"
class="com.octo.captcha.component.word.wordgenerator.DictionaryWordGenerator">
<constructor-arg>
<ref bean="filedict" />
</constructor-arg>
</bean>
<bean id="wordtoimage"
class="com.octo.captcha.component.image.wordtoimage.ComposedWordToImage">
<constructor-arg index="0">
<ref bean="fontGenRandom" />
</constructor-arg>
<constructor-arg index="1">
<ref bean="backGenUni" />
</constructor-arg>
<constructor-arg index="2">
<ref bean="simpleWhitePaster" />
</constructor-arg>
</bean>
<bean id="filedict"
class="com.octo.captcha.component.word.FileDictionary">
<constructor-arg index="0">
<value>toddlist</value>
</constructor-arg>
</bean>
<bean id="fontGenRandom"
class="com.octo.captcha.component.image.fontgenerator.RandomFontGenerator">
<!-- font min -->
<constructor-arg index="0">
<value>20</value>
</constructor-arg>
<!--font max -->
<constructor-arg index="1">
<value>20</value>
</constructor-arg>
<constructor-arg index="2">
<list>
<ref bean="fontArial" />
</list>
</constructor-arg>
</bean>
<bean id="fontArial" class="java.awt.Font">
<constructor-arg index="0">
<value>Arial</value>
</constructor-arg>
<constructor-arg index="1">
<value>0</value>
</constructor-arg>
<constructor-arg index="2">
<value>10</value>
</constructor-arg>
</bean>
<bean id="backGenUni"
class="com.octo.captcha.component.image.backgroundgenerator.UniColorBackgroundGenerator">
<!--length -->
<constructor-arg index="0">
<value>80</value>
</constructor-arg>
<!--hight -->
<constructor-arg index="1">
<value>25</value>
</constructor-arg>
</bean>
<bean id="simpleWhitePaster"
class="com.octo.captcha.component.image.textpaster.SimpleTextPaster">
<!-- min number -->
<constructor-arg type="java.lang.Integer" index="0">
<value>4</value>
</constructor-arg>
<!--max number -->
<constructor-arg type="java.lang.Integer" index="1">
<value>4</value>
</constructor-arg>
<!-- color -->
<constructor-arg type="java.awt.Color" index="2">
<ref bean="colorGreen" />
</constructor-arg>
</bean>
<bean id="colorGreen" class="java.awt.Color">
<constructor-arg index="0">
<value>0</value>
</constructor-arg>
<constructor-arg index="1">
<value>0</value>
</constructor-arg>
<constructor-arg index="2">
<value>255</value>
</constructor-arg>
</bean>