MyBatisPlus详解与实战应用

MyBatisPlus 详解与实战应用

一、MyBatisPlus 简介

MyBatisPlus 是一个基于 MyBatis 的增强工具,旨在简化数据库操作和提高开发效率。它提供了丰富的内置功能,例如自动映射、分页查询、条件构造器等,帮助开发者快速构建数据访问层。

1.1 MyBatisPlus 的优势

  • 简化开发:提供通用的增删改查方法,减少重复代码。
  • 支持链式编程:使用条件构造器(QueryWrapper、UpdateWrapper)实现灵活的查询和更新。
  • 强大的分页功能:集成分页插件,轻松实现分页查询。
  • 多租户支持:支持多租户架构,适用于 SaaS 场景。
  • 逻辑删除:支持软删除,避免数据真正删除。

1.2 MyBatisPlus 的核心组件

  • BaseMapper:MyBatisPlus 提供的基础接口,包含常见的增删改查方法。
  • IService:服务层接口,提供事务管理、批量操作等功能。
  • QueryWrapper / UpdateWrapper:用于构建查询和更新条件。
  • Page:分页工具类,配合 BaseMapper 使用。
  • 自动映射:自动映射数据库字段与实体类字段。

二、MyBatisPlus 的基本使用

2.1 引入依赖

pom.xml 中引入 MyBatisPlus 依赖:

xml 复制代码
<dependency>
    <groupId>com.baomidou</groupId>
    <artifactId>mybatis-plus-boot-starter</artifactId>
    <version>3.5.1</version>
</dependency>

2.2 配置 MyBatisPlus

application.yml 中配置 MyBatisPlus:

yaml 复制代码
spring:
  datasource:
    url: jdbc:mysql://localhost:3306/test_db?useSSL=false&serverTimezone=UTC
    username: root
    password: root
    driver-class-name: com.mysql.cj.jdbc.Driver

mybatis-plus:
  mapper-locations: classpath*:mapper/**/*.xml
  type-aliases-package: com.example.demo.entity

2.3 定义实体类

java 复制代码
import com.baomidou.mybatisplus.annotation.*;

@Data
@TableName("user_table")
public class User {
    @TableId(type = IdType.AUTO)
    private Long id;
    private String name;
    private Integer age;
    private String email;

    @TableLogic
    private Integer deleted;
}

2.4 定义 Mapper 接口

java 复制代码
import com.baomidou.mybatisplus.core.mapper.BaseMapper;

public interface UserMapper extends BaseMapper<User> {
}

2.5 使用 BaseMapper 实现基本操作

java 复制代码
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.List;

@Service
public class UserService {
    @Autowired
    private UserMapper userMapper;

    // 插入用户
    public void insertUser(User user) {
        userMapper.insert(user);
    }

    // 查询所有用户
    public List<User> getAllUsers() {
        return userMapper.selectList(null);
    }

    // 根据 ID 查询用户
    public User getUserById(Long id) {
        return userMapper.selectById(id);
    }

    // 更新用户信息
    public void updateUser(User user) {
        userMapper.updateById(user);
    }

    // 删除用户(逻辑删除)
    public void deleteUser(Long id) {
        userMapper.deleteById(id);
    }
}

三、MyBatisPlus 高级功能

3.1 条件构造器

MyBatisPlus 提供了 QueryWrapperUpdateWrapper,用于构建复杂的查询和更新条件。

3.1.1 QueryWrapper 示例
java 复制代码
// 查询年龄大于 20 的用户
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
queryWrapper.gt("age", 20);
List<User> users = userMapper.selectList(queryWrapper);
3.1.2 UpdateWrapper 示例
java 复制代码
// 将年龄大于 20 的用户邮箱更新为 "test@example.com"
UpdateWrapper<User> updateWrapper = new UpdateWrapper<>();
updateWrapper.gt("age", 20).set("email", "test@example.com");
userMapper.update(null, updateWrapper);

3.2 分页查询

MyBatisPlus 提供了 Page 工具类,用于实现分页查询。

3.2.1 分页查询示例
java 复制代码
// 查询第一页,每页 5 条数据
Page<User> page = new Page<>(1, 5);
Page<User> userPage = userMapper.selectPage(page, null);

List<User> users = userPage.getRecords();
long total = userPage.getTotal();

3.3 逻辑删除

MyBatisPlus 支持逻辑删除,避免数据真正删除。

3.3.1 配置逻辑删除

application.yml 中配置逻辑删除:

yaml 复制代码
mybatis-plus:
  global-config:
    db-config:
      logic-delete-value: 1
      logic-keep-value: 0

3.4 多租户支持

MyBatisPlus 支持多租户架构,适用于 SaaS 场景。

3.4.1 配置多租户

application.yml 中配置多租户:

yaml 复制代码
mybatis-plus:
  tenant:
    enable: true
    ignore-table: "user_table"  # 忽略的表
    tenant-id-column: "tenant_id"  # 租户 ID 列

四、MyBatisPlus 实战应用

4.1 场景说明

假设我们有一个电商平台,用户可以下单购买商品。我们需要实现以下功能:

  • 用户注册与信息管理
  • 商品管理
  • 订单管理

