基于SpringBoot实现验证码功能

[复制链接]
发表于 2026-2-19 18:48:14 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能,让你轻松玩转社区。

您需要 登录 才可以下载或查看,没有账号?立即注册

×
目次
一 实现思绪
二 代码实现
三 代码汇总



如今的登录都必要输入验证码用来检测是否是真人登录,以是验证码功能在如今好坏常广泛的,那么接下来我们就基于springboot来实现验证码功能。
一 实现思绪

         本日我们先容的是两种主流的验证码,一种就是上图所示的必要举行盘算的验证码,别的一种就是不必要盘算,直接输入的验证码。
   1.如果验证码的范例是一个盘算范例验证码
  1. * 那么我们就需要分析一下:
  2. * 比如一个计算类型的验证码:1+2=?
  3. * 那么我们到时候应该填入的验证码的答案是:3
  4. * 所以这个验证码它包含了两个部分,一个是"1+2=?" 另外一个是"3"
  5. * 其实生成这个计算问题是我们自己来实现的,我们的工具类已经封装好了计算提,比如:“1+2=3”
  6. * 所以我们现在要做的主要有三步:
  7. * 1.得到这个算式后,将算是“1+2=3”分割成两个部分,“1+2=?” 和 “3”
  8. * 2.然后我们需要把它们存储到缓存中去,前面可以当作key,后面可以当作value,然后进行验证答案的正确性
  9. * 3.最后,我们需要把“1+2=?”制作成一个图片返回给前端,用于展示给用户,
复制代码
    2.如果验证码的范例是一个寻常的图形验证码
      那么我们不要分为表达式和答案两个部门,我们只必要把天生的这个图形直接存入缓存中去就可以了。
      但是由于我们这两种范例是在同一个类中举行判断的,以是最好还是用两个变量来吸取。
    上面这两中范例的验证码判断完成之后,不管是那种范例,末了都必要把数据存到缓存中,而且都会天生一个Base64编码的一个图片,我们只必要返回这个图片即可,还必要一个uuid,由于这个是用来作为key的唯一标识。
  二 代码实现

开始代码之前,先先容一下我注入的几个bean:
  1.     @Autowired
  2.     private ISysConfigService configService ;  //判断是否开启验证码
  3.     @Autowired
  4.     private FeiSiConfig feiSiConfig ; //配置信息
  5.     @Autowired
  6.     private KaptchaTextCreator kaptchaTextCreator ; //随机生成验证码表达式
  7.     @Autowired
  8.     private RedisCache redisCache ; //存储数据到缓存
  9.     @Resource(name = "captchaProducer")
  10.     private Producer captchaProducer; //生成普通类型验证码图片
  11.     @Resource(name="captchaProducerMath")
  12.     private Producer  captchaProducerMath;  //生成计算类型验证码图片
复制代码
① 先判断有没有开启验证码功能。
   我们有一个网页功能的数据库表,内里可以选择是否开启验证码功能,而且在类加载的时间,我们就已经利用 @PostConstruct(标记在方法上, 当这个bean创建完成,自动实验这个注解标记方法,要求这个方法无参 类似 init-method设置) 注解将数据库的数据缓存在了redis内里。
  以是我们可以判断先判断有没有开启验证码功能:
  1. //        先要判断一下是否开启了验证码功能,如果没有开启,则不需要进行生成验证码的操作了
  2.         boolean captchaEnabled = configService.selectCaptchaEnabled();
  3.         if (!captchaEnabled){
  4.             return ajaxResult.put("captchaOnOff",captchaEnabled) ; //返回没有开启验证码信息给前端
  5.         }
复制代码
  1. configService这个类就是我们用来初始化缓存数据的,这个类代码如下:
