1、验证码案例
注:验证码生成大多由前端负责,但由于各位后端程序员不太懂前端,又想学习验证码的生成和验证,所以作者编写了这篇基本由后端负责的验证码案例!
随着安全性的要求越来越⾼, ⽬前项⽬中很多都使⽤了验证码, 验证码的形式也是多种多样, 更复杂的图形验证码和行为验证码已经成为了更流⾏的趋势.
验证码的实现⽅式很多, ⽹上也有⽐较多的插件或者⼯具包可以使⽤, 咱们选择使⽤Google的开源项⽬ Kaptcha来实现.
1.1、项目前端页面展示:
1.2、代码结构展示:
2、Kaptcha 插件介绍及简单讲解如何使用
- 此处我们使用的这个Kaptcha是适配SpringBoot进行二次开发后的,使用极其简单
- Kaptcha 是Google的⼀个⾼度可配置的实⽤验证码⽣成⼯具,官方文档:
- https://code.google.com/archive/p/kaptcha/
- ⽹上有很多⼈甚⾄公司基于Google的kaptcha进⾏了⼆次开发. 我们选择⼀个直接适配SpringBoot的 开源项⽬
- GitHub - oopsguy/kaptcha-spring-boot: Kaptcha Spring Boot Starter help you use Google Kaptcha with Spring Boot easier. 一个简单封装了 Kaptcha 验证码库的 Spring Boot Starter
- 由于作者的⽂档写的不是很全, 下⾯简单介绍下插件的使⽤
2.1、原理
验证码可以客⼾端⽣成, 也可以服务器⽣成. 对于普通的字符验证码, 后端通常分两部分.
⼀是⽣成验证码内容, 根据验证码内容和⼲扰项等, ⽣成图⽚, 返回给客⼾端
⼆是把验证码内容存储起来, 校验时取出来进⾏对⽐.
kaptcha插件选择把验证码存储在Session⾥.
2.2、引入依赖
<dependency>
<groupId>com.oopsguy.kaptcha</groupId>
<artifactId>kaptcha-spring-boot-starter</artifactId>
<version>1.0.0-beta-2</version>
</dependency>
2.3、生成验证码
该插件提供了两种⽅式⽣成验证码
- GitHub - oopsguy/kaptcha-spring-boot: Kaptcha Spring Boot Starter help you use Google Kaptcha with Spring Boot easier. 一个简单封装了 Kaptcha 验证码库的 Spring Boot Starter 第一种参考官方文档即可,有点麻烦,此处不再介绍
- 仅通过配置⽂件来⽣成验证码(超级简单,推荐)
2.4、Kaptcha详细配置如下:
上面的许多配置⽂档中都没有介绍, 感兴趣的朋友可以观看源码:
com.oopsguy.kaptcha.autoconfigure.KaptchaProperties
也可以使⽤ kaptcha.items 配置多个验证码⽣成器
kaptcha.items 是⼀个Map, key为验证码⽣成器名称, value为验证码⽣成器的配置
2.5、常用配置如下(直接在yml里配置即可,可适当忽略上面那么多配置,下面这些是最常用的!):
kaptcha:
image:
width: 100
height: 60
textproducer:
font:
size: 36
items:
# home captcha
admin:
path: /admin/captcha
session:
key: HOME_KAPTCHA_SESSION_KEY
date: HOME_KAPTCHA_SESSION_DATE
配置说明:
配置后, 可以直接访问 http://XXXX:port/home/captcha即可⽣成验证码
3、验证码项目正式编写
3.1、约定前后端交互接口
生成验证码
请求: GET /admin/captcha
响应:图片内容
补充说明:浏览器给服务器发送⼀个 GET /admin/captcha 这样的请求, 服务器返回⼀个图⽚, 浏览器显示在页面上
校验验证码是否正确
请求:POST /admin/check
请求中携带内容: captcha= XXXX (captcha是用户输入的验证码)
响应:true/false
根据⽤⼾输⼊的验证码, 校验验证码是否正确. true: 验证成功. false: 验证失败.
3.2、创建SpringBoot项目
如何在idea中创建Springboot项目? 手把手带你创建Springboot项目,稳!-CSDN博客
创建时导入SpringWeb和lombok依赖
3.3、实现服务器端(后端)代码
3.3.1、引入依赖
<dependency>
<groupId>com.oopsguy.kaptcha</groupId>
<artifactId>kaptcha-spring-boot-starter</artifactId>
<version>1.0.0-beta-2</version>
</dependency>
3.3.2、通过yml配置创建验证码生成器
你的application文件后缀大概率是 .properties ,将其后缀改为 .yml 即可
kaptcha:
image:
width: 100
height: 60
textproducer:
font:
size: 33
items:
# home captcha
admin:
path: /admin/captcha
session:
key: HOME_KAPTCHA_SESSION_KEY
date: HOME_KAPTCHA_SESSION_DATE
简单解释session下面的配置:
- key:引入该配置后,它会自动帮我们把验证码内容(已转换成字符串)设置到session中,名称为key后面的内容
- date:通常设置为验证码过期时间
友情提示:我这里只写了部分配置,能满足上面我展示图片的要求,若你想配置更多样式,可以查看我上面的配置大全!这里不过多介绍
3.3.3、后端返回验证码
注:该配置引入后,不需要写其他代码,他会自动创建/admin/captcha接口,访问该接口即显示验证码,这个工作是该配置以及引入的依赖包自动帮我们完成的
3.3.4、验证码校验
import org.springframework.util.StringUtils;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import javax.servlet.http.HttpSession;
import java.util.Date;
@RequestMapping("/admin")
@RestController
public class CaptchaController {
//企业标准(建议):
//常量定义: key: 全部大写, 单词之间使用下划线分割 value: 通常是小写, 以下划线分割
private static final String KAPTCHA_SESSION_KEY = "HOME_KAPTCHA_SESSION_KEY";
private static final String KAPTCHA_SESSION_DATE = "HOME_KAPTCHA_SESSION_DATE";
//验证码的有效时间:ms
private static final Long SESSION_TIMEOUT = 60 * 1000L;
//验证成功: true
//验证失败: false
/**
* 1. 从Session中获取到生成的验证码
* 2. 比对前端传递的验证码和Session中存储的是否一样
*/
@RequestMapping("/check")
public Boolean check(String captcha, HttpSession session){
if (!StringUtils.hasLength(captcha)){
return false;
}
//从Session中获取验证码
String saveCaptcha = (String)session.getAttribute(KAPTCHA_SESSION_KEY);
Date saveDate = (Date)session.getAttribute(KAPTCHA_SESSION_DATE);
//比对验证码
if (captcha.equals(saveCaptcha)){
//比对日期
if (saveDate==null || System.currentTimeMillis() - saveDate.getTime()<SESSION_TIMEOUT){
return true;
}
}
return false;
}
}
逻辑如下:
- 先判断验证码是否为空,若为空,直接返回false,不为空,往下走
- 从session中获取验证码和过期时间
- 比对验证码是否正确,且是否过期,如果有任意一个不符合条件,返回false,如果都符合条件,返回true
3.4、实现前端代码(带完整源码)
3.4.1、主页页面:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<title>验证码</title>
<style>
#inputCaptcha {
height: 30px;
vertical-align: middle;
}
#verificationCodeImg{
vertical-align: middle;
}
#checkCaptcha{
height: 40px;
width: 100px;
}
</style>
</head>
<body>
<h1>输入验证码</h1>
<div id="confirm">
<input type="text" name="inputCaptcha" id="inputCaptcha">
<!-- <img id="verificationCodeImg" src="/admin/captcha" style="cursor: pointer;" title="看不清?换一张" />-->
<img id="verificationCodeImg" src="http://127.0.0.1:8080/admin/captcha" style="cursor: pointer;" title="看不清?换一张" />
<input type="button" value="提交" id="checkCaptcha">
</div>
<script src="https://cdn.bootcdn.net/ajax/libs/jquery/3.6.4/jquery.min.js"></script>
<script>
$("#verificationCodeImg").click(function(){
// $(this).hide().attr('src', '/admin/captcha?dt=' + new Date().getTime()).fadeIn();
$(this).hide().attr('src', 'http://127.0.0.1:8080/admin/captcha?dt=' + new Date().getTime()).fadeIn();
});
$("#checkCaptcha").click(function () {
$.ajax({
type: "get",
url: "/admin/check",
data:{
captcha: $("#inputCaptcha").val()
},
success:function(result){
if(result){
location.href = "success.html";
// location.assign("success.html"); // 和上面这句一样,也是页面跳转
}else{
alert("验证码错误");
}
}
});
// alert("验证码校验");
});
</script>
</body>
</html>
前端代码就不在这里过多解释了,会的不用解释,不会的解释两下还是不明白,建议丢给gpt
3.4.2、验证正确后跳转的页面:
注:验证失败的话会在主页弹出一个小窗口,说明验证码校验失败
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>验证成功页</title>
</head>
<body>
<h1>验证成功</h1>
</body>
</html>
至此,项目所有代码编写完毕!
!!!注意事项!部署前后必看!!!
本项目部署在本地,默认是本地ip地址,也就是127.0.0.1或localhost
正常来说, 127.0.0.1:8080/index.html 和 localhost:8080/index.html 都可以,但是博主自己验证包括找了些其他博主验证,localhost:8080/index.html 访问的话是存在些许bug的,后端取session可能为空,原因是session没有设置
但127.0.0.1不会有这个问题,跨域访问ip也不会有问题,所以只要不用localhost即可,请问放心使用!
🧸欢迎您于百忙之中阅读这篇博客,📜希望这篇博客给您带来了一些帮助,祝您生活愉快!