一 通用枚举

解决了繁琐的配置,让 mybatis 优雅的使用枚举属性!

3.1.0开始,可配置默认枚举处理类来省略扫描通用枚举配置 默认枚举配置

  • 升级说明:

    3.1.0 以下版本改变了原生默认行为,升级时请将默认枚举设置为EnumOrdinalTypeHandler

  • 影响用户:

    实体中使用原生枚举

  • 其他说明:

    配置枚举包扫描的时候能提前注册使用注解枚举的缓存

  • 推荐配置:

    • 使用实现

      IEnum

      接口

      • 推荐配置defaultEnumTypeHandler

    • 使用注解枚举处理

      • 推荐配置typeEnumsPackage

    • 注解枚举处理与

      IEnum

      接口

      • 推荐配置typeEnumsPackage

    • 与原生枚举混用

      • 需配置defaultEnumTypeHandlertypeEnumsPackage

申明通用枚举属性

方式一: 使用 @EnumValue 注解枚举属性 完整示例

public enum GradeEnum {

PRIMARY(1, "小学"), SECONDORY(2, "中学"), HIGH(3, "高中");

GradeEnum(int code, String descp) {
this.code = code;
this.descp = descp;
}

@EnumValue//标记数据库存的值是code
private final int code;
//。。。
}

方式二: 枚举属性,实现 IEnum 接口如下:

public enum AgeEnum implements IEnum<Integer> {
ONE(1, "一岁"),
TWO(2, "二岁"),
THREE(3, "三岁"); private int value;
private String desc; @Override
public Integer getValue() {
return this.value;
}
}

实体属性使用枚举类型

public class User{
/**
* 名字
* 数据库字段: name varchar(20)
*/
private String name; /**
* 年龄,IEnum接口的枚举处理
* 数据库字段:age INT(3)
*/
private AgeEnum age; /**
* 年级,原生枚举(带{@link com.baomidou.mybatisplus.annotation.EnumValue}):
* 数据库字段:grade INT(2)
*/
private GradeEnum grade;
}

