MybatisPlus如何自定義TypeHandler映射JSON類型為List
自定義TypeHandler映射JSON類型為List
1. 實體類
這里只展示需要映射的字段,分別在所需映射的字段和實體類上添加注解。
@Data
@TableName(value = "report", autoResultMap = true)
public class Report {
private static final long serialVersionUID = 1L;
@ApiModelProperty("id")
@TableId(value = "id", type = IdType.AUTO)
private Integer id;
@ApiModelProperty("報名信息")
@TableField(typeHandler = ReportUserListTypeHandler.class)
private List<ReportUser> reportInfo;
}2. ListTypeHandler
提供一個 JSONArray 轉(zhuǎn)換為 Java List集合的處理器
import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.util.StrUtil;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.TypeReference;
import org.apache.ibatis.type.BaseTypeHandler;
import org.apache.ibatis.type.JdbcType;
import org.apache.ibatis.type.MappedJdbcTypes;
import org.apache.ibatis.type.MappedTypes;
import java.sql.CallableStatement;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;
@MappedJdbcTypes(JdbcType.VARBINARY)
@MappedTypes({List.class})
public abstract class ListTypeHandler<T> extends BaseTypeHandler<List<T>> {
@Override
public void setNonNullParameter(PreparedStatement ps, int i, List<T> parameter, JdbcType jdbcType) throws SQLException {
String content = CollUtil.isEmpty(parameter) ? null : JSON.toJSONString(parameter);
ps.setString(i, content);
}
@Override
public List<T> getNullableResult(ResultSet rs, String columnName) throws SQLException {
return this.getListByJsonArrayString(rs.getString(columnName));
}
@Override
public List<T> getNullableResult(ResultSet rs, int columnIndex) throws SQLException {
return this.getListByJsonArrayString(rs.getString(columnIndex));
}
@Override
public List<T> getNullableResult(CallableStatement cs, int columnIndex) throws SQLException {
return this.getListByJsonArrayString(cs.getString(columnIndex));
}
private List<T> getListByJsonArrayString(String content) {
return StrUtil.isBlank(content) ? new ArrayList<>() : JSON.parseObject(content, this.specificType());
}
/**
* 具體類型,由子類提供
*
* @return 具體類型
*/
protected abstract TypeReference<List<T>> specificType();
}3. ReportUserListTypeHandler
由具體的子類提供List集合泛型類型
import com.alibaba.fastjson.TypeReference;
import com.hanku.business.model.ReportUser;
import java.util.List;
public class ReportUserListTypeHandler extends ListTypeHandler<ReportUser> {
@Override
protected TypeReference<List<ReportUser>> specificType() {
return new TypeReference<List<ReportUser>>() {
};
}
}4. Java 泛型
如果在 ListTypeHandler 類中直接提供 TypeReference<List<T>> 這種類型,那就等效于TypeReference<List<Object>> 這種類型,后續(xù) fastjson 在轉(zhuǎn)換時無法確定具體的 Java 類型,轉(zhuǎn)換后的類型最終就會是 List<JSONObject> ;同理,如果使用 Jackson 作為 JSON 轉(zhuǎn)換工具,不確定具體類型時,最總會被轉(zhuǎn)換為LinkedHashMap 類型,都需要再使用 TypeReference 來轉(zhuǎn)換一次。
自定義TypeHandler的使用筆記
可通過自定義的TypeHandler實現(xiàn)某個屬性在插入數(shù)據(jù)庫以及查詢時的自動轉(zhuǎn)換,本例中是要將Map類型的屬性轉(zhuǎn)化成CLOB,然后存入數(shù)據(jù)庫。由于是復(fù)雜的Map,mp自帶的json轉(zhuǎn)換器會丟失部分信息。
類型轉(zhuǎn)換器還可以通過注解配置 java類型和jdbc類型
@MappedTypes:注解配置 java 類型@MappedJdbcTypes:注解配置 jdbc 類型
定義
@Slf4j
@MappedTypes({Object.class})
@MappedJdbcTypes(JdbcType.VARCHAR)
public class WeightListTypeHandler ?extends AbstractJsonTypeHandler<Object> {
? ? private static Gson gson = new Gson();
? ? private final Class<?> type;
? ? public WeightListTypeHandler(Class<?> type) {
? ? ? ? if (log.isTraceEnabled()) {
? ? ? ? ? ? log.trace("WeightListTypeHandler(" + type + ")");
? ? ? ? }
? ? ? ? Assert.notNull(type, "Type argument cannot be null");
? ? ? ? this.type = type;
? ? }
? ? @Override
? ? protected Object parse(String json) {
? ? ? ? Type type1 = new TypeToken<Map<String, List<WeightItem>>>(){}.getType();
? ? ? ? return gson.fromJson(json, type1);
? ? }
? ? @Override
? ? protected String toJson(Object obj) {
? ? ? ? return gson.toJson(obj);
? ? }
? ? public static void setGson(Gson gson) {
? ? ? ? Assert.notNull(gson, "Gson should not be null");
? ? ? ? WeightListTypeHandler.gson = gson;
? ? }
}使用
注意@TableName 注解 autoResultMap 屬性
@Data
@NoArgsConstructor
@TableName(value = "mix_target",autoResultMap = true)
public class MixTarget extends Model<MixTarget> {
@TableId(value = "id", type = IdType.AUTO)
private Long id;
/**
*指標描述
*/
@TableField("description")
private String description;
/**
* 指標名
*/
@TableField("name")
private String name;
/**
* 對應(yīng)屬性名
*/
@TableField("property_name")
private String propertyName;
/**
* 起始點類型
*/
@TableField("source_type")
private String sourceType;
/**
* 屬性對應(yīng)權(quán)值列表
* key 屬性名 value指定條件下的權(quán)值
*/
@TableField(value = "weight_list",typeHandler = WeightListTypeHandler.class,jdbcType = JdbcType.CLOB)
private Map<String, List<WeightItem>> weightList;
/**
* 運行狀態(tài)
* 0 新建未運行
* 1 運行中
* 2 已運行 成功
* 3 已運行 失敗
*/
@TableField("status")
private Integer status;
/**
* 是否可用
* 1 true
* 0 false
*/
@TableField("enable")
private Integer enable;
@TableField("create_time")
private LocalDateTime createTime;
}
以上為個人經(jīng)驗,希望能給大家一個參考,也希望大家多多支持腳本之家。
相關(guān)文章
java 通過發(fā)送json,post請求,返回json數(shù)據(jù)的方法
下面小編就為大家分享一篇java 通過發(fā)送json,post請求,返回json數(shù)據(jù)的方法,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧2018-03-03
springboot中restful風(fēng)格請求的使用方法示例
RESTful是一種web軟件風(fēng)格,它不是標準也不是協(xié)議,它不一定要采用,只是一種風(fēng)格,它倡導(dǎo)的是一個資源定位(url)及資源操作的風(fēng)格,下面這篇文章主要給大家介紹了關(guān)于springboot中restful風(fēng)格請求的使用方法,需要的朋友可以參考下2023-02-02