复制代码
  1. package com.fs.system.service.ipml;
  2. import cn.hutool.core.convert.Convert;
  3. import cn.hutool.core.util.StrUtil;
  4. import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
  5. import com.fs.common.constant.CacheConstants;
  6. import com.fs.common.core.pojo.SysConfig;
  7. import com.fs.common.util.RedisCache;
  8. import com.fs.common.util.StringUtils;
  9. import com.fs.system.mapper.SysConfigMapper;
  10. import com.fs.system.service.ISysConfigService;
  11. import org.springframework.beans.factory.annotation.Autowired;
  12. import org.springframework.stereotype.Service;
  13. import javax.annotation.PostConstruct;
  14. import java.util.List;
  15. import java.util.Objects;
  16. @Service
  17. public class SysConfigServiceImpl  implements ISysConfigService {
  18.     @Autowired
  19.     private SysConfigMapper sysConfigMapper;
  20.     @Autowired
  21.     private RedisCache redisCache;
  22.     @PostConstruct  //标记在方法上, 当这个bean创建完成,自动执行这个注解标记方法,要求这个方法无参  类似 init-method配置
  23.     public void  init(){
  24.         loadingConfigCache();
  25.     }
  26. //    初始化数据,当系统加载的时候,把数据存入到缓存中去
  27.     @Override
  28.     public void loadingConfigCache() {
  29.         System.out.println("初始化数据...");
  30.         //查询数据库
  31.         List<SysConfig> sysConfigs = sysConfigMapper.selectList(null);
  32.         //保存到redis缓存中
  33.         sysConfigs.forEach((sysConfig)->{
  34.             redisCache.setCacheObject(getCacheKey(sysConfig.getConfigKey()),sysConfig.getConfigValue());
  35.         });
  36.     }
  37.     /**
  38.      * 构建参数配置表的redis的key
  39.      * @param configKey
  40.      * @return
  41.      */
  42. //    获取redis缓存中的key
  43.     private String getCacheKey(String configKey){
  44.         return CacheConstants.SYS_CONFIG_KEY+configKey;
  45.     }
  46. //    判断账号的验证码是否以及开启
  47.     @Override
  48.     public boolean selectCaptchaEnabled() {
  49.         String cacheObject = redisCache.getCacheObject("sys.account.captchaOnOff");
  50.         if (StrUtil.isBlank(cacheObject)){
  51. //            如果查询出来的是空,则说明该账号是第一次登录,则默认开启验证码
  52.             return true ;
  53.         }
  54. //        如果不是空,那么查询到的数据不是true就是false,但是存到数据库的并不是Boolean类型而是String类型,
  55. //        所以我们借用工具直接把字符串转成对应的Boolean类型
  56.         return Convert.toBool(cacheObject) ;
  57.     }
  58. //    根据账号的key获取缓存中的value
  59.     @Override
  60.     public String selectConfigByKey(String configKey) {
  61. //       1. 如果从redis中得到了数据,那么直接返回
  62.         String cacheObject = redisCache.getCacheObject(getCacheKey(configKey));
  63. //        我们需要返回的是一个String类型,所以需要用工具包转为String类型
  64.         String toStr = Convert.toStr(cacheObject);
  65.         if (StrUtil.isNotBlank(toStr)){
  66.             return toStr ;
  67.         }
  68. //       2.如果没有得到数据,那么我们需要从sys_config数据库表中查询数据,同时把查询到的数据存入缓存中
  69.         LambdaQueryWrapper<SysConfig> queryWrapper=new LambdaQueryWrapper<>();
  70.         queryWrapper.eq(SysConfig::getConfigKey,configKey);
  71.         SysConfig sysConfig = sysConfigMapper.selectOne(queryWrapper);
  72. //        如果查到有数据,就存入redis并且返回
  73.         if(Objects.nonNull(sysConfig)){  //这里判空的方法不能继续和上面一样,因为sysConfig并不是字符串类型,而是一个对象
  74. //            获取到值
  75.             String configValue = sysConfig.getConfigValue();
  76.             redisCache.setCacheObject(getCacheKey(configKey),configValue);
  77.             return configValue;
  78.         }
  79. //        否则没有查到数据,则说明没有信息
  80.         return null ;
  81.     }
  82. }
复制代码

在举行正式写逻辑代码之前,我们必要引入几个变量。
按照我们上面分析的,如果是一个盘算范例的验证码,那么我们一个必要四个变量:
一个变量是表达式的前半部门,一个变量是表达式的答案,
一个变量是用于存储天生的验证码图片的Base64编码,
末了一个就是验证码数据存储在redis作为唯一标识key的uuid
  1.         BufferedImage image = null ;//图片
  2.         String expression ; //表达式部分
  3.         String answer ; //答案部分
  4.         String uuid  = UUID.randomUUID().toString();; //uuid
复制代码

② 判断开启后,我们接下来必要判断利用的是哪一种验证码,详细利用哪一种是我们自己设置好的,我们规定math是盘算范例的验证码,char是寻常验证码。
  
  1.          /**
  2.          * 至于这个captchaType的值是根据配置文件设置的,因为这个FeisiConfig是一个配置类
  3.          * 它加了‘@ConfigurationProperties(prefix = "fs")’这个注解,
  4.          * 而配置文件规定math是计算类型验证码,char是图形类型验证码
  5.          */
  6.         String captchaType = feiSiConfig.getCaptchaType();
复制代码
</
回复

使用道具 举报

登录后关闭弹窗

登录参与点评抽奖  加入IT实名职场社区
去登录
快速回复 返回顶部 返回列表