diff --git a/ruoyi-admin/src/main/java/com/ruoyi/web/controller/cai/app/AuthAppController.java b/ruoyi-admin/src/main/java/com/ruoyi/web/controller/cai/app/AuthAppController.java index 636656d1..3c4ec1d3 100644 --- a/ruoyi-admin/src/main/java/com/ruoyi/web/controller/cai/app/AuthAppController.java +++ b/ruoyi-admin/src/main/java/com/ruoyi/web/controller/cai/app/AuthAppController.java @@ -3,6 +3,7 @@ package com.ruoyi.web.controller.cai.app; import cn.dev33.satoken.annotation.SaIgnore; import cn.hutool.core.util.PhoneUtil; import com.ruoyi.cai.auth.*; +import com.ruoyi.cai.constant.RedisHttpConstant; import com.ruoyi.cai.dto.app.vo.LoginVo; import com.ruoyi.cai.enums.CodeEnum; import com.ruoyi.cai.enums.SystemConfigEnum; @@ -17,11 +18,15 @@ import com.ruoyi.cai.service.UserService; import com.ruoyi.common.annotation.Log; import com.ruoyi.common.core.domain.R; import com.ruoyi.common.enums.BusinessType; +import com.ruoyi.common.exception.ServiceException; import com.ruoyi.common.utils.ServletUtils; import com.ruoyi.common.utils.StringUtils; import io.swagger.v3.oas.annotations.Operation; import io.swagger.v3.oas.annotations.tags.Tag; import lombok.extern.slf4j.Slf4j; +import org.redisson.api.RAtomicLong; +import org.redisson.api.RedissonClient; +import org.redisson.client.RedisClient; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.validation.annotation.Validated; import org.springframework.web.bind.annotation.PostMapping; @@ -106,6 +111,7 @@ public class AuthAppController { } + @Deprecated @PostMapping("/register/code") @Operation(summary = "获取注册验证码") @Log(title = "获取注册验证码", businessType = BusinessType.OTHER, isSaveDb = false) @@ -143,6 +149,13 @@ public class AuthAppController { return R.fail(600,"9000009"); } ipBlackService.checkIpThrowException(ServletUtils.getClientIP()); + if(StringUtils.isBlank(code.getUserIp())){ + code.setUserIp(ServletUtils.getClientIP()); + } + boolean check = verificationCodeCheck.check(code.getTicket(), code.getUserIp(), code.getRandStr()); + if(!check){ + throw new ServiceException("图形验证码错误"); + } try { smsVerifyService.put(CodeEnum.RESET_PASSWORD,code.getMobile()); }catch (Exception e){ @@ -159,10 +172,69 @@ public class AuthAppController { @Autowired private IpBlackService ipBlackService; + + @PostMapping("/loginV2") + @Operation(summary = "登陆") + @Log(title = "登陆", businessType = BusinessType.OTHER, isSaveDb = false) + public R loginV2(@Validated @RequestBody LoginCaiUser loginBody){ + LoginVo vo = new LoginVo(); + ipBlackService.checkIpThrowException(ServletUtils.getClientIP()); + boolean needVerificationCode = this.checkNeedVerificationCode(loginBody); + if(needVerificationCode){ + vo.setLoginSuccess(false); + vo.setNeedVerificationCode(true); + return R.ok(); + } + try { + String token = caiLoginManager.login(loginBody.getUsername(), loginBody.getPassword()); + vo.setLoginSuccess(true); + vo.setToken(token); + vo.setUserInfo(currentUserManager.currentInfo()); + }catch (Exception e){ + loginAfterManager.loginAfter(loginBody,false,e.getMessage()); + ipRecordService.saveLoginIp(ServletUtils.getClientIP()); + throw e; + } + loginAfterManager.loginAfter(loginBody,true,"登录成功"); + return R.ok(vo); + } + + @Autowired + private RedissonClient redissonClient; + + private boolean checkNeedVerificationCode(LoginCaiUser loginBody){ + if(StringUtils.isNotEmpty(loginBody.getTicket()) || StringUtils.isNotEmpty(loginBody.getRandStr())){ + if(StringUtils.isBlank(loginBody.getUserIp())){ + loginBody.setUserIp(ServletUtils.getClientIP()); + } + boolean check = verificationCodeCheck.check(loginBody.getTicket(), loginBody.getUserIp(), loginBody.getRandStr()); + if(!check){ + throw new ServiceException("图形验证码错误"); + } + }else{ + Integer loginErrorOpenSecurity = systemConfigManager.getSystemConfigOfInt(SystemConfigEnum.LOGIN_ERROR_OPEN_SECURITY); + if(loginErrorOpenSecurity <= 0){ + return true; + } + String key = String.format(RedisHttpConstant.CHECK_LOGIN_NUM, loginBody.getUsername()); + RAtomicLong atomicLong = redissonClient.getAtomicLong(key); + if(atomicLong.get() >= loginErrorOpenSecurity){ + return true; + } + } + return false; + } + + + @PostMapping("/login") @Operation(summary = "登陆") @Log(title = "登陆", businessType = BusinessType.OTHER, isSaveDb = false) public R login(@Validated @RequestBody LoginCaiUser loginBody){ + boolean openOldLoginApi = systemConfigManager.getSystemConfigOfBool(SystemConfigEnum.OPEN_OLD_LOGIN_API); + if(!openOldLoginApi){ + return R.fail("404"); + } LoginVo vo = new LoginVo(); ipBlackService.checkIpThrowException(ServletUtils.getClientIP()); try { @@ -175,8 +247,6 @@ public class AuthAppController { throw e; } loginAfterManager.loginAfter(loginBody,true,"登录成功"); - // 异步调用通知 -// loginAfterManager.loginAfter(LoginHelper.getUserId()); return R.ok(vo); } diff --git a/ruoyi-cai/src/main/java/com/ruoyi/cai/auth/LoginCaiUser.java b/ruoyi-cai/src/main/java/com/ruoyi/cai/auth/LoginCaiUser.java index 7d63dd25..ae389b1f 100644 --- a/ruoyi-cai/src/main/java/com/ruoyi/cai/auth/LoginCaiUser.java +++ b/ruoyi-cai/src/main/java/com/ruoyi/cai/auth/LoginCaiUser.java @@ -14,4 +14,8 @@ public class LoginCaiUser { @Schema(description = "密码") @NotEmpty(message = "密码不能为空") private String password; + + private String ticket; + private String randStr; + private String userIp; } diff --git a/ruoyi-cai/src/main/java/com/ruoyi/cai/auth/RegisterCode.java b/ruoyi-cai/src/main/java/com/ruoyi/cai/auth/RegisterCode.java index d49842bf..438657db 100644 --- a/ruoyi-cai/src/main/java/com/ruoyi/cai/auth/RegisterCode.java +++ b/ruoyi-cai/src/main/java/com/ruoyi/cai/auth/RegisterCode.java @@ -8,4 +8,10 @@ import javax.validation.constraints.NotEmpty; public class RegisterCode { @NotEmpty(message = "手机号不能为空") private String mobile; + + @NotEmpty(message = "腾讯验证码参数[ticket]") + private String ticket; + @NotEmpty(message = "腾讯验证码所属参数[randStr]") + private String randStr; + private String userIp; } diff --git a/ruoyi-cai/src/main/java/com/ruoyi/cai/dto/app/vo/LoginVo.java b/ruoyi-cai/src/main/java/com/ruoyi/cai/dto/app/vo/LoginVo.java index 97230520..d108963f 100644 --- a/ruoyi-cai/src/main/java/com/ruoyi/cai/dto/app/vo/LoginVo.java +++ b/ruoyi-cai/src/main/java/com/ruoyi/cai/dto/app/vo/LoginVo.java @@ -4,6 +4,10 @@ import lombok.Data; @Data public class LoginVo { + // 是否登录成功 + private boolean loginSuccess; + // 是否需要图形验证码 + private boolean needVerificationCode; private String token; private CurrentUserInfoVo userInfo; } diff --git a/ruoyi-cai/src/main/java/com/ruoyi/cai/enums/SystemConfigEnum.java b/ruoyi-cai/src/main/java/com/ruoyi/cai/enums/SystemConfigEnum.java index 62cf2993..0a026ef7 100644 --- a/ruoyi-cai/src/main/java/com/ruoyi/cai/enums/SystemConfigEnum.java +++ b/ruoyi-cai/src/main/java/com/ruoyi/cai/enums/SystemConfigEnum.java @@ -16,6 +16,9 @@ public enum SystemConfigEnum { * 安全配置 */ OPEN_IP_NUMBER("5", "IP每日登录次数超过多少次封",SystemConfigGroupEnum.SECURITY), + LOGIN_ERROR_OPEN_SECURITY("2", "输入密码次数超过多少次开启图形验证码",SystemConfigGroupEnum.SECURITY), + // TODO 新台子改默认值 + OPEN_OLD_LOGIN_API("1", "开启旧版无验证码登录接口",SystemConfigGroupEnum.SECURITY), OPEN_IP_AUTO("1", "开启自动定时封IP",SystemConfigGroupEnum.SECURITY), OPEN_RESET_PASSWORD("1", "开启重置密码",SystemConfigGroupEnum.SECURITY, new BooleanSystemConfigCheck()), LOGIN_PASSWORD_ERROR_MAX_NUM("5", "登录输错密码上限",SystemConfigGroupEnum.SECURITY, new NumberSystemConfigCheck()),