código de verificación Fórmula matemática
Esta parte es para explicar el incremento en el código de verificación funcional antes de conseguir el papel pico de dirección de dos cosas:
- Prevenir cepillo malicioso Botón máquina de pico
- La dispersión de una petición de usuario, el servidor de reducir al mismo tiempo la carga de procesamiento
proceso de código:
- Cuando se representa la primera página, si se puede vaciar en la etapa, usted tendrá que llamar a servicios de fondo para generar un código digital;
- Después de que el extremo posterior del código generado imagen de verificación, la respuesta en presencia de un redis (tiempo de configuración se 300S), la imagen vuelve a la parte delantera;
- Los usuarios tienen que rellenar el código de verificación en la página puede hacer clic en el botón "matar de inmediato." Después de hacer clic en el botón inmediatamente pico, pico en primer lugar conseguir un camino al azar, antes de obtener la ruta de acceso verificará primero el PIN es correcto;
- Verificación, adquirido de Redis, si es necesario para eliminar el código correcto en Redis en.
porción códigos Generación de
getMiaoshaVerifyCod método MiaoshaController de:
@RequestMapping(value = "/verifyCode", method = RequestMethod.GET)
@ResponseBody
public Result<String> getMiaoshaVerifyCod(HttpServletResponse response,@RequestParam("goodsId") long goodsId,
@CookieValue(value = MiaoshaUserService.COOKI_NAME_TOKEN,required = false) String cookieToken,
@RequestParam(value = MiaoshaUserService.COOKI_NAME_TOKEN,required = false) String paramToken) {
if (StringUtils.isEmpty(cookieToken) && StringUtils.isEmpty(paramToken)) {
return Result.error(CodeMsg.SESSION_ERROR);//token不存在或失效
}
String token = StringUtils.isEmpty(paramToken) ? cookieToken : paramToken;
MiaoshaUser user = userService.getByToken(response, token);//从token中读用户信息
try {
BufferedImage image = miaoshaService.createVerifyCode(user, goodsId);
OutputStream out = response.getOutputStream();
ImageIO.write(image, "JPEG", out);
out.flush();
out.close();
return null;
} catch (Exception e) {
e.printStackTrace();
return Result.error(CodeMsg.MIAOSHA_FAIL);
}
}
MiaoshaService código del método relevante:
public BufferedImage createVerifyCode(MiaoshaUser user, long goodsId) {
if (user == null || goodsId <= 0) {
return null;
}
int width = 80;
int height = 32;
//create the image
BufferedImage image = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
Graphics g = image.getGraphics();
// set the background color
g.setColor(new Color(0xDCDCDC));
g.fillRect(0, 0, width, height);
// draw the border
g.setColor(Color.black);
g.drawRect(0, 0, width - 1, height - 1);
// create a random instance to generate the codes
Random rdm = new Random();
// make some confusion
for (int i = 0; i < 50; i++) {
int x = rdm.nextInt(width);
int y = rdm.nextInt(height);
g.drawOval(x, y, 0, 0);
}
// generate a random code
String verifyCode = generateVerifyCode(rdm);
g.setColor(new Color(0, 100, 0));
g.setFont(new Font("Candara", Font.BOLD, 24));
g.drawString(verifyCode, 8, 24);
g.dispose();
//把验证码存到redis中
int rnd = calc(verifyCode);
redisService.set(MiaoshaKey.getMiaoshaVerifyCode, user.getId() + "," + goodsId, rnd);
//输出图片
return image;
}
private static char[] ops = new char[]{'+', '-', '*'};
/**
* + - *
*/
private String generateVerifyCode(Random rdm) {
int num1 = rdm.nextInt(10);
int num2 = rdm.nextInt(10);
int num3 = rdm.nextInt(10);
char op1 = ops[rdm.nextInt(3)];
char op2 = ops[rdm.nextInt(3)];
String exp = "" + num1 + op1 + num2 + op2 + num3;
return exp;
}
//计算验证码的值
private static int calc(String exp) {
try {
ScriptEngineManager manager = new ScriptEngineManager();
ScriptEngine engine = manager.getEngineByName("JavaScript");
return (Integer) engine.eval(exp);
} catch (Exception e) {
e.printStackTrace();
return 0;
}
}
porción de código Autenticación
porque está en frente de la trayectoria se determina para obtener el código de verificación pico aleatorio es correcta, y así el método MiaoshaController getMiaoshaPath sobre:
@RequestMapping(value = "/path", method = RequestMethod.GET)
@ResponseBody
public Result<String> getMiaoshaPath(HttpServletResponse response, @RequestParam("goodsId") long goodsId,
@CookieValue(value = MiaoshaUserService.COOKI_NAME_TOKEN,required = false) String cookieToken,
@RequestParam(value = MiaoshaUserService.COOKI_NAME_TOKEN,required = false) String paramToken,
@RequestParam(value = "verifyCode", defaultValue = "0") int verifyCode) {
if (StringUtils.isEmpty(cookieToken) && StringUtils.isEmpty(paramToken)) {
return Result.error(CodeMsg.SESSION_ERROR);//token不存在或失效
}
String token = StringUtils.isEmpty(paramToken) ? cookieToken : paramToken;
MiaoshaUser user = userService.getByToken(response, token);//从token中读用户信息
//验证码校验
boolean check = miaoshaService.checkVerifyCode(user, goodsId, verifyCode);
if (!check) {
return Result.error(CodeMsg.REQUEST_ILLEGAL);
}
String path = miaoshaService.createMiaoshaPath(user, goodsId);
return Result.success(path);
}
MiaoshaService código relevante:
public boolean checkVerifyCode(MiaoshaUser user, long goodsId, int verifyCode) {
if (user == null || goodsId <= 0) {
return false;
}
Integer codeOld = redisService.get(MiaoshaKey.getMiaoshaVerifyCode, user.getId() + "," + goodsId, Integer.class);
if (codeOld == null || codeOld - verifyCode != 0) {
return false;
}
redisService.delete(MiaoshaKey.getMiaoshaVerifyCode, user.getId() + "," + goodsId);
return true;
}