【注意】:适用与springboot项目
1.加载jar包。由于groupId的不同,图片验证码的样式会有所不同
<!--计算类型的验证码 -->
<dependency>
<groupId>com.github.penggle</groupId>
<artifactId>kaptcha</artifactId>
<version>${kaptcha.version}</version>
</dependency>
//-----------分割线---------------------
<!-- 6位数字的验证码-->
<dependency>
<groupId>com.github.axet</groupId>
<artifactId>kaptcha</artifactId>
<version>${kaptcha.version}</version>
</dependency>
2.配置kaptcha,在配置类中配置
- 计算类型验证码的配置类
@Configuration
public class CaptchaConfig
{
@Bean(name = "captchaProducerMath")
public DefaultKaptcha getKaptchaBeanMath()
{
DefaultKaptcha defaultKaptcha = new DefaultKaptcha();
Properties properties = new Properties();
// 是否有边框 默认为true 我们可以自己设置yes,no
properties.setProperty("kaptcha.border", "yes");
// 边框颜色 默认为Color.BLACK
properties.setProperty("kaptcha.border.color", "105,179,90");
// 验证码文本字符颜色 默认为Color.BLACK
properties.setProperty("kaptcha.textproducer.font.color", "blue");
// 验证码图片宽度 默认为200
properties.setProperty("kaptcha.image.width", "160");
// 验证码图片高度 默认为50
properties.setProperty("kaptcha.image.height", "60");
// 验证码文本字符大小 默认为40
properties.setProperty("kaptcha.textproducer.font.size", "35");
// KAPTCHA_SESSION_KEY
properties.setProperty("kaptcha.session.key", "kaptchaCodeMath");
// 验证码文本生成器
properties.setProperty("kaptcha.textproducer.impl", "com.ruoyi.gateway.config.KaptchaTextCreator");
// 验证码文本字符间距 默认为2
properties.setProperty("kaptcha.textproducer.char.space", "3");
// 验证码文本字符长度 默认为5
properties.setProperty("kaptcha.textproducer.char.length", "6");
// 验证码文本字体样式 默认为new Font("Arial", 1, fontSize), new Font("Courier", 1,
// fontSize)
properties.setProperty("kaptcha.textproducer.font.names", "Arial,Courier");
// 验证码噪点颜色 默认为Color.BLACK
properties.setProperty("kaptcha.noise.color", "white");
// 干扰实现类
properties.setProperty("kaptcha.noise.impl", "com.google.code.kaptcha.impl.NoNoise");
// 图片样式 水纹com.google.code.kaptcha.impl.WaterRipple
// 鱼眼com.google.code.kaptcha.impl.FishEyeGimpy
// 阴影com.google.code.kaptcha.impl.ShadowGimpy
properties.setProperty("kaptcha.obscurificator.impl", "com.google.code.kaptcha.impl.ShadowGimpy");
Config config = new Config(properties);
defaultKaptcha.setConfig(config);
return defaultKaptcha;
}
}
- 6位数字的验证码的配置类
@Configuration
public class KaptchaConfig {
@Bean
public DefaultKaptcha producer() {
Properties properties = new Properties();
properties.put("kaptcha.border", "no");
properties.put("kaptcha.textproducer.font.color", "black");
properties.put("kaptcha.textproducer.char.space", "5");
Config config = new Config(properties);
DefaultKaptcha defaultKaptcha = new DefaultKaptcha();
defaultKaptcha.setConfig(config);
return defaultKaptcha;
}
}
3.生成验证码并且获取
- 图一的
@Slf4j
@Component
@AllArgsConstructor
public class ImgCodeHandler implements HandlerFunction<ServerResponse>
{
private final Producer producer;
private final StringRedisTemplate redisTemplate;
@Override
public Mono<ServerResponse> handle(ServerRequest serverRequest)
{
// 生成验证码
String capText = producer.createText();
String capStr = capText.substring(0, capText.lastIndexOf("@"));
String code = capText.substring(capText.lastIndexOf("@") + 1);
BufferedImage image = producer.createImage(capStr);
// 保存验证码信息
String randomStr = UUID.randomUUID().toString().replaceAll("-", "");
redisTemplate.opsForValue().set(Constants.DEFAULT_CODE_KEY + randomStr, code, 60, TimeUnit.SECONDS);
// 转换流信息写出
FastByteArrayOutputStream os = new FastByteArrayOutputStream();
try
{
ImageIO.write(image, "jpg", os);
}
catch (IOException e)
{
log.error("ImageIO write err", e);
return Mono.error(e);
}
return ServerResponse.status(HttpStatus.OK).contentType(MediaType.IMAGE_JPEG).header("randomstr", randomStr)
.body(BodyInserters.fromResource(new ByteArrayResource(os.toByteArray())));
}
}
- 图二的
@GetMapping("captcha.jpg")
public void captcha(HttpServletResponse response) throws ServletException, IOException {
response.setHeader("Cache-Control", "no-store, no-cache");
response.setContentType("image/jpeg");
// 生成文字验证码
String text = producer.createText();
// 生成图片验证码
BufferedImage image = producer.createImage(text);
// 保存到验证码到 session
ShiroUtils.setSessionAttribute(Constants.KAPTCHA_SESSION_KEY, text);
ServletOutputStream out = response.getOutputStream();
ImageIO.write(image, "jpg", out);
IOUtils.closeQuietly(out);
}
4.登录接口增加验证码验证
- 图一的
暂无 - 图二的
/**
* 登录接口
*/
@PostMapping(value = "/login")
public HttpResult login(@RequestBody LoginBean loginBean) throws IOException {
String userName = loginBean.getAccount();
String password = loginBean.getPassword();
String captcha = loginBean.getCaptcha();
// 从session中获取之前保存的验证码跟前台传来的验证码进行匹配
Object kaptcha = ShiroUtils.getSessionAttribute(Constants.KAPTCHA_SESSION_KEY);
if(kaptcha == null){
return HttpResult.error("验证码已失效");
}
if(!captcha.equals(kaptcha)){
return HttpResult.error("验证码不正确");
}
// 用户信息
SysUser user = sysUserService.findByName(userName);
// 账号不存在、密码错误
if (user == null) {
return HttpResult.error("账号不存在");
}
if (!match(user, password)) {
return HttpResult.error("密码不正确");
}
// 账号锁定
if (user.getStatus() == 0) {
return HttpResult.error("账号已被锁定,请联系管理员");
}
// 生成token,并保存到数据库
SysUserToken data = sysUserTokenService.createToken(user.getId());
return HttpResult.ok(data);
}