博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
JavaWeb---制作验证码
阅读量:2488 次
发布时间:2019-05-11

本文共 13877 字,大约阅读时间需要 46 分钟。

说起验证码,绝壁是个让人蛋疼的问题,特别是节假日在12306上面抢票的时候遇到的外星系验证码,大大降低了用户的体验度!

可是还是要知道验证码为什么存在,其作用是什么!

验证码形式

字母数字组合、加减法、中英文、算式加减法……

 

为什么需要验证码

验证码降低了用户体验度,但是为什么存在呢???

如果没有验证码:

1)       对特定用户不断登录破解密码

2)       对某个网站创建账户

3)       对某个网站提交垃圾数据

4)       都某个网站刷票

如果存在验证码:

只有人亲自识别验证码,输入验证码内容,才能登录、发评论等等,防止计算机破解自动登录发灌水帖等;通过验证码来区分人和计算机;

 

制作验证码

验证码包含两部分:输入框和显示验证码的图片;

一般验证机制如下图:

可是,显示验证码的图片是如何产生的呢?

通过Servlet手工制作验证码(简单型)

1)       手工生成的验证码比较简单,用到的类有

2)       BufferedImage图像数据缓冲区

3)       Graphics绘制图片

4)       Color获取颜色

5)       Random生成随机数

6)       ImageIO输出图片

 

ImageServlet类:

package hdu.terence; import java.awt.Color;import java.awt.Graphics;import java.awt.image.BufferedImage;import java.io.IOException;import java.io.PrintWriter;import java.util.Random; import javax.imageio.ImageIO;import javax.servlet.ServletException;import javax.servlet.http.HttpServlet;importjavax.servlet.http.HttpServletRequest;importjavax.servlet.http.HttpServletResponse; public class ImageServlet extendsHttpServlet {        publicImageServlet() {              super();       }        publicvoid destroy() {              super.destroy();       }       publicvoid doGet(HttpServletRequest request, HttpServletResponse response)                     throwsServletException, IOException {              BufferedImagebi=new BufferedImage(68,22,BufferedImage.TYPE_INT_RGB);              Graphicsg=bi.getGraphics();              Colorc=new Color(200,150,255);              g.setColor(c);              g.fillRect(0,0, 68, 22);              char[]ch="WQERTYUIOPASDFG127890HJKLZ3456XCVBNMmnbvcxzkjhgfdsaqwertyuiop".toCharArray();              Randomr=new Random();              intlen=ch.length,index;                           StringBuffersb=new StringBuffer();//用于保存图片              for(inti=0;i<4;i++)              {                     index=r.nextInt(len);                     g.setColor(newColor(r.nextInt(88),r.nextInt(188),r.nextInt(255)));                     g.drawString(ch[index]+"",(i*15)+3, 18);                     sb.append(ch[index]);              }              request.getSession().setAttribute("verifyCode",sb.toString());              ImageIO.write(bi,"JPG", response.getOutputStream());       }       publicvoid doPost(HttpServletRequest request, HttpServletResponse response)                     throwsServletException, IOException {       }       publicvoid init() throws ServletException {                    }}

 

LoginServlet类:

package hdu.terence; import java.io.IOException;import java.io.PrintWriter; import javax.servlet.ServletException;import javax.servlet.http.HttpServlet;importjavax.servlet.http.HttpServletRequest;importjavax.servlet.http.HttpServletResponse; public class LoginServlet extendsHttpServlet {              publicLoginServlet() {              super();       }       publicvoid destroy() {       }       publicvoid doGet(HttpServletRequest request, HttpServletResponse response)                     throwsServletException, IOException {              response.setContentType("text/html;charset=gbk");              StringverifyCode=(String) request.getSession().getAttribute("verifyCode");              StringcheckCode=request.getParameter("checkCode");              verifyCode=verifyCode.toUpperCase();              checkCode=checkCode.toUpperCase();                           PrintWriterout=response.getWriter();              if(checkCode.equals(verifyCode))              {                     out.println("niece!验证码输入正确!");              }              else              {                     out.println("你似不似撒?验证码都能输入错误!!!!!!");              }              out.flush();              out.close();       }       publicvoid doPost(HttpServletRequest request, HttpServletResponse response)                     throwsServletException, IOException {       }       publicvoid init() throws ServletException {       }}

 

JSP:

       
验证码:
验证码
看不清,重新获取
   
 

结果

通过Kaptcha开源组件制作验证码(花式验证码)

Kaptcha:这个工具是可配置的,可以生成各种花式的验证码,可通过配置参数增加机器识别难度。

 

准备步骤:

1)       下载kaptcha-2.3.jar()

2)       将jar包导入项目,添加到路径

3)       编写页面

4)       配置web.xml

5)       启动项目

 

数字、英文混合验证

Step1 JSP

输入验证码:
看不清,重换一张
   

