SpringBoot 3 + MyBatis-Plus 是目前 Java 后端开发中最流行的技术组合。本文将从零开始,带你搭建一个具备完整前后端分离能力的企业级项目,涵盖项目结构设计、数据库操作、权限认证和部署方案。
项目初始化:最佳实践的项目结构
src/main/java/com/example/project/\n├── config/ # 配置类(Security、CORS、MyBatis-Plus)\n├── controller/ # 控制器层\n├── service/ # 服务接口\n│ └── impl/ # 服务实现\n├── mapper/ # MyBatis Mapper 接口\n├── entity/ # 数据库实体\n├── dto/ # 数据传输对象\n├── vo/ # 视图对象(返回给前端)\n├── common/ # 公共类(统一响应、异常处理)\n│ ├── Result.java\n│ ├── GlobalExceptionHandler.java\n│ └── PageResult.java\n└── utils/ # 工具类MyBatis-Plus:告别手写 SQL
1. 基础配置
// application.yml\nspring:\n datasource:\n url: jdbc:mysql://localhost:3306/mydb?useUnicode=true&characterEncoding=utf8mb4\n username: root\n password: ${DB_PASSWORD}\nmybatis-plus:\n configuration:\n log-impl: org.apache.ibatis.logging.stdout.StdOutImpl # SQL 日志\n map-underscore-to-camel-case: true # 下划线转驼峰\n global-config:\n db-config:\n logic-delete-field: deleted # 逻辑删除字段\n logic-delete-value: 1\n logic-not-delete-value: 02. 实体与 Mapper
// User.java - 实体类\n@Data\n@TableName("t_user")\npublic class User {\n @TableId(type = IdType.AUTO)\n private Long id;\n private String username;\n @TableField(select = false) // 查询时排除密码\n private String password;\n private String email;\n @TableField(fill = FieldFill.INSERT)\n private LocalDateTime createTime;\n @TableField(fill = FieldFill.INSERT_UPDATE)\n private LocalDateTime updateTime;\n @TableLogic // 逻辑删除\n private Integer deleted;\n}\n\n// UserMapper.java - 一行代码完成 CRUD\n@Mapper\npublic interface UserMapper extends BaseMapper {\n // 继承 BaseMapper 后自动拥有 CRUD 方法\n // 复杂查询在这里自定义\n @Select("SELECT * FROM t_user WHERE email = #{email}")\n User selectByEmail(@Param("email") String email);\n} 3. 分页查询(一行代码)
// Controller\n@GetMapping("/list")\npublic Result> list(\n @RequestParam(defaultValue = "1") Integer page,\n @RequestParam(defaultValue = "10") Integer size,\n @RequestParam(required = false) String keyword\n) {\n Page pageParam = new Page<>(page, size);\n LambdaQueryWrapper wrapper = new LambdaQueryWrapper<>();\n if (keyword != null) {\n wrapper.like(User::getUsername, keyword)\n .or().like(User::getEmail, keyword);\n }\n wrapper.orderByDesc(User::getCreateTime);\n return Result.success(userService.page(pageParam, wrapper));\n} 统一响应与异常处理
// Result.java - 统一响应格式\n@Data\npublic class Result {\n private Integer code;\n private String message;\n private T data;\n\n public static Result success(T data) {\n Result r = new Result<>();\n r.code = 200; r.message = "success"; r.data = data;\n return r;\n }\n public static Result error(String message) {\n Result r = new Result<>();\n r.code = 500; r.message = message;\n return r;\n }\n}\n\n// GlobalExceptionHandler.java - 全局异常处理\n@RestControllerAdvice\npublic class GlobalExceptionHandler {\n @ExceptionHandler(Exception.class)\n public Result> handleException(Exception e) {\n log.error("系统异常", e);\n return Result.error("服务器内部错误");\n }\n @ExceptionHandler(MethodArgumentNotValidException.class)\n public Result> handleValidation(MethodArgumentNotValidException e) {\n String msg = e.getBindingResult().getFieldErrors()\n .stream().map(FieldError::getDefaultMessage)\n .collect(Collectors.joining(", "));\n return Result.error(msg);\n }\n} Spring Security + JWT 认证
// SecurityConfig.java\n@Configuration\n@EnableWebSecurity\npublic class SecurityConfig {\n @Bean\n public SecurityFilterChain filterChain(HttpSecurity http) throws Exception {\n http\n .csrf(AbstractHttpConfigurer::disable)\n .sessionManagement(s -> s.sessionCreationPolicy(SessionCreationPolicy.STATELESS))\n .authorizeHttpRequests(auth -> auth\n .requestMatchers("/api/auth/**").permitAll()\n .requestMatchers("/api/admin/**").hasRole("ADMIN")\n .anyRequest().authenticated()\n )\n .addFilterBefore(jwtAuthFilter, UsernamePasswordAuthenticationFilter.class);\n return http.build();\n }\n}\n\n// JwtUtil.java\n@Component\npublic class JwtUtil {\n @Value("${jwt.secret}")\n private String secret;\n\n public String generateToken(Long userId, String username) {\n return Jwts.builder()\n .setSubject(String.valueOf(userId))\n .claim("username", username)\n .setIssuedAt(new Date())\n .setExpiration(new Date(System.currentTimeMillis() + 7200000)) // 2小时\n .signWith(Keys.hmacShaKeyFor(secret.getBytes()))\n .compact();\n }\n}前后端分离项目部署
Docker Compose 一键部署
# docker-compose.yml\nversion: '3.8'\nservices:\n mysql:\n image: mysql:8.0\n environment:\n MYSQL_ROOT_PASSWORD: ${DB_PASSWORD}\n volumes:\n - mysql_data:/var/lib/mysql\n\n backend:\n build: ./backend\n ports:\n - "8080:8080"\n depends_on:\n - mysql\n environment:\n SPRING_DATASOURCE_URL: jdbc:mysql://mysql:3306/mydb\n\n frontend:\n build: ./frontend\n ports:\n - "80:80"\n depends_on:\n - backend\n\nvolumes:\n mysql_data:总结
SpringBoot 3 + MyBatis-Plus 的组合让 Java 后端开发变得异常高效——MyBatis-Plus 消除了 80% 的 CRUD 样板代码,SpringBoot 3 的自动配置让你专注于业务逻辑。但高效不等于简单:理解 Spring 的 IoC 容器、AOP 切面编程、事务传播机制,才能真正驾驭这套技术栈。
评论 (0)