文章

【若依】3、验证码(kaptcha)

AjaxResult:出参;code状态码)、msg返回内容)、data(数据对象)。 验证码引用了一个开源项目: GitHub - penggle/kaptcha: kaptcha - A kaptcha generation engine. captchaEnabled:是否开启验证码功能;对应的数据库中表:sys_config,此配置会缓存redis中。 验证码图片返回的格式是:base64编码,这样的优势是还可以同时返回其他数据。 captchaType验证码类型 math 数组计算 char 字符;可在 application.yml 中配置。

验证码配置

  • 关于验证码在session中的存储问题

tienchin-framework/src/main/java/top/yueyazhui/tienchin/framework/config/CaptchaConfig.java char:top.yueyazhui.tienchin.framework.config.CaptchaConfig#getKaptchaBean math:top.yueyazhui.tienchin.framework.config.CaptchaConfig#getKaptchaBeanMath 其中有一项配置可以忽略,因为这项配置不会生效:

1
2
// KAPTCHA_SESSION_KEY
properties.setProperty(KAPTCHA_SESSION_CONFIG_KEY, "kaptchaCode");
1
2
// KAPTCHA_SESSION_KEY
properties.setProperty(KAPTCHA_SESSION_CONFIG_KEY, "kaptchaCodeMath");

此项配置的作用是:生成验证码的时候,会自动将验证码文本存入session中。 如果使用kaptcha提供的KaptchaServlet这项配置才可以生效;如果是自己写的Controller不会生效,如有需要,自己写的Controller需要自己把验证码文本存入session中; 测试代码地址: yueyazhui/ruoyi_kaptcha

  • 验证码文本生成器

在math中使用了自己提供的验证码文本生成器 tienchin-framework/src/main/java/top/yueyazhui/tienchin/framework/config/KaptchaTextCreator.java

验证码的校验

入口: tienchin-admin/src/main/java/top/yueyazhui/tienchin/web/controller/system/SysLoginController.java top.yueyazhui.tienchin.web.controller.system.SysLoginController#login 校验方法: tienchin-framework/src/main/java/top/yueyazhui/tienchin/framework/web/service/SysLoginService.java top.yueyazhui.tienchin.framework.web.service.SysLoginService#validateCaptcha

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
/**
 * 校验验证码
 *
 * @param username 用户名
 * @param code     验证码
 * @param uuid     唯一标识
 * @return 结果
 */
public void validateCaptcha(String username, String code, String uuid) {
    String verifyKey = CacheConstants.CAPTCHA_CODE_KEY + StringUtils.nvl(uuid, "");
    // 获取redis中保存的验证码文本
    String captcha = redisCache.getCacheObject(verifyKey);
    // 删除redis中保存的验证码文本
    redisCache.deleteObject(verifyKey);
    if (captcha == null) {
        // redis中不存在验证码(超过两分钟,验证码过期被自动删除)
        // 开启一个异步任务去写日志
        AsyncManager.me().execute(AsyncFactory.recordLogininfor(username, Constants.LOGIN_FAIL, MessageUtils.message("user.jcaptcha.expire")));
        throw new CaptchaExpireException();
    }
    if (!code.equalsIgnoreCase(captcha)) {
        AsyncManager.me().execute(AsyncFactory.recordLogininfor(username, Constants.LOGIN_FAIL, MessageUtils.message("user.jcaptcha.error")));
        throw new CaptchaException();
    }
}
本文由作者按照 CC BY 4.0 进行授权