首页
/ 使用MyBatis-Plus Generator构建规范化Repository层

使用MyBatis-Plus Generator构建规范化Repository层

2026-03-17 03:20:54作者:霍妲思

场景引入:解决数据访问层架构一致性问题

在企业级应用开发中,保持数据访问层的架构一致性是提升代码可维护性的关键。MyBatis-Plus提供的代码生成器虽然能大幅减少重复工作,但默认生成的Service层代码结构有时无法满足团队对Repository模式的架构要求。本文将详细介绍如何通过自定义配置,让MyBatis-Plus Generator直接生成符合Repository模式的代码结构,实现数据访问层的标准化设计。

核心配置步骤:实现Repository层自动生成

配置包路径映射规则

解决什么问题:将生成的代码按Repository模式组织到正确的包结构中,避免与默认Service层命名冲突。

如何实现:通过PackageConfig配置项重定向生成文件的包路径,将原本生成到service包下的代码转移到repository包中:

// 配置包路径映射
PackageConfig packageConfig = new PackageConfig.Builder()
    .parent("com.company.project")  // 基础包路径
    .entity("domain")               // 实体类包名
    .mapper("mapper")               // Mapper接口包名
    .service("repository")          // Repository接口包名
    .serviceImpl("repository.impl") // Repository实现类包名
    .build();

为什么这样配置:采用"repository"作为数据访问层的包名,符合领域驱动设计(DDD)的分层思想,使代码结构更清晰,同时避免与业务逻辑层(Service)混淆。

自定义命名转换规则

解决什么问题:生成符合Repository模式的类名,使接口和实现类命名更具辨识度。

如何实现:通过ServiceStrategyConfig配置类名转换规则:

// 配置命名转换策略
ServiceStrategyConfig serviceStrategy = new ServiceStrategyConfig.Builder()
    // 将接口命名为"I+实体名+Repository"格式
    .convertServiceFileName((entityName) -> "I" + entityName + "Repository")
    // 将实现类命名为"实体名+Repository"格式
    .convertServiceImplFileName((entityName) -> entityName + "Repository")
    .build();

为什么这样配置:以"I"为接口前缀符合Java编程规范,"Repository"后缀明确标识了数据访问层的职责,使代码意图更清晰。

设置接口继承关系

解决什么问题:统一Repository层接口的基础方法定义,确保各Repository接口具有一致的方法签名。

如何实现:指定自定义的Repository基类接口和实现类:

// 配置接口继承关系
ServiceStrategyConfig serviceStrategy = new ServiceStrategyConfig.Builder()
    // 设置Repository接口的父接口
    .superServiceClass("com.company.project.repository.IBaseRepository")
    // 设置Repository实现类的父类
    .superServiceImplClass("com.company.project.repository.impl.BaseRepositoryImpl")
    .build();

为什么这样配置:通过继承基础接口,可以在基类中定义通用的数据访问方法,避免在每个Repository接口中重复声明,同时便于统一扩展功能。

完整实现案例:构建Repository生成器

下面是一个完整的AutoGenerator配置示例,整合了上述所有配置项:

// 1. 创建数据源配置
DataSourceConfig dataSourceConfig = new DataSourceConfig.Builder(
    "jdbc:mysql://localhost:3306/test_db",
    "root",
    "password"
).build();

// 2. 创建全局配置
GlobalConfig globalConfig = new GlobalConfig.Builder()
    .author("开发团队")                // 设置作者信息
    .outputDir(System.getProperty("user.dir") + "/src/main/java")  // 设置输出目录
    .commentDate("yyyy-MM-dd")        // 设置注释日期格式
    .build();

// 3. 创建包配置
PackageConfig packageConfig = new PackageConfig.Builder()
    .parent("com.company.project")
    .entity("domain")
    .mapper("mapper")
    .service("repository")
    .serviceImpl("repository.impl")
    .build();

// 4. 创建策略配置
StrategyConfig strategyConfig = new StrategyConfig.Builder()
    .addInclude("user", "order", "product")  // 设置需要生成的表名
    .serviceBuilder()
        .convertServiceFileName(entityName -> "I" + entityName + "Repository")
        .convertServiceImplFileName(entityName -> entityName + "Repository")
        .superServiceClass("com.company.project.repository.IBaseRepository")
        .superServiceImplClass("com.company.project.repository.impl.BaseRepositoryImpl")
        .enableFileOverride()  // 允许覆盖已有文件
    .entityBuilder()
        .enableLombok()        // 启用Lombok注解
        .enableTableFieldAnnotation()  // 为表字段添加注解
        .build();

// 5. 整合配置并执行生成
AutoGenerator generator = new AutoGenerator(dataSourceConfig);
generator.global(globalConfig)
    .packageInfo(packageConfig)
    .strategy(strategyConfig)
    .execute();

效果验证:查看生成的代码结构

执行生成器后,将得到以下代码结构,符合Repository模式的设计规范:

