开发在线法律咨询平台的设计与实现Day1
今日完成
user表的建立
DROP TABLE IF EXISTS `user`;
CREATE TABLE `user` (
`id` bigint NOT NULL AUTO_INCREMENT COMMENT 'id',
`username` varchar(256) CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci NULL DEFAULT NULL COMMENT '用户名',
`userAccount` varchar(256) CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci NULL DEFAULT NULL COMMENT '账号',
`avatarUrl` varchar(1024) CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci NULL DEFAULT NULL COMMENT '用户头像',
`gender` tinyint NULL DEFAULT NULL COMMENT '性别',
`userPassword` varchar(512) CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci NOT NULL COMMENT '密码',
`phone` varchar(128) CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci NULL DEFAULT NULL COMMENT '电话',
`email` varchar(512) CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci NULL DEFAULT NULL COMMENT '邮箱',
`userStatus` int NOT NULL DEFAULT 0 COMMENT '状态 0-正常',
`createTime` datetime NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
`updateTime` datetime NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '更新时间',
`isDelete` tinyint NOT NULL DEFAULT 0 COMMENT '是否删除',
`userRole` tinyint UNSIGNED NOT NULL DEFAULT 0 COMMENT '0-普通用户 1-律师 2-管理员',
PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 15 CHARACTER SET = utf8mb4 COLLATE = utf8mb4_0900_ai_ci ROW_FORMAT = Dynamic;
项目搭建
项目结构
定义错误码
ErrorCode.java
public enum ErrorCode {
PARAMS_ERROR(40000,"请求参数错误",""),
NULL_ERROR(40001,"请求数据为空",""),
NOT_LOGIN(40100,"未登录",""),
NO_AUTH(40101,"无权限",""),
FAIL_SEARCH(40102,"数据库操作失败",""),
SYSTEM_ERROR(50000,"系统错误","");
private final int code;
private final String message;
private final String description;
ErrorCode(int code, String message, String description) {
this.code = code;
this.message = message;
this.description = description;
}
public int getCode() {
return code;
}
public String getMessage() {
return message;
}
public String getDescription() {
return description;
}
}
通用返回类(返回给前端的数据)
BaseResponse.java
@Data
public class BaseResponse<T> implements Serializable {
private int code;
private T data;
private String message;
private String description;
public BaseResponse(int code, T data, String message,String description) {
this.code = code;
this.data = data;
this.message = message;
this.description = description;
}
public BaseResponse(int code, T data, String message) {
this.code = code;
this.data = data;
this.message = message;
this.description = "";
}
public BaseResponse(int code, T data) {
this(code,data,"","");
}
public BaseResponse(ErrorCode errorCode) {
this(errorCode.getCode(),null,errorCode.getMessage(),errorCode.getDescription());
}
}
返回类工具类
不用每次new BaseResponse<>(0,data,"ok","成功");太多余繁琐。
public class ResultUtils {
/**
* 成功
* @param data
* @return
* @param <T>
*/
public static <T> BaseResponse<T> success(T data){
return new BaseResponse<>(0,data,"ok","成功");
}
public static BaseResponse error(ErrorCode errorCode){
return new BaseResponse(errorCode);
}
public static BaseResponse error(int code, String message, String description) {
return new BaseResponse(code,null,message,description);
}
public static BaseResponse error(ErrorCode errorCode, String message) {
return new BaseResponse(errorCode.getCode(),message);
}
}
定义的全局常量
UserContant.java
public interface UserContant {
String SALT = "ysbt";
}
自定义异常类
public class BusinessException extends RuntimeException{
private final int code;
private final String description;
public BusinessException(String message, int code, String description) {
super(message);
this.code = code;
this.description = description;
}
public BusinessException(ErrorCode errorCode) {
super(errorCode.getMessage());
this.code = errorCode.getCode();
this.description = errorCode.getDescription();
}
public BusinessException(ErrorCode errorCode,String description) {
super(errorCode.getMessage());
this.code = errorCode.getCode();
this.description = description;
}
public int getCode() {
return code;
}
public String getDescription() {
return description;
}
}
捕获自己定义的异常类
@RestControllerAdvice
@Slf4j
public class GlobalExceptionHandler {
/**
* 捕获自己定义的异常类
* @param e
* @return
*/
@ExceptionHandler(BusinessException.class)
public BaseResponse businessExceptionHandler(BusinessException e){
log.error("businessException"+e.getMessage()+e);
return ResultUtils.error(e.getCode(),e.getMessage(),e.getDescription());
}
@ExceptionHandler(RuntimeException.class)
public BaseResponse runtimeExceptionHandler(RuntimeException e){
log.info("runtimeException"+e);
System.out.println(e);
return ResultUtils.error(ErrorCode.SYSTEM_ERROR,e.getMessage());
}
}
集成swagger
引入依赖
<dependency>
<groupId>org.springdoc</groupId>
<artifactId>springdoc-openapi-starter-webmvc-ui</artifactId>
<version>2.2.0</version>
</dependency>
配置swagger设置
@Configuration
@Profile({"dev", "test"})
public class SwaggerConfig {
@Bean
public OpenAPI openAPI() {
return new OpenAPI()
.info(new Info()
.title("消费者维权平台")
.description("为消费者维权")
.version("v1"))
.externalDocs(new ExternalDocumentation()
.description("项目API文档")
.url("/"));
}
}
接口开发
注册接口开发
UserServiceImpl.java
@Override
public long userRegister(String userAccount, String userPassword, String checkPassword) {
//验证是否非空,不为空执行下一步
if (StringUtils.isAnyBlank(userAccount,userPassword,checkPassword)){
throw new BusinessException(ErrorCode.NULL_ERROR,"参数为空");
//账号不能小于4位
}
if (userAccount.length()<4){
throw new BusinessException(ErrorCode.PARAMS_ERROR,"账号小于4位");
}
//密码不能小于8位
if (userPassword.length()<8 || checkPassword.length()<8){
throw new BusinessException(ErrorCode.PARAMS_ERROR,"密码小于8位");
}
//账号不能重复
QueryWrapper<User> qw = new QueryWrapper<>();
qw.eq("userAccount",userAccount);
long count = userMapper.selectCount(qw);
if (count > 0){
throw new BusinessException(ErrorCode.PARAMS_ERROR,"账号重复");
}
//账号不包含特殊字符
String regEx="[`~!@#$%^&*()+=|{}':;',\\[\\].<>/?~!@#¥%……&*() ——+|{}【】‘;:”“’。,、?]";
Matcher matcher = Pattern.compile(regEx).matcher(userAccount);
if (matcher.find()){
throw new BusinessException(ErrorCode.PARAMS_ERROR,"账号包含特殊字符");
}
//密码和校验密码不同
if(!(userPassword.equals(checkPassword))){
throw new BusinessException(ErrorCode.PARAMS_ERROR,"密码和校验密码不同");
}
// 3.对密码进行加密
String encryptPassword = DigestUtils.md5DigestAsHex((SALT + userPassword).getBytes());
// 4.向数据库插入数据
User user = new User();
user.setUserAccount(userAccount);
user.setUserPassword(encryptPassword);
boolean save = this.save(user);
if (!save){
throw new BusinessException(ErrorCode.FAIL_SEARCH,"注册失败");
}
return user.getId();
}
UserController.java
public BaseResponse<Long> userRegister(String userAccount,String userPassword,String checkPassword){
if(StringUtils.isAnyBlank(userAccount,userPassword,checkPassword)){
throw new BusinessException(ErrorCode.NULL_ERROR);
}
long l = userService.userRegister(userAccount, userPassword, checkPassword);
return ResultUtils.success(l);
};
开发中遇到的问题
一、mybaitsplus与springboot冲突
问题描述: 项目无法动,报 Action: Consider defining a bean of type 'com.qst.onlinelaw.mapper.UserMapper' in your configuration.。
解决过程: 修改依赖
具体实现:
springboot3在集成mybatisplus时要导入mybatis-plus-spring-boot3-starter而不是mybatis-plus-spring-boot-starter
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-spring-boot3-starter</artifactId>
<version>3.5.7</version>
</dependency>
二、mybaits内部错误
问题描述: 运行到持久层功能就报错MyBatisSystemException
解决过程: 修改application.yml中的数据库url,当时配错了
具体实现:
由于只有MyBatisSystemException导致不知道具体哪里写错了引入trycatch显示异常信息
try {
QueryWrapper<User> qw = new QueryWrapper<>();
qw.eq("userAccount", userAccount);
long count = userMapper.selectCount(qw);
} catch (MyBatisSystemException e) {
e.printStackTrace(); // 打印堆栈跟踪信息
// 或者使用日志记录器记录异常信息
// log.error("Error querying user count", e);
}