MybatisPlus 处理保存实体对象时,对于枚举类型的数据库存储问题
- 1. 前言
- 1.1 先看问题代码
- 1.2 存在的问题
- 2. 解决前言问题
- 2.1 自定义枚举
- 2.2 附源码:
- 3. 参考
- 4. 推荐 Mybatis、MybatisPlus 其他相关问题的文章
1. 前言
1.1 先看问题代码
- 如下:
- 枚举类:
- 实体:
用自带的枚举解析器:@TableField(typeHandler = EnumTypeHandler.class)
- service 里:(
通过mybatisPlus自带方法保存对象
)
1.2 存在的问题
- 发现问题,如下:
数据库存的不是我想要的枚举的key,想存 1 和 2,这种方式没有实现
- 所以需自己写枚举转换器
2. 解决前言问题
2.1 自定义枚举
- 看代码:
核心代码还是看下面源码吧 - 看效果:
问题解决
2.2 附源码:
- MyBaseEnum.java
package com.liu.susu.enums.handler; /** * description * * @author susu * @date 2022-12-01 **/ public interface MyBaseEnum { Object getCode(); String getDesc(); }
- ValueEnumTypeHandler.java
package com.liu.susu.enums.handler; import org.apache.ibatis.type.BaseTypeHandler; import org.apache.ibatis.type.JdbcType; import org.apache.ibatis.type.MappedTypes; import java.sql.CallableStatement; import java.sql.PreparedStatement; import java.sql.ResultSet; import java.sql.SQLException; /** * 值枚举转换处理器 * @param <E> 枚举类型 */ @MappedTypes({MyBaseEnum.class}) public class ValueEnumTypeHandler<E extends Enum<?> & MyBaseEnum> extends BaseTypeHandler<MyBaseEnum> { private Class<E> type; public ValueEnumTypeHandler(Class<E> type) { if (type == null) { throw new IllegalArgumentException("Type argument cannot be null"); } this.type = type; } @Override public void setNonNullParameter(PreparedStatement ps, int i, MyBaseEnum parameter, JdbcType jdbcType) throws SQLException { // ps.setInt(i, parameter.getCode()); ps.setObject(i, parameter.getCode()); } @Override public E getNullableResult(ResultSet rs, String columnName) throws SQLException { int code = rs.getInt(columnName); return rs.wasNull() ? null : codeOf(code); } @Override public E getNullableResult(ResultSet rs, int columnIndex) throws SQLException { int code = rs.getInt(columnIndex); return rs.wasNull() ? null : codeOf(code); } @Override public E getNullableResult(CallableStatement cs, int columnIndex) throws SQLException { int code = cs.getInt(columnIndex); return cs.wasNull() ? null : codeOf(code); } private E codeOf(int code){ try { return codeOf(type, code); } catch (Exception ex) { throw new IllegalArgumentException("Cannot convert" + code + "to" + type.getSimpleName() + "by code value.", ex); } } private static <E extends Enum<?> & MyBaseEnum> E codeOf(Class<E> enumClass, Object code) { E[] enumConstants = enumClass.getEnumConstants(); for (E e : enumConstants) { if (e.getCode() == code) { return e; } } return null; } }
- SexEnum.java
package com.liu.susu.enums; import com.baomidou.mybatisplus.annotation.EnumValue; import com.liu.susu.enums.handler.MyBaseEnum; public enum SexEnum implements MyBaseEnum { BOY("1","男孩"), GIRL("2","女孩"); // @EnumValue private String code; private String desc; SexEnum(String code, String desc) { this.code = code; this.desc = desc; } @Override public String getCode() { return this.code; } @Override public String getDesc() { return this.desc; } }
- 实体(实体里要注意换成
ValueEnumTypeHandler
):@TableField(typeHandler = ValueEnumTypeHandler.class) private SexEnum sex;
3. 参考
- 上述源码参考文章地址:
基于 SpringBoot+MybatisPlus+Jackson 优雅使用枚举值的方案.
4. 推荐 Mybatis、MybatisPlus 其他相关问题的文章
- 关于mybatis 枚举的其他问题可以看下面文章
- Mysql + Mybatis 开发中的各种小问题
- mybatis自定义枚举类型的转换器以及各种使用场景.
- springBoot项目 ObjectMapper 序列化统一格式处理(含枚举问题)
- 解决 LocalDateTime 的序列化与反序列化问题
- springboot项目前后端分离:统一返回数据格式+mybatis 分页(含枚举格式统一)
- MybatisPlus简单使用与自定义sql以及通过自定义sql实现多表联查的分页查询
- 解决雪花算法id精度丢失问题(自定义序列化类将Set<Long> 转化成 Set<String>)
- mybatis调用Oracle存储过程(给出无参、入参、出参调用等详细例子)——真的的保姆级别.