src:连接到后台生成的randomcode.jpg;

Step2  在web.xml中添加映射配置:

 

kaptcha
/randomcode.jpg

 

 

Step3  增加配置参数,防止机器识别图片

可配置的参数如下:

图片边框,合法值:yes , no
kaptcha.border
yes
-
边框颜色,合法值: r,g,b (and optional alpha) 或者white,black,blue.
kaptcha.border.color
red
-
边框厚度,合法值:>0
kaptcha.border.thickness
2
-
图片宽 200
kaptcha.image.width
150
-
图片高 50
kaptcha.image.height
50
-
图片实现类
kaptcha.producer.impl
com.google.code.kaptcha.impl.DefaultKaptcha
-
不用文本实现:com.google.code.kaptcha.impl.DifaultTextCreator用文本实现:则用自己重写的中文类(内含算法)ChineseTextCheck.ChineseTextCode
kaptcha.textproducer.impl
ChineseTextCheck.ChineseTextCode
-
文本集合,验证码值从此集合中获取
kaptcha.textproducer.char.string
qwertys1zcmd2345s67g890
-
-
-
验证码长度 5
kaptcha.textproducer.char.length
5
-
字体Arial, Courier
kaptcha.textproducer.font.names
Arial, Courier
-
字体大小 40px.
kaptcha.textproducer.font.size
30
-
字体颜色,合法值: r,g,b 或者 white,black,blue.
kaptcha.textproducer.font.color
black
-
文字间隔 2
kaptcha.textproducer.char.space
2
-
干扰实现类
kaptcha.noise.impl
-
-
com.google.code.kaptcha.impl.DefaultNoise
-
干扰颜色,合法值: r,g,b 或者 white,black,blue.
kaptcha.noise.color
blue
-
图片样式: 水纹com.google.code.kaptcha.impl.WaterRipple鱼眼com.google.code.kaptcha.impl.FishEyeGimpy阴影com.google.code.kaptcha.impl.ShadowGimpy
kaptcha.obscurificator.impl
com.google.code.kaptcha.impl.FishEyeGimpy
-
背景实现类
kaptcha.background.impl
com.google.code.kaptcha.impl.DefaultBackground
-
背景颜色渐变,开始颜色
kaptcha.background.clear.from
red
-
背景颜色渐变,结束颜色
kaptcha.background.clear.to
white
-
文字渲染器
kaptcha.word.impl
com.google.code.kaptcha.text.impl.DefaultWordRenderer
-
session中存放验证码的key键
kaptcha.session.key
KAPTCHA_SESSION_KEY
-
The date the kaptcha is generatedis put into the HttpSession. This is the key value for that item in thesession.
kaptcha.session.date
KAPTCHA_SESSION_DATE

 

Step 4  结果

 

中文验证码

Step1  重写配置文件里面的TextProducer类

 

import java.util.Random;import com.google.code.kaptcha.text.TextProducer;importcom.google.code.kaptcha.util.Configurable; public class ChineseTextCode extendsConfigurable implements TextProducer {        /*        * 中文验证码(non-Javadoc)        * 粘贴以下算法重写文本实现类        * @see com.google.code.kaptcha.text.TextProducer#getText()        */       publicString getText() {              intlength = getConfig().getTextProducerCharLength();              StringfinalWord = "", firstWord = "";              inttempInt = 0;              String[]array = { "0", "1", "2", "3","4", "5", "6", "7", "8","9",                            "a","b", "c", "d", "e", "f" };               Randomrand = new Random();               for(int i = 0; i < length; i++) {                     switch(rand.nextInt(array.length)) {                     case1:                            tempInt= rand.nextInt(26) + 65;                            firstWord= String.valueOf((char) tempInt);                            break;                     case2:                            intr1,                            r2,                            r3,                            r4;                            StringstrH,                            strL;//high&low                            r1= rand.nextInt(3) + 11; // 前闭后开[11,14)                            if(r1 == 13) {                                   r2= rand.nextInt(7);                            }else {                                   r2= rand.nextInt(16);                            }                             r3= rand.nextInt(6) + 10;                            if(r3 == 10) {                                   r4= rand.nextInt(15) + 1;                            }else if (r3 == 15) {                                   r4= rand.nextInt(15);                            }else {                                   r4= rand.nextInt(16);                            }                             strH= array[r1] + array[r2];                            strL= array[r3] + array[r4];                             byte[]bytes = new byte[2];                            bytes[0]= (byte) (Integer.parseInt(strH, 16));                            bytes[1]= (byte) (Integer.parseInt(strL, 16));                             firstWord= new String(bytes);                            break;                     default:                            tempInt= rand.nextInt(10) + 48;                            firstWord= String.valueOf((char) tempInt);                            break;                     }                     finalWord+= firstWord;              }              returnfinalWord;       }        publicString getText1() {              intlength = getConfig().getTextProducerCharLength();              //char[]charS = getConfig().getTextProducerCharString();                           String[]s = new String[]{"我","是","阿","S","靖","卡","哥","滚","蛋","呸"};               Randomrand = new Random();              StringBuffersb = new StringBuffer();              for(inti = 0; i < length; i++){                     intind =rand.nextInt(s.length);                     sb.append(s[ind]);              }              returnsb.toString();       }}

Step2  然后修改配置文件web.xml

文本实现类
kaptcha.textproducer.impl
ChineseTextCheck.ChineseTextCode

Step 3  结果

算式验证码

以重写Servlet的方式实现算式验证码

步骤:

1)       获取随机数值,结果相加

2)       将计算公式写到图片上

3)       将相加结果保存到session中

4)       依此为目标重写KapthaServlet类

 