4.2 数据库设计

4.2.1 用户表(user_table)
字段名 类型 描述
id BIGINT 主键
name VARCHAR 用户名
age INT 年龄
email VARCHAR 邮箱
deleted INT 逻辑删除标识
4.2.2 商品表(product_table)
字段名 类型 描述
id BIGINT 主键
name VARCHAR 商品名称
price DECIMAL 价格
stock INT 库存
4.2.3 订单表(order_table)
字段名 类型 描述
id BIGINT 主键
user_id BIGINT 用户 ID
product_id BIGINT 商品 ID
quantity INT 数量
total_price DECIMAL 总价

4.3 实体类定义

java 复制代码
// User.java(已在前面定义)

// Product.java
@Data
@TableName("product_table")
public class Product {
    @TableId(type = IdType.AUTO)
    private Long id;
    private String name;
    private BigDecimal price;
    private Integer stock;
}

// Order.java
@Data
@TableName("order_table")
public class Order {
    @TableId(type = IdType.AUTO)
    private Long id;
    private Long userId;
    private Long productId;
    private Integer quantity;
    private BigDecimal totalPrice;
}

4.4 Mapper 接口定义

java 复制代码
public interface ProductMapper extends BaseMapper<Product> {
}

public interface OrderMapper extends BaseMapper<Order> {
}

4.5 服务层实现

java 复制代码
@Service
public class OrderService {
    @Autowired
    private UserMapper userMapper;
    @Autowired
    private ProductMapper productMapper;
    @Autowired
    private OrderMapper orderMapper;

    // 下单
    public void placeOrder(Long userId, Long productId, Integer quantity) {
        User user = userMapper.selectById(userId);
        if (user == null) {
            throw new RuntimeException("用户不存在");
        }

        Product product = productMapper.selectById(productId);
        if (product == null) {
            throw new RuntimeException("商品不存在");
        }

        if (product.getStock() < quantity) {
            throw new RuntimeException("库存不足");
        }

        BigDecimal totalPrice = product.getPrice().multiply(new BigDecimal(quantity));
        Order order = new Order();
        order.setUserId(userId);
        order.setProductId(productId);
        order.setQuantity(quantity);
        order.setTotalPrice(totalPrice);

        orderMapper.insert(order);

        // 更新库存
        product.setStock(product.getStock() - quantity);
        productMapper.updateById(product);
    }

    // 查询用户订单
    public List<Order> getOrdersByUserId(Long userId) {
        QueryWrapper<Order> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("user_id", userId);
        return orderMapper.selectList(queryWrapper);
    }
}

4.6 控制器层实现

java 复制代码
@RestController
@RequestMapping("/orders")
public class OrderController {
    @Autowired
    private OrderService orderService;

    // 下单
    @PostMapping("/place")
    public void placeOrder(@RequestParam Long userId, @RequestParam Long productId, @RequestParam Integer quantity) {
        orderService.placeOrder(userId, productId, quantity);
    }

    // 查询用户订单
    @GetMapping("/user/{userId}")
    public List<Order> getOrdersByUserId(@PathVariable Long userId) {
        return orderService.getOrdersByUserId(userId);
    }
}

五、总结

本文详细介绍了 MyBatisPlus 的核心功能,包括其基本使用、高级功能(如条件构造器、分页查询、逻辑删除等)以及如何在实际项目中应用这些功能。通过一个电商平台的实战案例,我们展示了如何利用 MyBatisPlus 实现高效的数据库操作。

MyBatisPlus 是一个非常强大的工具,能够极大地简化数据库操作,提高开发效率。在实际开发中,合理使用 MyBatisPlus 的功能可以显著减少重复代码,提高代码可读性和维护性。

相关推荐
重生之我是Java开发战士10 小时前
【数据结构】优先级队列(堆)
java·数据结构·算法
菜鸟233号10 小时前
力扣216 组合总和III java实现
java·数据结构·算法·leetcode
dodod201210 小时前
Ubuntu24.04.3执行sudo apt install yarnpkg 命令失败的原因
java·服务器·前端
Evan芙10 小时前
搭建 LNMT 架构并配置 Tomcat 日志管理与自动备份
java·架构·tomcat
青云交10 小时前
Java 大视界 -- Java+Spark 构建企业级用户画像平台:从数据采集到标签输出全流程(437)
java·开发语言·spark·hbase 优化·企业级用户画像·标签计算·高并发查询
铉铉这波能秀10 小时前
正则表达式从入门到精通(字符串模式匹配)
java·数据库·python·sql·正则表达式·模式匹配·表格处理
武子康10 小时前
Java-202 RabbitMQ 生产安装与容器快速启动:Erlang 兼容、RPM 部署与常用命令
java·消息队列·rabbitmq·erlang·java-rabbitmq·mq
a程序小傲10 小时前
米哈游Java后端面试被问:Spring Boot Starter的制作原理
java·spring boot·后端
Misnearch10 小时前
Mock服务是什么?
java·后端·微服务·mock
后端小张10 小时前
【JAVA 进阶】深入理解Sentinel:分布式系统的流量守卫者
java·开发语言·spring boot·后端·spring·spring cloud·sentinel