mirror of
http://git.pig4cloud.com/pig/pigx.git
synced 2026-11-08 20:49:00 +08:00
✨ Introducing new features. #1245 升级验证码实现支持 行为验证码
This commit is contained in:
1 parent
4725c30dfc
commit
6a28df8884
8 files changed
+160
-42
No files matched your search
+5
@@ -91,4 +91,9 @@ public interface CommonConstants {
|
||||
* 默认存储bucket
|
||||
*/
|
||||
String BUCKET_NAME = "lengleng";
|
||||
|
||||
/**
|
||||
* 滑块验证码
|
||||
*/
|
||||
String IMAGE_CODE_TYPE = "blockPuzzle";
|
||||
}
|
||||
@@ -59,8 +59,8 @@
|
||||
</dependency>
|
||||
<!--验证码-->
|
||||
<dependency>
|
||||
<groupId>com.github.whvcse</groupId>
|
||||
<artifactId>easy-captcha</artifactId>
|
||||
<groupId>com.github.anji-plus</groupId>
|
||||
<artifactId>captcha</artifactId>
|
||||
<version>${kaptcha.version}</version>
|
||||
</dependency>
|
||||
<!--hutool-->
|
||||
|
||||
+42
@@ -0,0 +1,42 @@
|
||||
package com.pig4cloud.pigx.gateway.config;
|
||||
|
||||
import com.anji.captcha.service.CaptchaCacheService;
|
||||
import lombok.AllArgsConstructor;
|
||||
import org.springframework.context.annotation.Primary;
|
||||
import org.springframework.data.redis.core.StringRedisTemplate;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import java.util.concurrent.TimeUnit;
|
||||
|
||||
/**
|
||||
* @author lengleng
|
||||
* @date 2020/5/19
|
||||
* <p>
|
||||
* 验证码 缓存提供支持集群
|
||||
*/
|
||||
@Primary
|
||||
@Component
|
||||
@AllArgsConstructor
|
||||
public class CaptchaCacheServiceProvider implements CaptchaCacheService {
|
||||
private final StringRedisTemplate stringRedisTemplate;
|
||||
|
||||
@Override
|
||||
public void set(String key, String value, long expiresInSeconds) {
|
||||
stringRedisTemplate.opsForValue().set(key, value, expiresInSeconds, TimeUnit.SECONDS);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean exists(String key) {
|
||||
return stringRedisTemplate.hasKey(key);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void delete(String key) {
|
||||
stringRedisTemplate.delete(key);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String get(String key) {
|
||||
return stringRedisTemplate.opsForValue().get(key);
|
||||
}
|
||||
}
|
||||
+6
-6
@@ -17,10 +17,7 @@
|
||||
|
||||
package com.pig4cloud.pigx.gateway.config;
|
||||
|
||||
import com.pig4cloud.pigx.gateway.handler.ImageCodeHandler;
|
||||
import com.pig4cloud.pigx.gateway.handler.SwaggerResourceHandler;
|
||||
import com.pig4cloud.pigx.gateway.handler.SwaggerSecurityHandler;
|
||||
import com.pig4cloud.pigx.gateway.handler.SwaggerUiHandler;
|
||||
import com.pig4cloud.pigx.gateway.handler.*;
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
@@ -39,16 +36,19 @@ import org.springframework.web.reactive.function.server.RouterFunctions;
|
||||
@Configuration
|
||||
@AllArgsConstructor
|
||||
public class RouterFunctionConfiguration {
|
||||
private final ImageCodeCheckHandler imageCodeCheckHandler;
|
||||
private final ImageCodeCreateHandler imageCodeCreateHandler;
|
||||
private final SwaggerResourceHandler swaggerResourceHandler;
|
||||
private final SwaggerSecurityHandler swaggerSecurityHandler;
|
||||
private final SwaggerUiHandler swaggerUiHandler;
|
||||
private final ImageCodeHandler imageCodeHandler;
|
||||
|
||||
@Bean
|
||||
public RouterFunction routerFunction() {
|
||||
return RouterFunctions.route(
|
||||
RequestPredicates.path("/code")
|
||||
.and(RequestPredicates.accept(MediaType.TEXT_PLAIN)), imageCodeHandler)
|
||||
.and(RequestPredicates.accept(MediaType.TEXT_PLAIN)), imageCodeCreateHandler)
|
||||
.andRoute(RequestPredicates.POST("/check")
|
||||
.and(RequestPredicates.accept(MediaType.ALL)), imageCodeCheckHandler)
|
||||
.andRoute(RequestPredicates.GET("/swagger-resources")
|
||||
.and(RequestPredicates.accept(MediaType.ALL)), swaggerResourceHandler)
|
||||
.andRoute(RequestPredicates.GET("/swagger-resources/configuration/ui")
|
||||
|
||||
+18
-2
@@ -18,13 +18,17 @@
|
||||
package com.pig4cloud.pigx.gateway.filter;
|
||||
|
||||
import cn.hutool.core.util.StrUtil;
|
||||
import com.anji.captcha.model.vo.CaptchaVO;
|
||||
import com.anji.captcha.service.CaptchaService;
|
||||
import com.fasterxml.jackson.core.JsonProcessingException;
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import com.pig4cloud.pigx.common.core.constant.CacheConstants;
|
||||
import com.pig4cloud.pigx.common.core.constant.CommonConstants;
|
||||
import com.pig4cloud.pigx.common.core.constant.SecurityConstants;
|
||||
import com.pig4cloud.pigx.common.core.constant.enums.LoginTypeEnum;
|
||||
import com.pig4cloud.pigx.common.core.exception.ValidateCodeException;
|
||||
import com.pig4cloud.pigx.common.core.util.R;
|
||||
import com.pig4cloud.pigx.common.core.util.SpringContextHolder;
|
||||
import com.pig4cloud.pigx.common.core.util.WebUtils;
|
||||
import com.pig4cloud.pigx.gateway.config.FilterIgnorePropertiesConfig;
|
||||
import lombok.AllArgsConstructor;
|
||||
@@ -44,8 +48,8 @@ import reactor.core.publisher.Mono;
|
||||
|
||||
/**
|
||||
* @author lengleng
|
||||
* @date 2018/7/4
|
||||
* 验证码处理
|
||||
* @date 2020/5/19
|
||||
* 登录逻辑验证码处理
|
||||
*/
|
||||
@Slf4j
|
||||
@Component
|
||||
@@ -125,6 +129,18 @@ public class ValidateCodeGatewayFilter extends AbstractGatewayFilterFactory {
|
||||
|
||||
String randomStr = request.getQueryParams().getFirst("randomStr");
|
||||
|
||||
// 若是滑块登录
|
||||
if (CommonConstants.IMAGE_CODE_TYPE.equalsIgnoreCase(randomStr)) {
|
||||
CaptchaService captchaService = SpringContextHolder.getBean(CaptchaService.class);
|
||||
CaptchaVO vo = new CaptchaVO();
|
||||
vo.setCaptchaVerification(code);
|
||||
if (!captchaService.verification(vo).isSuccess()) {
|
||||
throw new ValidateCodeException("验证码不能为空");
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
//https://gitee.com/log4j/pig/issues/IWA0D
|
||||
String mobile = request.getQueryParams().getFirst("mobile");
|
||||
if (StrUtil.isNotBlank(mobile)) {
|
||||
|
||||
+66
@@ -0,0 +1,66 @@
|
||||
/*
|
||||
* Copyright (c) 2018-2025, lengleng All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
*
|
||||
* Redistributions of source code must retain the above copyright notice,
|
||||
* this list of conditions and the following disclaimer.
|
||||
* Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* Neither the name of the pig4cloud.com developer nor the names of its
|
||||
* contributors may be used to endorse or promote products derived from
|
||||
* this software without specific prior written permission.
|
||||
* Author: lengleng (wangiegie@gmail.com)
|
||||
*/
|
||||
|
||||
package com.pig4cloud.pigx.gateway.handler;
|
||||
|
||||
import com.anji.captcha.model.common.ResponseModel;
|
||||
import com.anji.captcha.model.vo.CaptchaVO;
|
||||
import com.anji.captcha.service.CaptchaService;
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import com.pig4cloud.pigx.common.core.constant.CommonConstants;
|
||||
import com.pig4cloud.pigx.common.core.util.R;
|
||||
import com.pig4cloud.pigx.common.core.util.SpringContextHolder;
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.SneakyThrows;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.stereotype.Component;
|
||||
import org.springframework.web.reactive.function.BodyInserters;
|
||||
import org.springframework.web.reactive.function.server.HandlerFunction;
|
||||
import org.springframework.web.reactive.function.server.ServerRequest;
|
||||
import org.springframework.web.reactive.function.server.ServerResponse;
|
||||
import reactor.core.publisher.Mono;
|
||||
|
||||
/**
|
||||
* @author lengleng
|
||||
* @date 2020/5/19
|
||||
* 验证码生成逻辑处理类
|
||||
*/
|
||||
@Slf4j
|
||||
@Component
|
||||
@AllArgsConstructor
|
||||
public class ImageCodeCheckHandler implements HandlerFunction<ServerResponse> {
|
||||
private final ObjectMapper objectMapper;
|
||||
|
||||
|
||||
@Override
|
||||
@SneakyThrows
|
||||
public Mono<ServerResponse> handle(ServerRequest request) {
|
||||
CaptchaVO vo = new CaptchaVO();
|
||||
vo.setPointJson(request.queryParam("pointJson").get());
|
||||
vo.setToken(request.queryParam("token").get());
|
||||
vo.setCaptchaType(CommonConstants.IMAGE_CODE_TYPE);
|
||||
|
||||
CaptchaService captchaService = SpringContextHolder.getBean(CaptchaService.class);
|
||||
ResponseModel responseModel = captchaService.check(vo);
|
||||
|
||||
return ServerResponse.status(HttpStatus.OK)
|
||||
.contentType(MediaType.APPLICATION_JSON)
|
||||
.body(BodyInserters.fromValue(objectMapper.writeValueAsString(R.ok(responseModel))));
|
||||
}
|
||||
}
|
||||
+20
-31
@@ -17,58 +17,47 @@
|
||||
|
||||
package com.pig4cloud.pigx.gateway.handler;
|
||||
|
||||
import com.pig4cloud.pigx.common.core.constant.CacheConstants;
|
||||
import com.pig4cloud.pigx.common.core.constant.SecurityConstants;
|
||||
import com.wf.captcha.ArithmeticCaptcha;
|
||||
import com.anji.captcha.model.common.ResponseModel;
|
||||
import com.anji.captcha.model.vo.CaptchaVO;
|
||||
import com.anji.captcha.service.CaptchaService;
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import com.pig4cloud.pigx.common.core.constant.CommonConstants;
|
||||
import com.pig4cloud.pigx.common.core.util.R;
|
||||
import com.pig4cloud.pigx.common.core.util.SpringContextHolder;
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.SneakyThrows;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.springframework.core.io.ByteArrayResource;
|
||||
import org.springframework.data.redis.core.RedisTemplate;
|
||||
import org.springframework.data.redis.serializer.StringRedisSerializer;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.stereotype.Component;
|
||||
import org.springframework.util.FastByteArrayOutputStream;
|
||||
import org.springframework.web.reactive.function.BodyInserters;
|
||||
import org.springframework.web.reactive.function.server.HandlerFunction;
|
||||
import org.springframework.web.reactive.function.server.ServerRequest;
|
||||
import org.springframework.web.reactive.function.server.ServerResponse;
|
||||
import reactor.core.publisher.Mono;
|
||||
|
||||
import java.util.concurrent.TimeUnit;
|
||||
|
||||
/**
|
||||
* @author lengleng
|
||||
* @date 2018/7/5
|
||||
* @date 2020/5/19
|
||||
* 验证码生成逻辑处理类
|
||||
*/
|
||||
@Slf4j
|
||||
@Component
|
||||
@AllArgsConstructor
|
||||
public class ImageCodeHandler implements HandlerFunction<ServerResponse> {
|
||||
private static final Integer DEFAULT_IMAGE_WIDTH = 100;
|
||||
private static final Integer DEFAULT_IMAGE_HEIGHT = 40;
|
||||
private final RedisTemplate redisTemplate;
|
||||
public class ImageCodeCreateHandler implements HandlerFunction<ServerResponse> {
|
||||
private final ObjectMapper objectMapper;
|
||||
|
||||
|
||||
@Override
|
||||
@SneakyThrows
|
||||
public Mono<ServerResponse> handle(ServerRequest serverRequest) {
|
||||
ArithmeticCaptcha captcha = new ArithmeticCaptcha(DEFAULT_IMAGE_WIDTH, DEFAULT_IMAGE_HEIGHT);
|
||||
CaptchaVO vo = new CaptchaVO();
|
||||
vo.setCaptchaType(CommonConstants.IMAGE_CODE_TYPE);
|
||||
CaptchaService captchaService = SpringContextHolder.getBean(CaptchaService.class);
|
||||
ResponseModel responseModel = captchaService.get(vo);
|
||||
|
||||
String result = captcha.text();
|
||||
|
||||
//保存验证码信息
|
||||
String randomStr = serverRequest.queryParam("randomStr").get();
|
||||
redisTemplate.setKeySerializer(new StringRedisSerializer());
|
||||
redisTemplate.opsForValue().set(CacheConstants.DEFAULT_CODE_KEY + randomStr, result
|
||||
, SecurityConstants.CODE_TIME, TimeUnit.SECONDS);
|
||||
|
||||
// 转换流信息写出
|
||||
FastByteArrayOutputStream os = new FastByteArrayOutputStream();
|
||||
captcha.out(os);
|
||||
|
||||
return ServerResponse
|
||||
.status(HttpStatus.OK)
|
||||
.contentType(MediaType.IMAGE_JPEG)
|
||||
.body(BodyInserters.fromResource(new ByteArrayResource(os.toByteArray())));
|
||||
return ServerResponse.status(HttpStatus.OK)
|
||||
.contentType(MediaType.APPLICATION_JSON)
|
||||
.body(BodyInserters.fromValue(objectMapper.writeValueAsString(R.ok(responseModel))));
|
||||
}
|
||||
}
|
||||
@@ -41,7 +41,7 @@
|
||||
<maven.compiler.target>1.8</maven.compiler.target>
|
||||
<spring-boot-admin.version>2.2.3</spring-boot-admin.version>
|
||||
<hutool.version>5.3.3</hutool.version>
|
||||
<kaptcha.version>1.6.2</kaptcha.version>
|
||||
<kaptcha.version>1.1.8</kaptcha.version>
|
||||
<swagger.fox.version>2.9.2</swagger.fox.version>
|
||||
<knife4j.version>2.0.2</knife4j.version>
|
||||
<velocity.version>1.7</velocity.version>
|
||||
|
||||
Reference in new issue
Block a user