From 6ebe8da9b42e773f48260c6d1e0b90307bde5303 Mon Sep 17 00:00:00 2001 From: kongzy <kongzy> Date: 星期一, 27 十一月 2023 09:28:00 +0800 Subject: [PATCH] 增加验证码 --- assess-system/src/main/java/com/gkhy/assess/system/service/CaptchaService.java | 15 + assess-common/src/main/java/com/gkhy/assess/common/config/KaptchaTextCreator.java | 68 ++++++++ assess-framework/src/main/java/com/gkhy/assess/framework/config/DruidConfig.java | 2 assess-system/src/main/java/com/gkhy/assess/system/service/impl/SysUserServiceImpl.java | 29 +++ assess-common/src/main/java/com/gkhy/assess/common/domain/vo/LoginBody.java | 2 assess-admin/src/main/java/com/gkhy/assess/admin/controller/CaptchaController.java | 33 ++++ assess-common/pom.xml | 4 assess-framework/src/main/java/com/gkhy/assess/framework/shiro/ShiroConfig.java | 1 pom.xml | 8 + assess-common/src/main/java/com/gkhy/assess/common/constant/CacheConstant.java | 2 assess-common/src/main/java/com/gkhy/assess/common/config/CaptchaConfig.java | 84 ++++++++++ assess-framework/src/main/java/com/gkhy/assess/framework/interceptor/LogInterceptor.java | 2 assess-system/src/main/java/com/gkhy/assess/system/utils/ShiroUtils.java | 2 assess-system/src/main/java/com/gkhy/assess/system/service/impl/CaptchaServiceImpl.java | 60 +++++++ assess-system/src/main/java/com/gkhy/assess/system/domain/vo/CaptchaVO.java | 14 + assess-framework/src/main/java/com/gkhy/assess/framework/aop/LogAspect.java | 130 ++++++++++++++++ 16 files changed, 453 insertions(+), 3 deletions(-) diff --git a/assess-admin/src/main/java/com/gkhy/assess/admin/controller/CaptchaController.java b/assess-admin/src/main/java/com/gkhy/assess/admin/controller/CaptchaController.java new file mode 100644 index 0000000..18b4e2e --- /dev/null +++ b/assess-admin/src/main/java/com/gkhy/assess/admin/controller/CaptchaController.java @@ -0,0 +1,33 @@ +package com.gkhy.assess.admin.controller; + +import com.gkhy.assess.common.api.CommonResult; +import com.gkhy.assess.system.service.CaptchaService; +import io.swagger.annotations.Api; +import io.swagger.annotations.ApiOperation; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.web.bind.annotation.GetMapping; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RestController; + +/** + * 验证码操作处理 + * + * @author ruoyi + */ +@Api(tags = "验证码前端控制器") +@RestController +@RequestMapping("/system/captcha") +public class CaptchaController +{ + @Autowired + private CaptchaService captchaService; + /** + * 生成验证码 + */ + @ApiOperation(value = "生成验证码") + @GetMapping("/captchaImage") + public CommonResult captchaImage() + { + return CommonResult.success(captchaService.captchaImage()); + } +} diff --git a/assess-common/pom.xml b/assess-common/pom.xml index 1da62fb..78cd94b 100644 --- a/assess-common/pom.xml +++ b/assess-common/pom.xml @@ -107,6 +107,10 @@ <groupId>com.github.ben-manes.caffeine</groupId> <artifactId>caffeine</artifactId> </dependency> + <dependency> + <groupId>com.github.penggle</groupId> + <artifactId>kaptcha</artifactId> + </dependency> </dependencies> </project> \ No newline at end of file diff --git a/assess-common/src/main/java/com/gkhy/assess/common/config/CaptchaConfig.java b/assess-common/src/main/java/com/gkhy/assess/common/config/CaptchaConfig.java new file mode 100644 index 0000000..35d2fe4 --- /dev/null +++ b/assess-common/src/main/java/com/gkhy/assess/common/config/CaptchaConfig.java @@ -0,0 +1,84 @@ +package com.gkhy.assess.common.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; + +import static com.google.code.kaptcha.Constants.*; + +/** + * 验证码配置 + * + */ +@Configuration +public class CaptchaConfig +{ + @Bean(name = "captchaProducer") + public DefaultKaptcha getKaptchaBean() + { + DefaultKaptcha defaultKaptcha = new DefaultKaptcha(); + Properties properties = new Properties(); + // 是否有边框 默认为true 我们可以自己设置yes,no + properties.setProperty(KAPTCHA_BORDER, "yes"); + // 验证码文本字符颜色 默认为Color.BLACK + properties.setProperty(KAPTCHA_TEXTPRODUCER_FONT_COLOR, "black"); + // 验证码图片宽度 默认为200 + properties.setProperty(KAPTCHA_IMAGE_WIDTH, "160"); + // 验证码图片高度 默认为50 + properties.setProperty(KAPTCHA_IMAGE_HEIGHT, "60"); + // 验证码文本字符大小 默认为40 + properties.setProperty(KAPTCHA_TEXTPRODUCER_FONT_SIZE, "38"); + // KAPTCHA_SESSION_KEY + properties.setProperty(KAPTCHA_SESSION_CONFIG_KEY, "kaptchaCode"); + // 验证码文本字符长度 默认为5 + properties.setProperty(KAPTCHA_TEXTPRODUCER_CHAR_LENGTH, "4"); + // 验证码文本字体样式 默认为new Font("Arial", 1, fontSize), new Font("Courier", 1, fontSize) + properties.setProperty(KAPTCHA_TEXTPRODUCER_FONT_NAMES, "Arial,Courier"); + // 图片样式 水纹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; + } + + @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_CONFIG_KEY, "kaptchaCodeMath"); + // 验证码文本生成器 + properties.setProperty(KAPTCHA_TEXTPRODUCER_IMPL, "com.gkhy.assess.common.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; + } +} diff --git a/assess-common/src/main/java/com/gkhy/assess/common/config/KaptchaTextCreator.java b/assess-common/src/main/java/com/gkhy/assess/common/config/KaptchaTextCreator.java new file mode 100644 index 0000000..0678e70 --- /dev/null +++ b/assess-common/src/main/java/com/gkhy/assess/common/config/KaptchaTextCreator.java @@ -0,0 +1,68 @@ +package com.gkhy.assess.common.config; + +import com.google.code.kaptcha.text.impl.DefaultTextCreator; + +import java.util.Random; + +/** + * 验证码文本生成器 + * + */ +public class KaptchaTextCreator extends DefaultTextCreator +{ + private static final String[] CNUMBERS = "0,1,2,3,4,5,6,7,8,9,10".split(","); + + @Override + public String getText() + { + Integer result = 0; + Random random = new Random(); + int x = random.nextInt(10); + int y = random.nextInt(10); + StringBuilder suChinese = new StringBuilder(); + int randomoperands = random.nextInt(3); + if (randomoperands == 0) + { + result = x * y; + suChinese.append(CNUMBERS[x]); + suChinese.append("*"); + suChinese.append(CNUMBERS[y]); + } + else if (randomoperands == 1) + { + if ((x != 0) && y % x == 0) + { + result = y / x; + suChinese.append(CNUMBERS[y]); + suChinese.append("/"); + suChinese.append(CNUMBERS[x]); + } + else + { + result = x + y; + suChinese.append(CNUMBERS[x]); + suChinese.append("+"); + suChinese.append(CNUMBERS[y]); + } + } + else + { + if (x >= y) + { + result = x - y; + suChinese.append(CNUMBERS[x]); + suChinese.append("-"); + suChinese.append(CNUMBERS[y]); + } + else + { + result = y - x; + suChinese.append(CNUMBERS[y]); + suChinese.append("-"); + suChinese.append(CNUMBERS[x]); + } + } + suChinese.append("=?@" + result); + return suChinese.toString(); + } +} \ No newline at end of file diff --git a/assess-common/src/main/java/com/gkhy/assess/common/constant/CacheConstant.java b/assess-common/src/main/java/com/gkhy/assess/common/constant/CacheConstant.java index e619920..053462c 100644 --- a/assess-common/src/main/java/com/gkhy/assess/common/constant/CacheConstant.java +++ b/assess-common/src/main/java/com/gkhy/assess/common/constant/CacheConstant.java @@ -11,6 +11,8 @@ String SYS_CONFIG_KEY = "sys_config:"; + String CAPTCHA_CODE_KEY = "captcha_codes:"; + diff --git a/assess-common/src/main/java/com/gkhy/assess/common/domain/vo/LoginBody.java b/assess-common/src/main/java/com/gkhy/assess/common/domain/vo/LoginBody.java index 6765e9a..2910ef7 100644 --- a/assess-common/src/main/java/com/gkhy/assess/common/domain/vo/LoginBody.java +++ b/assess-common/src/main/java/com/gkhy/assess/common/domain/vo/LoginBody.java @@ -19,6 +19,6 @@ private String password; @ApiModelProperty(value = "验证码",required = false) private String code; - @ApiModelProperty(value = "唯一标识",required = false) + @ApiModelProperty(value = "验证码唯一标识",required = false) private String uuid; } diff --git a/assess-framework/src/main/java/com/gkhy/assess/framework/aop/LogAspect.java b/assess-framework/src/main/java/com/gkhy/assess/framework/aop/LogAspect.java new file mode 100644 index 0000000..41fed63 --- /dev/null +++ b/assess-framework/src/main/java/com/gkhy/assess/framework/aop/LogAspect.java @@ -0,0 +1,130 @@ +package com.gkhy.assess.framework.aop; + +import cn.hutool.core.util.StrUtil; +import cn.hutool.core.util.URLUtil; +import cn.hutool.extra.servlet.ServletUtil; +import cn.hutool.json.JSONObject; +import com.gkhy.assess.system.utils.ShiroUtils; +import lombok.extern.slf4j.Slf4j; +import org.aspectj.lang.JoinPoint; +import org.aspectj.lang.ProceedingJoinPoint; +import org.aspectj.lang.Signature; +import org.aspectj.lang.annotation.AfterThrowing; +import org.aspectj.lang.annotation.Around; +import org.aspectj.lang.annotation.Aspect; +import org.aspectj.lang.annotation.Pointcut; +import org.aspectj.lang.reflect.MethodSignature; +import org.springframework.stereotype.Component; +import org.springframework.web.bind.annotation.RequestBody; +import org.springframework.web.bind.annotation.RequestParam; +import org.springframework.web.context.request.RequestContextHolder; +import org.springframework.web.context.request.ServletRequestAttributes; + +import javax.servlet.http.HttpServletRequest; +import java.lang.reflect.Method; +import java.lang.reflect.Parameter; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +@Aspect +@Component +@Slf4j +public class LogAspect { + @Pointcut("execution(public * com.gkhy.assess.*.controller..*.*(..))") + public void logPointCut(){ + + } + + /** + * 处理完请求后执行 + * + * @param joinPoint 切点 + */ + @Around("logPointCut()") + public Object doAround(ProceedingJoinPoint joinPoint) throws Throwable{ + long startTime = System.currentTimeMillis(); + //获取当前请求对象 + ServletRequestAttributes attributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes(); + HttpServletRequest request = attributes.getRequest(); + Signature signature = joinPoint.getSignature(); + MethodSignature methodSignature = (MethodSignature) signature; + Method method = methodSignature.getMethod(); + StringBuffer requestURL = request.getRequestURL(); + JSONObject webLog = new JSONObject(); + String urlStr = request.getRequestURL().toString(); + webLog.put("basePath",StrUtil.removeSuffix(urlStr, URLUtil.url(urlStr).getPath())); + webLog.put("ip", ServletUtil.getClientIP(request,null)); + webLog.put("method",request.getMethod()); + Object params=getParameter(method, joinPoint.getArgs()); + webLog.put("parameter",params); + webLog.put("uri",request.getRequestURI()); + webLog.put("url",requestURL.toString()); + String userId=ShiroUtils.getUserId()!=null?String.valueOf(ShiroUtils.getUserId()):""; + webLog.put("userId",userId); + log.info(webLog.toString()); + Object result = joinPoint.proceed(); + if (result == null) { + //如果切到了 没有返回类型的void方法,这里直接返回 + return null; + } + long endTime = System.currentTimeMillis(); + webLog.put("result",result); + webLog.put("spendTime",endTime - startTime); + log.info(webLog.toString()); + return result; + } + + /** + * 拦截异常操作 + * + * @param joinPoint 切点 + * @param e 异常 + */ + @AfterThrowing(value = "logPointCut()", throwing = "e") + public void doAfterThrowing(JoinPoint joinPoint, Exception e) + { + //获取当前请求对象 + ServletRequestAttributes attributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes(); + HttpServletRequest request = attributes.getRequest(); + String urlStr = request.getRequestURL().toString(); + log.error("@AfterThrowing异常通知:url={},出错了error_message={}", urlStr,e.getMessage()); + } + + + + /** + * 根据方法和传入的参数获取请求参数 + */ + private Object getParameter(Method method, Object[] args) { + List<Object> argList = new ArrayList<>(); + Parameter[] parameters = method.getParameters(); + for (int i = 0; i < parameters.length; i++) { + //将RequestBody注解修饰的参数作为请求参数 + RequestBody requestBody = parameters[i].getAnnotation(RequestBody.class); + if (requestBody != null) { + argList.add(args[i]); + } + //将RequestParam注解修饰的参数作为请求参数 + RequestParam requestParam = parameters[i].getAnnotation(RequestParam.class); + if (requestParam != null) { + Map<String, Object> map = new HashMap<>(); + String key = parameters[i].getName(); + if (StrUtil.isNotEmpty(requestParam.value())) { + key = requestParam.value(); + } + map.put(key, args[i]); + argList.add(map); + } + } + if (argList.size() == 0) { + return null; + } else if (argList.size() == 1) { + return argList.get(0); + } else { + return argList; + } + } + +} diff --git a/assess-framework/src/main/java/com/gkhy/assess/framework/config/DruidConfig.java b/assess-framework/src/main/java/com/gkhy/assess/framework/config/DruidConfig.java index c3aa3c5..ff4fa0a 100644 --- a/assess-framework/src/main/java/com/gkhy/assess/framework/config/DruidConfig.java +++ b/assess-framework/src/main/java/com/gkhy/assess/framework/config/DruidConfig.java @@ -80,6 +80,7 @@ String commonJsPattern=pattern.replaceAll("\\*","js/common.js"); final String filePath="support/http/resources/js/common.js"; Filter filter=new Filter() { + @Override public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException { filterChain.doFilter(servletRequest,servletResponse); @@ -91,6 +92,7 @@ text=text.replaceAll("powered.*?shrek.wang</a>",""); servletResponse.getWriter().write(text); } + }; diff --git a/assess-framework/src/main/java/com/gkhy/assess/framework/interceptor/LogInterceptor.java b/assess-framework/src/main/java/com/gkhy/assess/framework/interceptor/LogInterceptor.java index db4a372..03740b0 100644 --- a/assess-framework/src/main/java/com/gkhy/assess/framework/interceptor/LogInterceptor.java +++ b/assess-framework/src/main/java/com/gkhy/assess/framework/interceptor/LogInterceptor.java @@ -26,7 +26,7 @@ MDC.put("requestId", requestId); MDC.put("clientIP", ip); MDC.put("url", url); - String userId= String.valueOf(ShiroUtils.getUserId()); + String userId= ShiroUtils.getUserId()!=null?String.valueOf(ShiroUtils.getUserId()):""; MDC.put("userId", userId); return true; } diff --git a/assess-framework/src/main/java/com/gkhy/assess/framework/shiro/ShiroConfig.java b/assess-framework/src/main/java/com/gkhy/assess/framework/shiro/ShiroConfig.java index a594680..1e30371 100644 --- a/assess-framework/src/main/java/com/gkhy/assess/framework/shiro/ShiroConfig.java +++ b/assess-framework/src/main/java/com/gkhy/assess/framework/shiro/ShiroConfig.java @@ -75,6 +75,7 @@ chain.addPathDefinition("/system/agency/getAgencyById","anon"); chain.addPathDefinition("/system/user/agencyRegister","anon"); + chain.addPathDefinition("/system/captcha/captchaImage","anon"); //除了以上的请求外,其它请求都需要登录 chain.addPathDefinition("/**", "jwtFilter,authc"); // 需登录才能访问 diff --git a/assess-system/src/main/java/com/gkhy/assess/system/domain/vo/CaptchaVO.java b/assess-system/src/main/java/com/gkhy/assess/system/domain/vo/CaptchaVO.java new file mode 100644 index 0000000..c9db5d6 --- /dev/null +++ b/assess-system/src/main/java/com/gkhy/assess/system/domain/vo/CaptchaVO.java @@ -0,0 +1,14 @@ +package com.gkhy.assess.system.domain.vo; + +import io.swagger.annotations.ApiModel; +import io.swagger.annotations.ApiModelProperty; +import lombok.Data; + +@Data +@ApiModel(value = "验证码对象", description = "验证码对象") +public class CaptchaVO { + @ApiModelProperty("唯一标识") + private String uuid; + @ApiModelProperty("验证码图片内容,base64") + private String image; +} diff --git a/assess-system/src/main/java/com/gkhy/assess/system/service/CaptchaService.java b/assess-system/src/main/java/com/gkhy/assess/system/service/CaptchaService.java new file mode 100644 index 0000000..9361b00 --- /dev/null +++ b/assess-system/src/main/java/com/gkhy/assess/system/service/CaptchaService.java @@ -0,0 +1,15 @@ +package com.gkhy.assess.system.service; + +import com.gkhy.assess.system.domain.vo.CaptchaVO; + +import java.awt.image.BufferedImage; + +public interface CaptchaService { + + /** + * 生成验证码图片 + * @return + */ + CaptchaVO captchaImage(); + +} diff --git a/assess-system/src/main/java/com/gkhy/assess/system/service/impl/CaptchaServiceImpl.java b/assess-system/src/main/java/com/gkhy/assess/system/service/impl/CaptchaServiceImpl.java new file mode 100644 index 0000000..f128fef --- /dev/null +++ b/assess-system/src/main/java/com/gkhy/assess/system/service/impl/CaptchaServiceImpl.java @@ -0,0 +1,60 @@ +package com.gkhy.assess.system.service.impl; + +import cn.hutool.core.codec.Base64; +import com.gkhy.assess.common.constant.CacheConstant; +import com.gkhy.assess.common.exception.ApiException; +import com.gkhy.assess.common.utils.RedisUtils; +import com.gkhy.assess.system.domain.vo.CaptchaVO; +import com.gkhy.assess.system.service.CaptchaService; +import com.google.code.kaptcha.Producer; +import lombok.extern.slf4j.Slf4j; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.util.FastByteArrayOutputStream; + +import javax.annotation.Resource; +import javax.imageio.ImageIO; +import java.awt.image.BufferedImage; +import java.io.IOException; +import java.util.UUID; +import java.util.concurrent.TimeUnit; + +@Slf4j +@Service +public class CaptchaServiceImpl implements CaptchaService { + @Resource(name = "captchaProducer") + private Producer captchaProducer; + + @Resource(name = "captchaProducerMath") + private Producer captchaProducerMath; + @Autowired + private RedisUtils redisUtils; + + @Override + public CaptchaVO captchaImage() { + String uuid= UUID.randomUUID().toString(); + String verifyKey= CacheConstant.CAPTCHA_CODE_KEY+uuid; + String capText=captchaProducerMath.createText(); + String capStr=capText.substring(0,capText.lastIndexOf("@")); + String code=capText.substring(capText.lastIndexOf("@")+1); + BufferedImage image=captchaProducerMath.createImage(capStr); + redisUtils.set(verifyKey,code,2, TimeUnit.MINUTES); + // 转换流信息写出 + FastByteArrayOutputStream os = new FastByteArrayOutputStream(); + try + { + ImageIO.write(image, "jpg", os); + } + catch (IOException e) + { + log.error(e.getMessage()); + throw new ApiException("生成验证码失败"); + } + CaptchaVO captchaVO=new CaptchaVO(); + captchaVO.setUuid(uuid); + captchaVO.setImage(Base64.encode(os.toByteArray())); + return captchaVO; + } + + +} diff --git a/assess-system/src/main/java/com/gkhy/assess/system/service/impl/SysUserServiceImpl.java b/assess-system/src/main/java/com/gkhy/assess/system/service/impl/SysUserServiceImpl.java index 9bfc0cd..6ceaac1 100644 --- a/assess-system/src/main/java/com/gkhy/assess/system/service/impl/SysUserServiceImpl.java +++ b/assess-system/src/main/java/com/gkhy/assess/system/service/impl/SysUserServiceImpl.java @@ -1,6 +1,7 @@ package com.gkhy.assess.system.service.impl; import cn.hutool.core.util.ObjectUtil; +import cn.hutool.core.util.StrUtil; import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; import com.gkhy.assess.common.api.CommonPage; import com.gkhy.assess.common.constant.CacheConstant; @@ -57,6 +58,8 @@ @Override public AccountVO login(LoginBody loginBody) { + // 验证码校验 + validateCaptcha(loginBody.getUsername(), loginBody.getCode(), loginBody.getUuid()); UsernamePasswordToken usernamePasswordToken = new UsernamePasswordToken(loginBody.getUsername(), loginBody.getPassword(), false); Subject subject= SecurityUtils.getSubject(); String msg ; @@ -84,6 +87,32 @@ } } + /** + * 校验验证码 + * + * @param username 用户名 + * @param code 验证码 + * @param uuid 唯一标识 + * @return 结果 + */ + public void validateCaptcha(String username, String code, String uuid) + { + if(StrUtil.isBlank(code)||StrUtil.isBlank(uuid)){ + throw new ApiException("验证码或验证码标识为空"); + } + String verifyKey = CacheConstant.CAPTCHA_CODE_KEY +uuid; + String captcha = (String) redisUtils.get(verifyKey); + redisUtils.del(verifyKey); + if (StrUtil.isBlank(captcha)) + { + throw new ApiException("验证码已失效"); + } + if (!code.equalsIgnoreCase(captcha)) + { + throw new ApiException("验证码不正确"); + } + } + @Override public void logout() { String jwtToken = request.getHeader(JwtTokenUtil.USER_LOGIN_TOKEN); diff --git a/assess-system/src/main/java/com/gkhy/assess/system/utils/ShiroUtils.java b/assess-system/src/main/java/com/gkhy/assess/system/utils/ShiroUtils.java index 682c61b..4fcd1bf 100644 --- a/assess-system/src/main/java/com/gkhy/assess/system/utils/ShiroUtils.java +++ b/assess-system/src/main/java/com/gkhy/assess/system/utils/ShiroUtils.java @@ -25,7 +25,7 @@ public static Long getUserId() { - return getSysUser().getId().longValue(); + return getSysUser()!=null?getSysUser().getId().longValue():null; } public static SysUser getSysUser() diff --git a/pom.xml b/pom.xml index 82664af..ea92af6 100644 --- a/pom.xml +++ b/pom.xml @@ -39,6 +39,7 @@ <java-jwt.version>3.11.0</java-jwt.version> <fastjson.version>1.2.76</fastjson.version> <caffeine.version>2.9.3</caffeine.version> + <kaptcha.version>2.3.2</kaptcha.version> </properties> <dependencyManagement> <dependencies> @@ -143,6 +144,13 @@ <version>${caffeine.version}</version> </dependency> + <!-- 验证码 --> + <dependency> + <groupId>com.github.penggle</groupId> + <artifactId>kaptcha</artifactId> + <version>${kaptcha.version}</version> + </dependency> + </dependencies> </dependencyManagement> -- Gitblit v1.9.2