登录验证码功能实现:Spring Boot + Vue 全流程解析
验证码是保护系统安全的重要防线,本文将完整解析前后端分离架构中验证码功能的实现原理与代码实践。
一、验证码的核心作用
防暴力破解:增加恶意登录的时间成本
阻断自动化脚本:防止机器人批量攻击
安全加固:作为密码之外的第二道安全屏障
二、后端实现(Spring Boot)
1. 验证码生成与存储
@RestController
public class CaptchaController {@Autowiredprivate RedisTemplate<String, String> redisTemplate;@GetMapping("/captcha")public Result generateCaptcha() {// 创建数学公式验证码(可切换为图形验证码)CircleCaptcha captcha = CaptchaUtil.createCircleCaptcha(150, 40, 4, 4);String code = captcha.getCode().toUpperCase(); // 验证码文本String uuid = IdUtil.simpleUUID(); // 唯一标识// 存储到Redis(120秒有效期)redisTemplate.opsForValue().set("captcha:" + uuid, code,120, TimeUnit.SECONDS);// 构造响应数据Map<String, Object> result = new HashMap<>();result.put("uuid", uuid);result.put("img", captcha.getImageBase64Data());return Result.ok().data(result);}
}
三、前端实现(Vue + ElementUI)
1. 验证码组件
//vue组件
<template><el-form-item prop="code"><el-input v-model="loginForm.code" placeholder="验证码" /><div class="captcha-img"><img :src="'data:image/png;base64,' + captchaImg" @click="refreshCaptcha"></div></el-form-item>
</template><script>
export default {data() {return {loginForm: {username: '',password: '',code: '',uuid: ''},captchaImg: ''}},methods: {// 获取验证码async refreshCaptcha() {const res = await getCaptchaImg();this.captchaImg = res.img;this.loginForm.uuid = res.uuid;},// 登录提交async handleLogin() {await this.$refs.form.validate();try {await login(this.loginForm);// 登录成功跳转...} catch (error) {// 失败时刷新验证码this.refreshCaptcha(); }}},mounted() {this.refreshCaptcha();}
}
</script>
四、关键技术解析
验证码生成工具
Hutool的
CircleCaptcha
:创建带干扰线的数学公式验证码可切换为
ShearCaptcha
(扭曲图形验证码)或GifCaptcha
(动态验证码)
Redis存储设计
Key: "captcha:3b4e5c6d-7f8a-90b1-c2d3e4f5a6b7" Value: "A3F8" # 验证码文本 TTL: 120秒 # 短时效保障安全
2
安全增强策略
验证码全大写比对:
.equalsIgnoreCase()
单次有效性:验证后立即删除Redis记录
请求频率限制:IP级验证码获取限流
五、最佳实践建议
多类型验证码切换
// 根据安全级别动态选择 Captcha createCaptcha(int securityLevel) {switch(securityLevel) {case 1: return new LineCaptcha();case 2: return new CircleCaptcha();case 3: return new GifCaptcha();default: return new ShearCaptcha();} }
行为验证码集成
滑块验证:使用AJ-Captcha等开源方案
文字点选:结合机器学习识别复杂场景
监控与告警
// 记录验证失败日志 @Aspect public class CaptchaAspect {@AfterThrowing(pointcut = "execution(* login(..))", throwing = "ex")public void logFailedAttempt(Throwable ex) {if ("验证码错误".equals(ex.getMessage())) {securityLogService.logFailedAttempt();}} }
六、总结
验证码功能实现需关注三个核心维度:
生成复杂度 - 平衡用户体验与安全性
传输安全 - Base64编码直传避免额外请求
验证可靠性 - Redis保证验证状态的原子性