Spring Boot项目Auth模块如何接入anji-captcha验证码
验证码作为防御自动化攻击的“得力小助手”,能有效拦住机器人和恶意脚本的捣乱。今天这篇文章,就手把手教大家在Spring Boot框架的Auth模块里,接入超实用的anji-captcha滑动验证码功能,从配置、实现接口到融入认证流程,每一步都安排得明明白白!
一、配置验证码服务
咱要接入验证码,得先有个能生成和验证它的服务类。这里,咱们用超好用的anji-captcha库,再借助Spring的@Bean注解,把它“送”到IoC容器里,这样后续就能随时用啦。
@Bean public CaptchaService captchaService() { // 创建配置属性对象 Properties config = new Properties(); // 使用Redis作为验证码的缓存,这样能避免内存占用太多,还能在分布式环境里正常工作 config.put(Const.CAPTCHA_CACHETYPE, "redis"); // 去掉验证码上的水印,如果想加的话也能自定义内容 config.put(Const.CAPTCHA_WATER_MARK, ""); // 设置验证码类型为滑动拼图验证码,要是想用别的类型也能改 config.put(Const.CAPTCHA_TYPE, CaptchaTypeEnum.BLOCKPUZZLE.getCodeValue()); // 这是个可选配置,用来指定拼图图片放哪儿,不写的话就用默认图片 // config.put(Const.ORIGINAL_PATH_JIGSAW, FileUtil.getAbsolutePath("classpath:captcha")); // 通过工厂模式,根据配置创建验证码服务实例 return CaptchaServiceFactory.getInstance(config); }
这里的配置参数都很关键:
CAPTCHA_CACHETYPE
:决定了验证码的缓存类型,选Redis是因为它能让验证码在分布式场景里稳定存储,还不咋占内存。CAPTCHA_WATER_MARK
:就是控制水印的,空着就是没水印,要是有特殊需求,比如加上公司logo啥的,就可以自定义。CAPTCHA_TYPE
:能选择各种验证码类型,这次咱用的是滑动拼图验证码,要是想换成像点击特定图片那种,改这里就行。ORIGINAL_PATH_JIGSAW
:这个参数可写可不写,写了就能指定拼图图片的存放路径,不写就用默认的图片。
CaptchaServiceFactory.getInstance(config)
用的是工厂模式,它能根据咱们设置的配置,自动创建合适的验证码服务实例,然后注册成Spring Bean,要用的时候直接“拿”来用就好。
二、实现验证码控制器
验证码有俩核心功能,生成和验证,咱们就通过CaptchaController
这个类来实现对应的接口。其实,CaptchaService
这个实例是anji-captcha包里自带的,咱们不用自己再写一套校验逻辑,在配置里设置好验证码类型和缓存来源,在控制器里调用就行。
@RestController @RequestMapping("/ua/captcha") @Api(tags = "验证码") public class CaptchaController { // 通过依赖注入,把CaptchaService引入到控制器里 private final CaptchaService captchaService; public CaptchaController(CaptchaService captchaService) { this.captchaService = captchaService; } // 处理生成验证码的请求 @PostMapping("/get") public ServerResponseEntity<ResponseModel> get(@RequestBody CaptchaVO captchaVO) { // 调用CaptchaService的get方法生成验证码,并返回结果 return ServerResponseEntity.success(captchaService.get(captchaVO)); } // 处理验证验证码的请求 @PostMapping("/check") public ServerResponseEntity<ResponseModel> check(@RequestBody CaptchaVO captchaVO) { // 调用CaptchaService的check方法验证验证码,并返回结果 return ServerResponseEntity.success(captchaService.check(captchaVO)); } }
这里面的门道也不少:
- 依赖注入:通过构造函数把
CaptchaService
注入进来,这样控制器就能调用它的各种方法啦。 - 接口设计:
/get
接口:专门用来生成验证码,会返回拼图图片,还有像背景图、拼图块这些相关数据。/check
接口:用来验证用户滑动的结果,比如拼图坐标对不对,然后返回验证成不成功。
- 请求与响应:
- 请求体用
CaptchaVO
来装前端传过来的参数,像验证码ID、滑动坐标这些。 - 响应的时候,用
ServerResponseEntity
包装ResponseModel
,统一返回格式,这样前后端交互起来就特别方便。
- 请求体用
- 注解说明:
@RestController
:这是告诉程序,这个类是个RESTful风格的控制器,返回的数据都是JSON格式的。@RequestMapping("/ua/captcha")
:给验证码相关的接口统一设置了一个路径前缀,方便管理。@Api(tags = "验证码")
:这是Swagger的注解,能自动生成API文档,开发和测试的时候就很方便查看接口信息。
三、定义验证码DTO
为了让验证码能在认证流程里“工作”,咱们得定义一个数据传输对象,也就是DTO。这个CaptchaAuthenticationDTO
能把验证码的验证结果和认证参数“绑”在一起。
public class CaptchaAuthenticationDTO extends AuthenticationDTO { // 这个字段用来存验证码验证结果,前端调用/check接口后返回的验证令牌就存这儿 @ApiModelProperty(value = "验证码", required = true) private String captchaVerification; // 获取验证码验证结果 public String getCaptchaVerification() { return captchaVerification; } // 设置验证码验证结果 public void setCaptchaVerification(String captchaVerification) { this.captchaVerification = captchaVerification; } // 重写toString方法,方便打印对象信息 @Override public String toString() { return "CaptchaAuthenticationDTO{" + "captchaVerification='" + captchaVerification + ''' + "} " + super.toString(); } }
这里要注意:
- 继承
AuthenticationDTO
:CaptchaAuthenticationDTO
继承了基础认证DTO,这样既能复用原来的认证字段,比如用户名、密码,又能扩展出验证码字段,代码的复用性和扩展性都很强。 - 字段定义:
captchaVerification
专门用来存验证码验证结果,一般是前端验证完后传过来的验证令牌。 - Swagger注解:
@ApiModelProperty
是Swagger的注解,给字段加了描述,生成API文档的时候就能看到每个字段是干啥的了。
四、集成到认证流程
(一)前端调用
- 用户一打开登录页面,前端就赶紧调用
/ua/captcha/get
接口,把滑动验证码“请”出来。 - 用户滑动完成后,前端再调用
/ua/captcha/check
接口验证结果,拿到captchaVerification
这个验证令牌。
(二)后端验证
- 在认证接口,比如登录接口里,接收
CaptchaAuthenticationDTO
对象,里面就带着用户名、密码和验证码验证结果这些信息。 - 仔细检查
captchaVerification
是不是有效,如果无效,那就别往下走了,直接返回认证失败的提示。
@PostMapping("/login") public ServerResponseEntity login(@RequestBody CaptchaAuthenticationDTO dto) { // 调用captchaService的verification方法,验证验证码 ResponseModel response = captchaService.verification(dto.getCaptchaVerification()); // 如果验证没通过 if (!response.isSuccess()) { // 返回验证码验证失败的提示 return ServerResponseEntity.fail("验证码验证失败"); } // 验证码通过了,接着走用户名密码认证的逻辑 return ServerResponseEntity.success("登录成功"); }
五、总结
到这儿,咱们就成功在Auth模块里接入滑动验证码啦!关键步骤再给大家捋一遍:
- 用
@Bean
配置验证码服务,各种类型随便选,超灵活。 CaptchaController
把生成和验证接口都准备好了,用起来超方便。- 定义
CaptchaAuthenticationDTO
,让验证码能顺利融入认证流程。 - 在认证逻辑里严格验证验证码结果,给应用安全再加道“锁”。
希望这篇文章能帮到大家,要是在接入过程中有啥问题,欢迎在评论区留言交流!