Step1  重写KaptchaServlet

package formula; import com.google.code.kaptcha.Producer;import com.google.code.kaptcha.util.Config;import java.awt.image.BufferedImage;import java.io.IOException;import java.util.Enumeration;import java.util.Properties;import javax.imageio.ImageIO;import javax.servlet.Servlet;import javax.servlet.ServletConfig;import javax.servlet.ServletException;import javax.servlet.ServletOutputStream;import javax.servlet.http.HttpServlet;import javax.servlet.http.HttpServletRequest;importjavax.servlet.http.HttpServletResponse;import javax.servlet.http.HttpSession; public class KaptchaServlet extendsHttpServlet implements Servlet {       privateProperties props;       privateProducer kaptchaProducer;       privateString sessionKeyValue;        publicKaptchaServlet() {              this.props= new Properties();               this.kaptchaProducer= null;               this.sessionKeyValue= null;       }        publicvoid init(ServletConfig conf) throws ServletException {              super.init(conf);               ImageIO.setUseCache(false);               EnumerationinitParams = conf.getInitParameterNames();              while(initParams.hasMoreElements()) {                     Stringkey = (String) initParams.nextElement();                     Stringvalue = conf.getInitParameter(key);                     this.props.put(key,value);              }               Configconfig = new Config(this.props);              this.kaptchaProducer= config.getProducerImpl();              this.sessionKeyValue= config.getSessionKey();       }        publicvoid doGet(HttpServletRequest req, HttpServletResponse resp)                     throwsServletException, IOException {              resp.setDateHeader("Expires",0L);               resp.setHeader("Cache-Control","no-store, no-cache, must-revalidate");               resp.addHeader("Cache-Control","post-check=0, pre-check=0");               resp.setHeader("Pragma","no-cache");               resp.setContentType("image/jpeg");               StringcapText = this.kaptchaProducer.createText();              Strings1 = capText.substring(0, 1);              Strings2 = capText.substring(1, 2);              intr = Integer.valueOf(s1).intValue() + Integer.valueOf(s2).intValue();               req.getSession().setAttribute(this.sessionKeyValue,String.valueOf(r));               BufferedImagebi = this.kaptchaProducer.createImage(s1+"+"+s2+"=?");               ServletOutputStreamout = resp.getOutputStream();               ImageIO.write(bi,"jpg", out);              try{                     out.flush();              }finally {                     out.close();              }       }}

Step2  配置web.xml

kaptcha
文字、数字英文方式:com.google.code.kaptcha.servlet.KaptchaServlet 算式:使用自己重写的类:formula.KaptchaServlet
formula.KaptchaServlet

上述中formula.KaptchaServlet是指自己在formula包下重写的KaptchaServlet类。

Step3  结果

References Demo

参考源码:

你可能感兴趣的文章
ios设备唯一标识获取策略
查看>>
获取推送通知的DeviceToken
查看>>
Could not find a storyboard named 'Main' in bundle NSBundle
查看>>
CocoaPods安装和使用教程
查看>>
Beginning Auto Layout Tutorial
查看>>
block使用小结、在arc中使用block、如何防止循环引用
查看>>
iPhone开发学习笔记002——Xib设计UITableViewCell然后动态加载
查看>>
iOS开发中遇到的问题整理 (一)
查看>>
Swift code into Object-C 出现 ***-swift have not found this file 的问题
查看>>
为什么你的App介绍写得像一坨翔?
查看>>
RTImageAssets插件--@3x可自动生成@2x图片
查看>>
iOS开发的一些奇巧淫技
查看>>
常浏览的博客和网站
查看>>
Xcode 工程文件打开不出来, cannot be opened because the project file cannot be parsed.
查看>>
iOS在Xcode6中怎么创建OC category文件
查看>>
5、JavaWeb学习之基础篇—标签(自定义&JSTL)
查看>>
8、JavaWEB学习之基础篇—文件上传&下载
查看>>
reRender属性的使用
查看>>
href="javascript:void(0)"
查看>>
h:panelGrid、h:panelGroup标签学习
查看>>