src/main/java/com/company/project/
├── domain                # 领域模型层
│   ├── User.java
│   ├── Order.java
│   └── Product.java
├── mapper                # 数据访问映射层
│   ├── UserMapper.java
│   ├── OrderMapper.java
│   └── ProductMapper.java
└── repository            # 仓储层
    ├── IUserRepository.java
    ├── IOrderRepository.java
    ├── IProductRepository.java
    └── impl
        ├── UserRepository.java
        ├── OrderRepository.java
        └── ProductRepository.java

生成的IUserRepository接口将继承IBaseRepository,包含基础的数据访问方法:

public interface IUserRepository extends IBaseRepository<User> {
    // 继承自IBaseRepository的方法:
    // - save(User entity)
    // - update(User entity)
    // - deleteById(Serializable id)
    // - User getById(Serializable id)
    // - List<User> list()
    // ...其他通用方法
}

扩展技巧:增强Repository层功能

自定义基础Repository接口

创建功能丰富的基础Repository接口,为所有Repository提供通用方法:

public interface IBaseRepository<T> {
    /**
     * 保存实体
     */
    boolean save(T entity);
    
    /**
     * 更新实体
     */
    boolean update(T entity);
    
    /**
     * 根据ID删除
     */
    boolean deleteById(Serializable id);
    
    /**
     * 根据ID查询
     */
    T getById(Serializable id);
    
    /**
     * 查询所有
     */
    List<T> list();
    
    /**
     * 分页查询
     */
    Page<T> page(Page<T> page);
    
    /**
     * 条件查询
     */
    List<T> list(QueryWrapper<T> queryWrapper);
}

实现通用Repository基类

创建BaseRepositoryImpl实现类,提供基础方法的默认实现:

public class BaseRepositoryImpl<M extends BaseMapper<T>, T> 
        implements IBaseRepository<T> {

    @Autowired
    protected M baseMapper;

    @Override
    public boolean save(T entity) {
        return baseMapper.insert(entity) > 0;
    }

    @Override
    public boolean update(T entity) {
        return baseMapper.updateById(entity) > 0;
    }

    // 实现其他接口方法...
}

多模块项目配置

对于多模块项目,可以为不同模块配置独立的Repository生成规则:

// 为用户模块配置Repository生成
PackageConfig userPackageConfig = new PackageConfig.Builder()
    .parent("com.company.project.user")
    .entity("domain")
    .mapper("mapper")
    .service("repository")
    .serviceImpl("repository.impl")
    .build();

// 为订单模块配置Repository生成
PackageConfig orderPackageConfig = new PackageConfig.Builder()
    .parent("com.company.project.order")
    .entity("domain")
    .mapper("mapper")
    .service("repository")
    .serviceImpl("repository.impl")
    .build();

问题排查:常见配置错误及解决方法

错误1:基类找不到

错误表现:生成代码时提示"无法找到IBaseRepository类"

解决方法

  1. 检查superServiceClass配置的类全限定名是否正确
  2. 确保IBaseRepository接口已在项目中创建
  3. 如使用多模块项目,需确保依赖模块已正确引入

错误2:包名冲突

错误表现:生成的Repository类与其他类重名

解决方法

  1. 修改convertServiceFileName和convertServiceImplFileName的命名规则
  2. 调整packageConfig中的包路径配置
  3. 使用enableFileOverride()允许覆盖已有文件

错误3:Lombok注解未生效

错误表现:生成的实体类缺少getter/setter方法

解决方法

  1. 确保在entityBuilder中启用了enableLombok()
  2. 检查项目中是否已添加Lombok依赖
  3. IDE中是否安装了Lombok插件并启用注解处理

错误4:表名与实体名映射错误

错误表现:生成的Repository操作的表名不正确

解决方法

  1. 在strategyConfig中配置tablePrefix去除表前缀
  2. 使用convertFileName自定义实体名转换规则
  3. 检查数据库连接配置是否正确指向目标数据库

注意事项:确保配置正确实施

  1. 基础类准备:在执行生成器前,必须确保项目中已创建IBaseRepository接口和BaseRepositoryImpl实现类,否则会导致编译错误。

  2. 依赖配置:确认项目中已添加MyBatis-Plus Generator依赖,以及数据库驱动依赖:

<dependency>
    <groupId>com.baomidou</groupId>
    <artifactId>mybatis-plus-generator</artifactId>
    <version>最新版本</version>
</dependency>
  1. 版本兼容性:不同版本的MyBatis-Plus Generator配置方式可能存在差异,本文配置适用于3.5.1+版本。

  2. 代码规范:生成代码后,建议对生成的Repository接口添加@Repository注解,便于Spring自动扫描和管理。

  3. 自定义扩展:对于复杂业务场景,可通过实现ITemplate接口自定义代码生成模板,进一步定制Repository层实现。

通过以上配置,MyBatis-Plus Generator将能够生成符合Repository模式的代码结构,帮助团队建立规范的数据访问层架构,提升代码质量和开发效率。

登录后查看全文
热门项目推荐
相关项目推荐