这个dome案例参考:https://www.jianshu.com/p/fdafd4126c2e (进行了简化)
依赖
<dependency>
<groupId>com.github.penggle</groupId>
<artifactId>kaptcha</artifactId>
<version>2.3.2</version>
</dependency>
config:
package com.xxx.admin.config;
import com.google.code.kaptcha.impl.DefaultKaptcha;
import com.google.code.kaptcha.util.Config;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import java.util.Properties;
/**
* description: Captcha验证码配置类
* version: 1.0
* date:
* @author:
*
*/
@Configuration
public class CaptchaConfig {
/**
* 运算验证码器
* @return 返回运算验证码
*/
@Bean(name = "captchaProducerMath")
public DefaultKaptcha getKaptchaBeanMath() {
DefaultKaptcha defaultKaptcha = new DefaultKaptcha();
Properties properties = new Properties();
// 是否有边框 默认为true 我们可以自己设置yes,no
properties.setProperty("kaptcha.border", "no");
// 边框颜色 默认为Color.BLACK
properties.setProperty("kaptcha.border.color", "55,160,204");
// 验证码文本字符颜色 默认为Color.BLACK
properties.setProperty("kaptcha.textproducer.font.color", "blue");
// 背景渐变色,开始颜色
properties.setProperty("kaptcha.background.clear.from", "234,172,236");
// 背景渐变色,结束颜色
properties.setProperty("kaptcha.background.clear.to", "234,144,115");
// 验证码图片宽度 默认为200
properties.setProperty("kaptcha.image.width", "170");
// 验证码图片高度 默认为50
properties.setProperty("kaptcha.image.height", "60");
// 验证码文本字符大小 默认为40
properties.setProperty("kaptcha.textproducer.font.size", "35");
// KAPTCHA_SESSION_KEY
properties.setProperty("kaptcha.session.key", "kaptchaMathCode");
// --------------验证码文本生成器,这里需要设置成自己项目的包名----------------------
properties.setProperty("kaptcha.textproducer.impl", "com.chenyou.admin.config.KaptchaMathTextCreator");
// 验证码文本字符间距 默认为2
properties.setProperty("kaptcha.textproducer.char.space", "3");
// 验证码文本字符长度 默认为9
properties.setProperty("kaptcha.textproducer.char.length", "9");
// 验证码文本字体样式 默认为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", "243,79,67");
// 干扰实现类
// 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;
}
}
package com.xxx.admin.config;
import com.google.code.kaptcha.text.impl.DefaultTextCreator;
import java.util.Random;
/**
* @Description: 运算验证码
* -------------------
* @Author:
* @Date:
*/
public class KaptchaMathTextCreator extends DefaultTextCreator {
// 运算表达式及结果值
StringBuilder result = new StringBuilder();
/**
* 获取运算验证码
* @return 返回运算验证码
*/
@Override
public String getText() {
Random random = new Random(System.currentTimeMillis());
int x = random.nextInt(20);
int y = random.nextInt(10);
int operationalRules = random.nextInt(4);
switch (operationalRules) {
case 0 : add(x, y); break;
case 1 : subtract(x, y); break;
case 2 : multiply(x, y); break;
//case 3 : divide(x, y); break;
default : multiply(x, y); break;
}
return result.toString();
}
/**
* 加法运算
* @param x 变量x
* @param y 变量y
*/
private void add(int x, int y) {
result.append(x);
result.append(" + ");
result.append(y);
result.append(" = ?@");
result.append(x + y);
}
/**
* 减法运算
* @param x 变量x
* @param y 变量y
*/
private void subtract(int x, int y) {
int max = Math.max(x, y);
int min = Math.min(x, y);
result.append(max);
result.append(" - ");
result.append(min);
result.append(" = ?@");
result.append(max - min);
}
/**
* 乘法运算
* @param x 变量x
* @param y 变量y
*/
private void multiply(int x, int y) {
int value = x * y;
result.append(x);
result.append(value > 100 ? " + " : " * ");
result.append(y);
result.append(" = ?@");
result.append(value > 100 ? x + y : x * y);
}
/**
* 除法运算
* @param x 变量x
* @param y 变量y
*/
private void divide(int x, int y) {
int max = Math.max(x, y);
int min = Math.min(x, y);
if (min == 0) {
multiply(max, min);
} else if(max % min == 0) {
result.append(max);
result.append(" / ");
result.append(min);
result.append(" = ?@");
result.append(max / min);
} else {
result.append(max);
result.append(" % ");
result.append(min);
result.append(" = ?@");
result.append(max % min);
}
}
}
调用实现:
/**
* 数值运算验证码
*/
@Autowired
private Producer captchaProducerMath;
/**
* 获取运算验证码
*
* @param
* @return 运算验证吗
* @throws ServiceException 查询运算验证码异常
*/
public JSONObject operationCodeVerification(Long uid){//这里uid只是作为标记
JSONObject returnJosn=new JSONObject();
StringBuffer img=new StringBuffer();
byte[] bytes = null;
String text = "";
BufferedImage bufferedImage = null;
try {
// 生成运算验证码文本
text = captchaProducerMath.createText();
String key=MD5Util.encode(text);
returnJosn.put("key",key);
//获取运算结果
String str1 = text.substring(0, text.indexOf("@"));
String str2 = text.substring(str1.length()+1, text.length());
//截取运算公式
String value = text.substring(0, text.lastIndexOf("@"));
// 生成运算验证码图片
bufferedImage = captchaProducerMath.createImage(value);
//将计算公式验证码写入redis
redisTemplate.opsForValue().set(uid+key,str2,5,TimeUnit.MINUTES);
// 在分布式应用中,可将session改为redis存储
ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
ImageIO.write(bufferedImage, "png", byteArrayOutputStream);
bytes = byteArrayOutputStream.toByteArray();
// 图片base64加密
img.append(Base64Utils.encodeToString(bytes));
} catch (IOException e) {
e.printStackTrace();
}
returnJosn.put("value",img.toString());
return returnJosn;
}