用户模块

This commit is contained in:
chen-xin-zhi 2025-05-07 00:27:51 +08:00
parent ef88f4be1e
commit fa3612648b
17 changed files with 574 additions and 31 deletions

View File

@ -57,8 +57,8 @@ public class PermissionCheck {
// 接口的权限
String mustRole = requiresPermission.mustRole();
// 获取接口权限的枚举类
UserRoleEnum mustUserRoleEnum = UserRoleEnum.getEnumByValue(mustRole);
ThrowUtils.throwIf(mustUserRoleEnum == null, ErrorCode.NO_AUTH_ERROR);
UserRoleEnum interfaceRoleEnum = UserRoleEnum.getEnumByValue(mustRole);
ThrowUtils.throwIf(interfaceRoleEnum == null, ErrorCode.NO_AUTH_ERROR);
// 获取用户权限
String token = request.getHeader("Authorization");
ThrowUtils.throwIf(StringUtils.isBlank(token), ErrorCode.NO_AUTH_ERROR, "JWT为空");
@ -81,11 +81,11 @@ public class PermissionCheck {
String userRole = userInfo.getUserRole();
UserRoleEnum userRoleEnum = UserRoleEnum.getEnumByValue(userRole);
// 接口权限只能是 ADMIN 或者 BOSS用户权限是 ADMIN 或者 BOSSUSERBAN
// 接口权限只能是 USERADMINBOSS用户权限是 ADMINBOSSUSERBAN
// 校验角色
ThrowUtils.throwIf(UserRoleEnum.USER.equals(userRoleEnum), ErrorCode.NO_AUTH_ERROR);
ThrowUtils.throwIf(UserRoleEnum.USER.equals(userRoleEnum) && !UserRoleEnum.USER.equals(interfaceRoleEnum), ErrorCode.NO_AUTH_ERROR);
ThrowUtils.throwIf(UserRoleEnum.BAN.equals(userRoleEnum), ErrorCode.NO_AUTH_ERROR, "用户已被封禁");
ThrowUtils.throwIf(UserRoleEnum.ADMIN.equals(userRoleEnum) && UserRoleEnum.BOSS.equals(mustUserRoleEnum), ErrorCode.NO_AUTH_ERROR);
ThrowUtils.throwIf(UserRoleEnum.ADMIN.equals(userRoleEnum) && UserRoleEnum.BOSS.equals(interfaceRoleEnum), ErrorCode.NO_AUTH_ERROR);
return joinPoint.proceed();
}

View File

@ -0,0 +1,10 @@
package com.greenorange.promotion.constant;
public interface SystemConstant {
/**
* 验证码
*/
String VERIFICATION_CODE = "verificationCode";
}

View File

@ -62,7 +62,6 @@ public class FileInfoController {
*/
@PostMapping("upload")
@Operation(summary = "Web端文件上传服务器", description = "参数文件添加请求体权限管理员方法名addFileInfo")
@SysLog(title = "文件管理", content = "Web端文件上传(服务器)")
public BaseResponse<String> uploadFile(@RequestPart("file") MultipartFile multipartFile, UploadFileRequest uploadFileRequest) throws IOException{
// 校验文件
fileInfoService.validFile(multipartFile, uploadFileRequest);

View File

@ -8,24 +8,25 @@ import com.greenorange.promotion.annotation.SysLog;
import com.greenorange.promotion.common.BaseResponse;
import com.greenorange.promotion.common.ErrorCode;
import com.greenorange.promotion.common.ResultUtils;
import com.greenorange.promotion.constant.SystemConstant;
import com.greenorange.promotion.constant.UserConstant;
import com.greenorange.promotion.exception.ThrowUtils;
import com.greenorange.promotion.model.dto.CommonBatchRequest;
import com.greenorange.promotion.model.dto.CommonRequest;
import com.greenorange.promotion.model.dto.user.UserInfoAddRequest;
import com.greenorange.promotion.model.dto.user.UserInfoLoginRequest;
import com.greenorange.promotion.model.dto.user.UserInfoQueryRequest;
import com.greenorange.promotion.model.dto.user.UserInfoUpdateRequest;
import com.greenorange.promotion.model.dto.CommonStringRequest;
import com.greenorange.promotion.model.dto.user.*;
import com.greenorange.promotion.model.entity.UserInfo;
import com.greenorange.promotion.model.vo.user.UserInfoVO;
import com.greenorange.promotion.service.common.CommonService;
import com.greenorange.promotion.service.user.UserInfoService;
import com.greenorange.promotion.utils.JWTUtils;
import com.greenorange.promotion.utils.RegexUtils;
import com.greenorange.promotion.utils.SendSmsUtil;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.tags.Tag;
import jakarta.annotation.Resource;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.validation.Valid;
import jakarta.validation.constraints.NotBlank;
import lombok.extern.slf4j.Slf4j;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.web.bind.annotation.*;
@ -59,30 +60,121 @@ public class UserInfoController {
private JWTUtils jwtUtils;
/**
* 小程序端用户获取验证码
* @param commonStringRequest 手机号
* @return 验证码
*/
@PostMapping("code")
@Operation(summary = "小程序端用户获取验证码", description = "参数手机号权限管理员boss, admin)方法名getVerificationCode")
@SysLog(title = "用户管理", content = "小程序端用户获取验证码")
public BaseResponse<String> getVerificationCode(@Valid @RequestBody CommonStringRequest commonStringRequest) {
String phoneNumber = commonStringRequest.getTemplateString();
String verificationCode = userInfoService.getVerificationCode(phoneNumber);
return ResultUtils.success(verificationCode);
}
/**
* 小程序端用户注册
* @param userInfoRegisterRequest 小程序用户注册请求体
* @return 是否注册成功
*/
@PostMapping("register")
@Operation(summary = "小程序端用户注册", description = "参数小程序用户注册请求体权限管理员boss, admin)方法名userInfoMiniRegister")
@SysLog(title = "用户管理", content = "小程序端用户注册")
public BaseResponse<Boolean> userInfoMiniRegister(@Valid @RequestBody UserInfoRegisterRequest userInfoRegisterRequest) {
userInfoService.userInfoMiniRegister(userInfoRegisterRequest);
return ResultUtils.success(true);
}
/**
* 小程序端用户密码登录
* @param userInfoMiniPasswordLoginRequest 小程序用户密码登录请求体
* @return token
*/
@PostMapping("mini/pwd/login")
@Operation(summary = "小程序端用户密码登录", description = "参数小程序用户密码登录请求体权限管理员boss, admin)方法名userInfoMiniLogin")
@SysLog(title = "用户管理", content = "小程序端用户密码登录")
public BaseResponse<String> userInfoMiniLoginByPwd(@Valid @RequestBody UserInfoMiniPasswordLoginRequest userInfoMiniPasswordLoginRequest) {
String token = userInfoService.userInfoMiniLoginByPwd(userInfoMiniPasswordLoginRequest);
return ResultUtils.success(token);
}
/**
* 小程序端用户验证码登录
* @param userInfoMiniVerifyCodeLoginRequest 小程序用户验证码登录请求体
* @return token
*/
@PostMapping("mini/vcd/login")
@Operation(summary = "小程序端用户验证码登录", description = "参数小程序用户验证码登录请求体权限管理员boss, admin)方法名userInfoMiniLoginByVcd")
@SysLog(title = "用户管理", content = "小程序端用户验证码登录")
public BaseResponse<String> userInfoMiniLoginByVcd(@Valid @RequestBody UserInfoMiniVerifyCodeLoginRequest userInfoMiniVerifyCodeLoginRequest) {
String token = userInfoService.userInfoMiniLoginByVcd(userInfoMiniVerifyCodeLoginRequest);
return ResultUtils.success(token);
}
/**
* 小程序用户重置密码
* @param userInfoResetRequest 小程序用户密码重置请求体
* @return 是否重置成功
*/
@PostMapping("mini/reset/pwd")
@Operation(summary = "小程序用户重置密码", description = "参数小程序用户密码重置请求体权限管理员boss, admin)方法名userInfoMiniResetPwd")
@SysLog(title = "用户管理", content = "小程序端用户重置密码")
public BaseResponse<Boolean> userInfoMiniResetPwd(@Valid @RequestBody UserInfoResetRequest userInfoResetRequest) {
userInfoService.userInfoMiniResetPwd(userInfoResetRequest);
return ResultUtils.success(true);
}
/**
* 小程序端用户退出登录(用户退出时将 token 加入 Redis 黑名单)
* @return 是否退出登录成功
*/
@GetMapping("mini/logout")
@Operation(summary = "小程序端用户退出登录", description = "参数JWT权限管理员boss, admin)方法名userInfoMiniLogout")
@RequiresPermission(mustRole = UserConstant.DEFAULT_ROLE)
@SysLog(title = "用户管理", content = "小程序端用户退出登录")
public BaseResponse<Boolean> userInfoMiniLogout(@RequestHeader("Authorization") String token) {
// 获取token的过期时间
DecodedJWT decodedJWT = jwtUtils.verify(token);
long expirationTime = decodedJWT.getExpiresAt().getTime() - System.currentTimeMillis();
// 将token存入Redis黑名单并设置过期时间与token一致
redisTemplate.opsForValue().set(token, token, expirationTime, TimeUnit.MILLISECONDS);
return ResultUtils.success(true);
}
/**
* web端管理员登录
* @param userInfoLoginRequest 用户登录请求体
* @param userInfoLoginRequest web用户登录请求体
* @return 是否登录成功
*/
@PostMapping("login")
@Operation(summary = "web端管理员登录", description = "参数用户登录请求体权限管理员boss, admin)方法名userInfoLogin")
@Operation(summary = "web端管理员登录", description = "参数:web用户登录请求体权限管理员boss, admin)方法名userInfoLogin")
@SysLog(title = "用户管理", content = "web端管理员登录")
public BaseResponse<String> userInfoLogin(@Valid @RequestBody UserInfoLoginRequest userInfoLoginRequest, HttpServletRequest request) {
String userAccount = userInfoLoginRequest.getUserAccount();
String userPassword = userInfoLoginRequest.getUserPassword();
String token = userInfoService.userInfoLogin(userAccount, userPassword, request);
public BaseResponse<String> userInfoLogin(@Valid @RequestBody UserInfoLoginRequest userInfoLoginRequest) {
String token = userInfoService.userInfoLogin(userInfoLoginRequest);
return ResultUtils.success(token);
}
/**
* web端管理员退出登录(用户退出时将 token 加入 Redis 黑名单)
* @return 是否退出登录成功
*/
@PostMapping("logout")
@GetMapping("logout")
@Operation(summary = "web端管理员退出登录", description = "参数JWT权限管理员boss, admin)方法名userInfoLogout")
@RequiresPermission(mustRole = UserConstant.ADMIN_ROLE)
@SysLog(title = "用户管理", content = "web端管理员退出登录")
@ -98,6 +190,8 @@ public class UserInfoController {
/**
* web端管理员添加用户表
* @param userInfoAddRequest 用户表添加请求体
@ -105,6 +199,8 @@ public class UserInfoController {
*/
@PostMapping("add")
@Operation(summary = "web端管理员添加用户", description = "参数用户表添加请求体权限管理员boss, admin)方法名addUserInfo")
@RequiresPermission(mustRole = UserConstant.ADMIN_ROLE)
@SysLog(title = "用户管理", content = "web端管理员添加用户")
public BaseResponse<Boolean> addUserInfo(@Valid @RequestBody UserInfoAddRequest userInfoAddRequest) {
UserInfo userInfo = commonService.copyProperties(userInfoAddRequest, UserInfo.class);
userInfoService.save(userInfo);

View File

@ -16,9 +16,6 @@ import java.io.Serializable;
* 文件添加请求体
*/
@Data
@NoArgsConstructor
@AllArgsConstructor
@Builder
@Schema(description = "文件添加请求体", requiredProperties = {
"name",
"type",

View File

@ -5,7 +5,10 @@ import com.greenorange.promotion.model.enums.UserRoleEnum;
import io.swagger.v3.oas.annotations.media.Schema;
import jakarta.validation.constraints.NotBlank;
import jakarta.validation.constraints.Size;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.io.Serial;
import java.io.Serializable;

View File

@ -0,0 +1,36 @@
package com.greenorange.promotion.model.dto.user;
import io.swagger.v3.oas.annotations.media.Schema;
import jakarta.validation.constraints.NotBlank;
import jakarta.validation.constraints.Size;
import lombok.Data;
import java.io.Serial;
import java.io.Serializable;
/**
* 小程序用户密码登录请求体
*/
@Data
@Schema(description = "小程序用户密码登录请求体", requiredProperties = {"phoneNumber", "userPassword"})
public class UserInfoMiniPasswordLoginRequest implements Serializable {
/**
* 账号
*/
@NotBlank(message = "手机号不能为空")
@Schema(description = "手机号", example = "15888610253")
private String phoneNumber;
/**
* 密码
*/
@NotBlank(message = "密码不能为空")
@Size(min = 6, max = 10, message = "密码长度在 6 到 10 个字符")
@Schema(description = "密码(建议加密存储)", example = "qingcheng")
private String userPassword;
@Serial
private static final long serialVersionUID = 1L;
}

View File

@ -0,0 +1,36 @@
package com.greenorange.promotion.model.dto.user;
import io.swagger.v3.oas.annotations.media.Schema;
import jakarta.validation.constraints.NotBlank;
import lombok.Data;
import java.io.Serial;
import java.io.Serializable;
/**
* 小程序用户验证码登录请求体
*/
@Data
@Schema(description = "小程序用户验证码登录请求体", requiredProperties = {"phoneNumber", "verificationCode"})
public class UserInfoMiniVerifyCodeLoginRequest implements Serializable {
/**
* 账号
*/
@NotBlank(message = "手机号不能为空")
@Schema(description = "手机号", example = "15888610253")
private String phoneNumber;
/**
* 验证码
*/
@NotBlank(message = "验证码不能为空")
@Schema(description = "验证码", example = "666999")
private String verificationCode;
@Serial
private static final long serialVersionUID = 1L;
}

View File

@ -0,0 +1,57 @@
package com.greenorange.promotion.model.dto.user;
import io.swagger.v3.oas.annotations.media.Schema;
import jakarta.validation.constraints.NotBlank;
import jakarta.validation.constraints.Size;
import lombok.Data;
import java.io.Serial;
import java.io.Serializable;
/**
* 小程序用户注册请求体
*/
@Data
@Schema(description = "小程序用户注册请求体", requiredProperties = {"nickName", "phoneNumber",
"verificationCode", "invitationCode", "userPassword"})
public class UserInfoRegisterRequest implements Serializable {
/**
* 用户昵称
*/
@NotBlank(message = "用户昵称不能为空")
@Schema(description = "用户昵称", example = "chenxinzhi")
private String nickName;
/**
* 手机号
*/
@NotBlank(message = "手机号不能为空")
@Schema(description = "手机号", example = "15888610253")
private String phoneNumber;
/**
* 验证码
*/
@NotBlank(message = "验证码不能为空")
@Schema(description = "验证码", example = "666999")
private String verificationCode;
/**
* 邀请码
*/
@Schema(description = "邀请码", example = "666999")
private String invitationCode;
/**
* 密码
*/
@NotBlank(message = "密码不能为空")
@Size(min = 6, max = 10, message = "密码长度在 6 到 10 个字符")
@Schema(description = "密码(建议加密存储)", example = "qingcheng")
private String userPassword;
@Serial
private static final long serialVersionUID = 1L;
}

View File

@ -0,0 +1,53 @@
package com.greenorange.promotion.model.dto.user;
import io.swagger.v3.oas.annotations.media.Schema;
import jakarta.validation.constraints.NotBlank;
import jakarta.validation.constraints.Size;
import lombok.Data;
import java.io.Serial;
import java.io.Serializable;
/**
* 用户信息重置请求体
*/
@Data
@Schema(description = "小程序用户信息重置请求体", requiredProperties =
{"phoneNumber", "verificationCode", "userPassword", "userConfirmPassword"})
public class UserInfoResetRequest implements Serializable {
/**
* 手机号
*/
@NotBlank(message = "手机号不能为空")
@Schema(description = "手机号", example = "15888610253")
private String phoneNumber;
/**
* 验证码
*/
@NotBlank(message = "验证码不能为空")
@Schema(description = "验证码", example = "666999")
private String verificationCode;
/**
* 密码
*/
@NotBlank(message = "密码不能为空")
@Size(min = 6, max = 10, message = "密码长度在 6 到 10 个字符")
@Schema(description = "密码(建议加密存储)", example = "qingcheng")
private String userPassword;
/**
* 确认密码
*/
@NotBlank(message = "确认密码不能为空")
@Size(min = 6, max = 10, message = "密码长度在 6 到 10 个字符")
@Schema(description = "确认密码(建议加密存储)", example = "qingcheng")
private String userConfirmPassword;
@Serial
private static final long serialVersionUID = 1L;
}

View File

@ -6,7 +6,11 @@ import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import java.io.Serializable;
import java.util.Date;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
/**
* 文件上传列表
@ -14,6 +18,9 @@ import lombok.Data;
*/
@TableName(value ="file_info")
@Data
@NoArgsConstructor
@AllArgsConstructor
@Builder
public class FileInfo implements Serializable {
/**
* 文件ID

View File

@ -6,7 +6,11 @@ import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import java.io.Serializable;
import java.util.Date;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
/**
* 用户基本信息表

View File

@ -96,7 +96,7 @@ public class FileInfoServiceImpl extends ServiceImpl<FileInfoMapper, FileInfo>
FileInfo fileInfo = this.getOne(lambdaQueryWrapper);
if (fileInfo != null) return fileInfo.getFileView();
// 保存文件
FileInfoAddRequest fileInfoAddRequest = FileInfoAddRequest.builder()
fileInfo = FileInfo.builder()
.name(fileName)
.type(fileType)
.path(filePath)
@ -105,7 +105,6 @@ public class FileInfoServiceImpl extends ServiceImpl<FileInfoMapper, FileInfo>
.biz(biz)
.hashValue(hashValue)
.build();
fileInfo = commonService.copyProperties(fileInfoAddRequest, FileInfo.class);
this.save(fileInfo);
// 创建上传目录如果不存在
File file = new File(UPLOAD_DIR + filePath);

View File

@ -1,7 +1,7 @@
package com.greenorange.promotion.service.user;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.greenorange.promotion.model.dto.user.UserInfoQueryRequest;
import com.greenorange.promotion.model.dto.user.*;
import com.greenorange.promotion.model.entity.UserInfo;
import com.baomidou.mybatisplus.extension.service.IService;
import jakarta.servlet.http.HttpServletRequest;
@ -23,5 +23,35 @@ public interface UserInfoService extends IService<UserInfo> {
/**
* web端用户登录
*/
String userInfoLogin(String userAccount, String userPassword, HttpServletRequest request);
String userInfoLogin(UserInfoLoginRequest userInfoLoginRequest);
/**
* 小程序用户注册
*/
void userInfoMiniRegister(UserInfoRegisterRequest userInfoRegisterRequest);
/**
* 小程序端用户密码登录
*/
String userInfoMiniLoginByPwd(UserInfoMiniPasswordLoginRequest userInfoMiniPasswordLoginRequest);
/**
* 小程序用户验证码登录
*/
String userInfoMiniLoginByVcd(UserInfoMiniVerifyCodeLoginRequest userInfoMiniVerifyCodeLoginRequest);
/**
* 小程序用户重置密码
*/
void userInfoMiniResetPwd(UserInfoResetRequest userInfoResetRequest);
/**
* 小程序用户获取验证码
*/
String getVerificationCode(String phoneNumber);
}

View File

@ -1,26 +1,34 @@
package com.greenorange.promotion.service.user.impl;
import cn.hutool.core.util.RandomUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.greenorange.promotion.annotation.RequiresPermission;
import com.greenorange.promotion.common.ErrorCode;
import com.greenorange.promotion.constant.CommonConstant;
import com.greenorange.promotion.constant.SystemConstant;
import com.greenorange.promotion.constant.UserConstant;
import com.greenorange.promotion.exception.ThrowUtils;
import com.greenorange.promotion.mapper.UserInfoMapper;
import com.greenorange.promotion.model.dto.user.UserInfoQueryRequest;
import com.greenorange.promotion.model.dto.user.*;
import com.greenorange.promotion.model.entity.UserInfo;
import com.greenorange.promotion.service.common.CommonService;
import com.greenorange.promotion.service.user.UserInfoService;
import com.greenorange.promotion.utils.JWTUtils;
import com.greenorange.promotion.utils.RegexUtils;
import com.greenorange.promotion.utils.SendSmsUtil;
import com.greenorange.promotion.utils.SqlUtils;
import jakarta.annotation.Resource;
import jakarta.servlet.http.HttpServletRequest;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Service;
import java.util.HashMap;
import java.util.Map;
import java.util.concurrent.TimeUnit;
/**
* @author 35880
@ -35,6 +43,14 @@ public class UserInfoServiceImpl extends ServiceImpl<UserInfoMapper, UserInfo>
private JWTUtils jwtUtils;
@Resource
private CommonService commonService;
@Resource
private RedisTemplate<String, String> redisTemplate;
/**
* 获取查询条件
*/
@ -56,7 +72,9 @@ public class UserInfoServiceImpl extends ServiceImpl<UserInfoMapper, UserInfo>
* web端用户登录
*/
@Override
public String userInfoLogin(String userAccount, String userPassword, HttpServletRequest request) {
public String userInfoLogin(UserInfoLoginRequest userInfoLoginRequest) {
String userAccount = userInfoLoginRequest.getUserAccount();
String userPassword = userInfoLoginRequest.getUserPassword();
LambdaQueryWrapper<UserInfo> lambdaQueryWrapper = new LambdaQueryWrapper<>();
lambdaQueryWrapper.eq(UserInfo::getUserAccount, userAccount).eq(UserInfo::getUserPassword, userPassword);
UserInfo userInfo = this.getOne(lambdaQueryWrapper);
@ -66,6 +84,132 @@ public class UserInfoServiceImpl extends ServiceImpl<UserInfoMapper, UserInfo>
payload.put("userPassword", userPassword);
return jwtUtils.generateToken(payload);
}
/**
* 小程序用户注册
*/
@Override
public void userInfoMiniRegister(UserInfoRegisterRequest userInfoRegisterRequest) {
String phoneNumber = userInfoRegisterRequest.getPhoneNumber();
ThrowUtils.throwIf(RegexUtils.isPhoneInvalid(phoneNumber), ErrorCode.PARAMS_ERROR, "手机号格式无效");
LambdaQueryWrapper<UserInfo> phoneNumberLambdaQueryWrapper = new LambdaQueryWrapper<>();
phoneNumberLambdaQueryWrapper.eq(UserInfo::getPhoneNumber, phoneNumber);
UserInfo userInfo = this.getOne(phoneNumberLambdaQueryWrapper);
ThrowUtils.throwIf(userInfo != null, ErrorCode.OPERATION_ERROR, "手机号已注册");
String verificationCode = userInfoRegisterRequest.getVerificationCode();
String code = redisTemplate.opsForValue().get(SystemConstant.VERIFICATION_CODE + ":" + verificationCode);
ThrowUtils.throwIf(code == null, ErrorCode.OPERATION_ERROR, "验证码已失效");
// 移除验证码
redisTemplate.delete(SystemConstant.VERIFICATION_CODE + ":" + verificationCode);
String invitationCode = userInfoRegisterRequest.getInvitationCode();
LambdaQueryWrapper<UserInfo> invitedLambdaQueryWrapper = new LambdaQueryWrapper<>();
invitedLambdaQueryWrapper.eq(UserInfo::getInvitationCode, invitationCode);
UserInfo parentUserInfo = this.getOne(invitedLambdaQueryWrapper);
ThrowUtils.throwIf(parentUserInfo == null, ErrorCode.OPERATION_ERROR, "邀请码错误");
UserInfo myUserInfo = commonService.copyProperties(userInfoRegisterRequest, UserInfo.class);
userInfo.setParentUserId(parentUserInfo.getId());
userInfo.setInvitationCode(RandomUtil.randomNumbers(6));
userInfo.setUserAccount(RandomUtil.randomNumbers(8));
userInfo.setUserRole(UserConstant.DEFAULT_ROLE);
userInfo.setUserAvatar(UserConstant.USER_DEFAULT_AVATAR);
userInfo.setSuperUserList(parentUserInfo.getSuperUserList() + "," + parentUserInfo.getId());
this.save(myUserInfo);
}
/**
* 小程序端用户密码登录
*/
@Override
public String userInfoMiniLoginByPwd(UserInfoMiniPasswordLoginRequest userInfoMiniPasswordLoginRequest) {
String phoneNumber = userInfoMiniPasswordLoginRequest.getPhoneNumber();
ThrowUtils.throwIf(RegexUtils.isPhoneInvalid(phoneNumber), ErrorCode.PARAMS_ERROR, "手机号格式无效");
String userPassword = userInfoMiniPasswordLoginRequest.getUserPassword();
LambdaQueryWrapper<UserInfo> lambdaQueryWrapper = new LambdaQueryWrapper<>();
lambdaQueryWrapper.eq(UserInfo::getPhoneNumber, phoneNumber).eq(UserInfo::getUserPassword, userPassword);
UserInfo userInfo = this.getOne(lambdaQueryWrapper);
ThrowUtils.throwIf(userInfo == null, ErrorCode.OPERATION_ERROR, "手机号未注册");
Map<String, String> payload = new HashMap<>();
payload.put("phoneNumber", phoneNumber);
payload.put("userPassword", userPassword);
return jwtUtils.generateToken(payload);
}
/**
* 小程序用户验证码登录
*/
@Override
public String userInfoMiniLoginByVcd(UserInfoMiniVerifyCodeLoginRequest userInfoMiniVerifyCodeLoginRequest) {
String phoneNumber = userInfoMiniVerifyCodeLoginRequest.getPhoneNumber();
ThrowUtils.throwIf(RegexUtils.isPhoneInvalid(phoneNumber), ErrorCode.PARAMS_ERROR, "手机号格式无效");
String verificationCode = userInfoMiniVerifyCodeLoginRequest.getVerificationCode();
String code = redisTemplate.opsForValue().get(SystemConstant.VERIFICATION_CODE + ":" + verificationCode);
ThrowUtils.throwIf(code == null, ErrorCode.OPERATION_ERROR, "验证码已失效");
// 移除验证码
redisTemplate.delete(SystemConstant.VERIFICATION_CODE + ":" + verificationCode);
LambdaQueryWrapper<UserInfo> lambdaQueryWrapper = new LambdaQueryWrapper<>();
lambdaQueryWrapper.eq(UserInfo::getPhoneNumber, phoneNumber);
UserInfo userInfo = this.getOne(lambdaQueryWrapper);
String userPassword = userInfo.getUserPassword();
Map<String, String> payload = new HashMap<>();
payload.put("phoneNumber", phoneNumber);
payload.put("userPassword", userPassword);
return jwtUtils.generateToken(payload);
}
/**
* 小程序用户重置密码
*/
@Override
public void userInfoMiniResetPwd(UserInfoResetRequest userInfoResetRequest) {
String phoneNumber = userInfoResetRequest.getPhoneNumber();
ThrowUtils.throwIf(RegexUtils.isPhoneInvalid(phoneNumber), ErrorCode.PARAMS_ERROR, "手机号格式无效");
String verificationCode = userInfoResetRequest.getVerificationCode();
String code = redisTemplate.opsForValue().get(SystemConstant.VERIFICATION_CODE + ":" + verificationCode);
ThrowUtils.throwIf(code == null, ErrorCode.OPERATION_ERROR, "验证码已失效");
// 移除验证码
redisTemplate.delete(SystemConstant.VERIFICATION_CODE + ":" + verificationCode);
String userPassword = userInfoResetRequest.getUserPassword();
String userConfirmPassword = userInfoResetRequest.getUserConfirmPassword();
ThrowUtils.throwIf(!userPassword.equals(userConfirmPassword), ErrorCode.OPERATION_ERROR, "两次密码不一致");
// 更新用户密码
LambdaUpdateWrapper<UserInfo> lambdaUpdateWrapper = new LambdaUpdateWrapper<>();
lambdaUpdateWrapper.eq(UserInfo::getPhoneNumber, phoneNumber).set(UserInfo::getUserPassword, userPassword);
this.update(lambdaUpdateWrapper);
}
/**
* 小程序用户获取验证码
*/
@Override
public String getVerificationCode(String phoneNumber) {
ThrowUtils.throwIf(RegexUtils.isPhoneInvalid(phoneNumber), ErrorCode.PARAMS_ERROR, "手机号格式错误");
String verificationCode = SendSmsUtil.getVerificationCode(phoneNumber);
ThrowUtils.throwIf(verificationCode == null, ErrorCode.OPERATION_ERROR, "验证码获取失败");
redisTemplate.opsForValue().set(SystemConstant.VERIFICATION_CODE + ":" + verificationCode, verificationCode, 5, TimeUnit.MINUTES);
return verificationCode;
}
}

View File

@ -0,0 +1,73 @@
package com.greenorange.promotion.utils;
import org.apache.http.HttpEntity;
import org.apache.http.NameValuePair;
import org.apache.http.client.entity.UrlEncodedFormEntity;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.message.BasicNameValuePair;
import org.apache.http.util.EntityUtils;
import org.dom4j.Document;
import org.dom4j.DocumentHelper;
import org.dom4j.Element;
import java.util.ArrayList;
import java.util.List;
public class SendSmsUtil {
private static String Url = "http://106.ihuyi.com/webservice/sms.php?method=Submit";
public static String getVerificationCode(String phoneNumber) {
// 创建 HttpClient
try (CloseableHttpClient client = HttpClients.createDefault()) {
// 创建 POST 请求
HttpPost post = new HttpPost(Url);
post.setHeader("Content-Type", "application/x-www-form-urlencoded;charset=GBK");
// 生成验证码
int mobile_code = (int) ((Math.random() * 9 + 1) * 100000);
String content = "您的验证码是:" + mobile_code + "。请不要把验证码泄露给其他人。";
// 设置请求参数
List<NameValuePair> data = new ArrayList<>();
data.add(new BasicNameValuePair("account", "C08121984"));
data.add(new BasicNameValuePair("password", "84a27a879413ec629bf26c5d84a25271"));
data.add(new BasicNameValuePair("mobile", phoneNumber));
data.add(new BasicNameValuePair("content", content));
// 设置请求体
UrlEncodedFormEntity entity = new UrlEncodedFormEntity(data, "GBK");
post.setEntity(entity);
// 执行请求
String response = client.execute(post, httpResponse -> {
HttpEntity entity1 = httpResponse.getEntity();
return EntityUtils.toString(entity1, "GBK");
});
// 解析返回的 XML 响应
Document doc = DocumentHelper.parseText(response);
Element root = doc.getRootElement();
String code = root.elementText("code");
String msg = root.elementText("msg");
String smsid = root.elementText("smsid");
System.out.println(code);
System.out.println(msg);
System.out.println(smsid);
if ("2".equals(code)) {
System.out.println("短信提交成功");
return String.valueOf(mobile_code);
}
} catch (Exception e) {
e.printStackTrace();
}
return null;
}
}

View File

@ -28,8 +28,7 @@ public class sendsms {
post.setHeader("Content-Type", "application/x-www-form-urlencoded;charset=GBK");
// 生成验证码
// int mobile_code = (int) ((Math.random() * 9 + 1) * 100000);
int mobile_code = 114514;
int mobile_code = (int) ((Math.random() * 9 + 1) * 100000);
String content = "您的验证码是:" + mobile_code + "。请不要把验证码泄露给其他人。";
// 设置请求参数