二 代码

  • pom.xml

    <dependencies>
    <dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter</artifactId>
    </dependency>
    <dependency>
    <groupId>com.baomidou</groupId>
    <artifactId>mybatis-plus-boot-starter</artifactId>
    <version>3.2.0</version>
    </dependency>
    <dependency>
    <groupId>org.projectlombok</groupId>
    <artifactId>lombok</artifactId>
    </dependency>
    <!-- https://mvnrepository.com/artifact/p6spy/p6spy -->
    <dependency>
    <groupId>p6spy</groupId>
    <artifactId>p6spy</artifactId>
    <version>3.8.0</version>
    </dependency>
    <dependency>
    <groupId>com.h2database</groupId>
    <artifactId>h2</artifactId>
    <scope>runtime</scope>
    </dependency>

    <dependency>
    <groupId>com.alibaba</groupId>
    <artifactId>fastjson</artifactId>
    <version>1.2.49</version>
    <scope>test</scope>
    </dependency>
    <!-- for testing -->
    <dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-test</artifactId>
    <scope>test</scope>
    </dependency>
    <dependency>
    <groupId>com.alibaba</groupId>
    <artifactId>fastjson</artifactId>
    <version>RELEASE</version>
    <scope>compile</scope>
    </dependency>
    </dependencies>
  • application.yml

    spring:
    datasource:
    driver-class-name: com.p6spy.engine.spy.P6SpyDriver
    url: jdbc:p6spy:h2:tcp://192.168.180.115:19200/~/mem/test
    username: root
    password: test

    # MP 配置
    mybatis-plus:
    type-enums-package: com.mp.sampleenum.enums
    configuration:
    # 3.0.8之前版本问题默认将枚举注册为EnumOrdinalTypeHandler,这是错误的方式,默认是 org.apache.ibatis.type.EnumTypeHandler
    # 如果项目之中实体统一使用IEnum或注解的方式,可配置成 com.baomidou.mybatisplus.extension.handlers.EnumTypeHandler,也可省略上面的type-enums-package配置
    # 配置type-enums-package只对注解方式的枚举处理能提前加载缓存.
    default-enum-type-handler: org.apache.ibatis.type.EnumOrdinalTypeHandler
  • 配置类

    @Configuration
    @MapperScan("com.mp.sampleenum.mapper")
    public class MybatisPlusConfig {

    }
  • 实体类

    @EqualsAndHashCode(callSuper = true)
    @Data
    @Accessors(chain = true)
    public class User extends BaseEntity {

    private String name;

    private String email;

    /**
    * IEnum接口的枚举处理
    */
    private AgeEnum age;

    /**
    * 原生枚举: 默认使用枚举值顺序: 0:MALE, 1:FEMALE
    */

    private GenderEnum gender;

    /**
    * 原生枚举(带{@link com.baomidou.mybatisplus.annotation.EnumValue}):
    * 数据库的值对应该注解对应的属性
    */
    @JSONField(serialzeFeatures= SerializerFeature.WriteEnumUsingToString)
    private GradeEnum grade;


    private UserState userState;

    }

    @Data
    @Accessors(chain = true)
    public class BaseEntity {
    private Long id;

    }
  • 枚举

    @Getter
    public enum AgeEnum implements IEnum<Integer> {
    ONE(1, "一岁"),
    TWO(2, "二岁"),
    THREE(3, "三岁");

    private final int value;
    private final String desc;

    AgeEnum(final int value, final String desc) {
    this.value = value;
    this.desc = desc;
    }

    @Override
    public Integer getValue() {
    return value;
    }
    }


    public enum GenderEnum {
    MALE,
    FEMALE;
    }

    @Getter
    //@JSONType(serializeEnumAsJavaBean = true)
    public enum GradeEnum {

    PRIMARY(1, "小学"),
    SECONDORY(2, "中学"),
    HIGH(3, "高中");

    GradeEnum(int code, String descp) {
    this.code = code;
    this.descp = descp;
    }

    //@EnumValue
    private final int code;
    @EnumValue
    private final String descp;

    }


    @Getter
    public enum UserState implements IBaseEnum<Integer> {

    ACTIVE(1, "A"),
    INACTIVE(2, "I");

    private final int state;
    private final String descp;

    UserState(int state, String descp) {
    this.state = state;
    this.descp = descp;

    }

    @Override
    public Integer getValue() {
    return state;
    }

    @Override
    public String getDescription() {
    return descp;
    }
    }

    public interface IBaseEnum<T extends Serializable> extends IEnum<T>{

    String getDescription();
    }

    注:推荐加注解的方式,GradeEnum这个枚举想要插入String类型,用Fastjson进行序列化。

  • 测试类

    @SpringBootTest
    class SampleEnumApplicationTests {

    @Resource
    private UserMapper mapper;

    @Test
    public void insert() {
    User user = new User();
    user.setName("K神");
    user.setAge(AgeEnum.ONE);
    user.setGrade(GradeEnum.HIGH);
    user.setGender(GenderEnum.MALE);
    user.setEmail("abc@mp.com");
    user.setUserState(UserState.ACTIVE);
    Assert.assertTrue(mapper.insert(user) > 0);
    // 成功直接拿会写的 ID
    System.err.println("\n插入成功 ID 为:" + user.getId());

    List<User> list = mapper.selectList(null);
    for (User u : list) {
    System.out.println(u);
    Assert.assertNotNull("age should not be null", u.getAge());
    if (u.getId().equals(user.getId())) {
    Assert.assertNotNull("gender should not be null", u.getGender());
    Assert.assertNotNull("grade should not be null", u.getGrade());

    }
    }
    }

    @Test
    public void delete() {
    Assert.assertTrue(mapper.delete(new QueryWrapper<User>()
    .lambda().eq(User::getAge, AgeEnum.TWO)) > 0);
    }

    @Test
    public void update() {
    Assert.assertTrue(mapper.update(new User().setAge(AgeEnum.TWO),
    new QueryWrapper<User>().eq("age", AgeEnum.THREE)) > 0);
    }

    @Test
    public void select() {
    User user = mapper.selectOne(new QueryWrapper<User>().lambda().eq(User::getId, 2));
    Assert.assertEquals("Jack", user.getName());
    Assert.assertTrue(AgeEnum.THREE == user.getAge());

    //#1500 github: verified ok. Not a bug
    List<User> userList = mapper.selectList(new QueryWrapper<User>().lambda().eq(User::getUserState, UserState.ACTIVE));
    Assert.assertEquals(3, userList.size());
    Optional<User> userOptional = userList.stream()
    .filter(x -> x.getId() == 1)
    .findFirst();
    userOptional.ifPresent(user1 -> Assert.assertTrue(user1.getUserState() == UserState.ACTIVE));
    }

    }
     
  • 测试结果

     Consume Time:0 ms 2019-10-31 14:42:38
    Execute SQL:INSERT INTO user ( id, gender, user_state, grade, name, age, email ) VALUES ( 1189794788921081858, 0, 1, '高中', 'K神', 1, 'abc@mp.com' )


    插入成功 ID 为:1189794788921081858
    Consume Time:6 ms 2019-10-31 14:42:38
    Execute SQL:SELECT id,gender,user_state,grade,name,age,email FROM user

SpringBoot与MybatisPlus3.X整合之通用枚举(十二)的更多相关文章

  1. Spring+SpringMVC+MyBatis+easyUI整合基础篇(十二)阶段总结

    不知不觉,已经到了基础篇的收尾阶段了,看着前面的十几篇文章,真的有点不敢相信,自己竟然真的坚持了下来,虽然过程中也有过懒散和焦虑,不过结果还是自己所希望的,克服了很多的问题,将自己的作品展现出来,也发 ...

  2. SpringBoot与MybatisPlus3.X整合示例(十六)

    包含 分页.逻辑删除.自定义全局操作 等绝大部分常用功能的使用示例,相当于大整合的完整示例 pom.xml <dependencies> <dependency> <gr ...

  3. SpringBoot与MybatisPlus3.X整合之字段类型处理器(八)

    pom.xml <dependencies> <dependency> <groupId>org.springframework.boot</groupId& ...

  4. SpringBoot与MybatisPlus3.X整合之动态表名 SQL 解析器(七)

    pom.xml <dependencies> <dependency> <groupId>org.springframework.boot</groupId& ...

  5. Spring+SpringMVC+MyBatis+easyUI整合优化篇(十二)数据层优化-explain关键字及慢sql优化

    本文提要 从编码角度来优化数据层的话,我首先会去查一下项目中运行的sql语句,定位到瓶颈是否出现在这里,首先去优化sql语句,而慢sql就是其中的主要优化对象,对于慢sql,顾名思义就是花费较多执行时 ...

  6. Spring+SpringMVC+MyBatis+easyUI整合进阶篇(十二)Spring集成Redis缓存

    作者:13 GitHub:https://github.com/ZHENFENG13 版权声明:本文为原创文章,未经允许不得转载. 整合Redis 本来以为类似的Redis教程和整合代码应该会很多,因 ...

  7. Spring+SpringMVC+MyBatis+easyUI整合进阶篇(十五)阶段总结

    作者:13 GitHub:https://github.com/ZHENFENG13 版权声明:本文为原创文章,未经允许不得转载. 一 每个阶段在结尾时都会有一个阶段总结,在<SSM整合基础篇& ...

  8. 新手之:SpringBoot ——Reids主从哨兵整合(CentOS7)

    一.Redis主从搭建(一台服务器模拟多个端口) 结构图:) 1.确保安装了Redis,我装在了/opt/redis目录下.可通过"whereis redis-cli"命令查看是否 ...

  9. (七) SpringBoot起飞之路-整合SpringSecurity(Mybatis、JDBC、内存)

    兴趣的朋友可以去了解一下前五篇,你的赞就是对我最大的支持,感谢大家! (一) SpringBoot起飞之路-HelloWorld (二) SpringBoot起飞之路-入门原理分析 (三) Sprin ...

随机推荐

  1. 初识PE文件结构

    前言 目前网络上有关PE文件结构说明的文章太多了,自己的这篇文章只是单纯的记录自己对PE文件结构的学习.理解和总结. 基础概念 PE(Portable Executable:可移植的执行体)是Win3 ...

  2. Spring 梳理 - @Component

    使用@Component注解,表示该类定义为Spring管理Bean,使用默认value(可选)属性表示Bean标识符.如果不指定标识符,默认为首字母小写类名.例如类UserController的标识 ...

  3. JVM 调优 - jhat

    Java命令学习系列(五)——jhat 2016-01-21 分类:Java 阅读(8708) 评论(3) 阿里大牛珍藏架构资料,点击链接免费获取 jhat(Java Heap Analysis To ...

  4. volatile 关键字的作用

    简介Java 语言提供了一种稍弱的同步机制,即 volatile 变量,用来确保将变量的更新操作通知到其他线程.volatile 变量具备两种特性:变量可见性.禁止重排序. 作为同步锁在访问 vola ...

  5. 面试|简单描述MySQL中,索引,主键,唯一索引,联合索引 的区别,对数据库的性能有什么影响(从读写两方面)

    索引是一种特殊的文件(InnoDB 数据表上的索引是表空间的一个组成部分),它们 包含着对数据表里所有记录的引用指针. 普通索引(由关键字 KEY 或 INDEX 定义的索引)的唯一任务是加快对数据的 ...

  6. 总结下var、let 和 const 的区别

    一.var变量 <!DOCTYPE html> <html lang="en"> <head> <meta charset="U ...

  7. STM32之串口DMA接收不定长数据

    STM32之串口DMA接收不定长数据 引言 在使用stm32或者其他单片机的时候,会经常使用到串口通讯,那么如何有效地接收数据呢?假如这段数据是不定长的有如何高效接收呢? 同学A:数据来了就会进入串口 ...

  8. c#之线程基础(一)

    可以认为线程是一个虚拟进程,用于独立运行一个特定的程序. 1.使用c#创建线程 using System; using System.Threading; //3 namespace MutiThre ...

  9. Orecle基本概述(1)

    Orecle1.什么是orecle及体系结构?* 全局数据库,指物理磁盘数据库,一个真实存在的磁盘目录.*用户: 用户在oracle里面是用来隔离数据的*表空间: 逻辑结构,不可视的,虚拟的,用户的数 ...

  10. Vue3都使用Proxy了,你更应该了解Proxy

    vue3.0的pre-alpha版代码已经开源了,就像作者之前放出的消息一样,其数据响应这一部分已经由ES6的Proxy来代替Object.defineProperty实现,感兴趣的同学可以看其实现源 ...