Mybatis自动映射Java对象 与 MySQL8后的JSON数据
文章目录
- Mybatis自动映射Java对象 与 MySQL8后的JSON数据
- 1.转化成为正常Json类型
- 1.1 JsonTypeHander
- 1.2 ListJsonTypeHandler 负责List<T> 类型
- 1.3 实体类
- 1.4 mapper
- 1.5 测试类
- 2. 存储为携带类型的Json
Mybatis自动映射Java对象 与 MySQL8后的JSON数据
1.转化成为正常Json类型
自认为
优点:数据库存储为单纯的数据,不需要额外存储类型
缺点:不够通用 对于Map、Object、List<T>能用,但是对于List<List<T>>不太行需要写两个Typehander不够优雅
接下来,简单过一下流程(只有插入和查找)
1.1 JsonTypeHander
notice: 使用的转换JSON工具是hutool中的,如果自己有别的转换可以使用别的json转换工具
hutool工具包
<dependency><groupId>cn.hutool</groupId><artifactId>hutool-all</artifactId><version>5.8.11</version></dependency>
JsonTypeHandler 这个负责非List,一般存储的都是Map,Object,和List
public class JsonTypeHandler<T> extends BaseTypeHandler<T>{private Class<T> clazz;//在Mybatis中将类型注入进来public JsonTypeHandler(Class<T> clazz) {this.clazz = clazz;}//写入数据@Overridepublic void setNonNullParameter(PreparedStatement ps, int i, Object parameter, JdbcType jdbcType) throws SQLException {ps.setString(i, JSONUtil.toJsonStr(parameter));}/*** 一般是根据列名字获取下方就不再详述“(因为我也不知道,还没用到)* @param rs 结果* @param colName 列名*/@SneakyThrows@Overridepublic T getNullableResult(ResultSet rs, String colName) {String data = rs.getString(colName);return StrUtil.isBlank(data) ? null : JSONUtil.toBean(data, clazz);}@SneakyThrows@Overridepublic T getNullableResult(ResultSet rs, int colIndex) {String data = rs.getString(colIndex);return StrUtil.isBlank(data) ? null : JSONUtil.toBean(data, clazz);}@SneakyThrows@Overridepublic T getNullableResult(CallableStatement cs, int i) {String data = cs.getString(i);return StrUtil.isBlank(data) ? null : JSONUtil.toBean(data, clazz);}}
1.2 ListJsonTypeHandler 负责List 类型
public class ListJsonTypeHandler<T> extends BaseTypeHandler<List<T>> implements InitializingBean {private Class<T> clazz;public ListJsonTypeHandler(Class<T> clazz) {this.clazz = clazz;}@Overridepublic void setNonNullParameter(PreparedStatement ps, int i, List<T> parameter, JdbcType jdbcType) throws SQLException {ps.setString(i, JSONUtil.toJsonStr(parameter));}@Overridepublic List<T> getNullableResult(ResultSet rs, String columnName) throws SQLException {String data = rs.getString(columnName);return StrUtil.isBlank(data) ? null : JSONUtil.parseArray(data).toList(clazz);}@SneakyThrows@Overridepublic List<T> getNullableResult(ResultSet rs, int colIndex) {String data = rs.getString(colIndex);return StrUtil.isBlank(data) ? null : JSONUtil.parseArray(data).toList(clazz);}@SneakyThrows@Overridepublic List<T> getNullableResult(CallableStatement cs, int i) {String data = cs.getString(i);return StrUtil.isBlank(data) ? null : JSONUtil.parseArray(data).toList(clazz);}
1.3 实体类
@Data
@AllArgsConstructor
@NoArgsConstructor
@Builder
public class Json {/*** 唯一标识*/private Integer id;/*** map*/private Map<String,Object> mapJson;/*** 对象* 这个对象自定义的放在下面*/private Object objJson;/*** list集合* <? extends Object>这个我也不知道怎么设置 但是用这个没错*/private List<? extends Object> listJson;
}//测试的对象
@Data
@AllArgsConstructor
@NoArgsConstructor
@Builder
public class JsonObj {/*** 唯一id*/private Integer id;/*** 测试所用*/private String str;
}
1.4 mapper
//查找 不建议用 * 代替 我是为啦偷工减料@Select(" SELECT * from json ")@Results(value = {@Result(property = "id", column = "id"),@Result(property = "mapJson", column = "mapJson", typeHandler = JsonTypeHandler.class,javaType = HashMap.class),@Result(property = "objJson", column = "objJson", typeHandler = JsonTypeHandler.class,javaType = JsonObj.class),@Result(property = "listJson", column = "listJson", typeHandler = ListJsonTypeHandler.class,javaType = JsonObj.class)})List<Json> select1();
// 增加@Insert("insert into json( mapJson, objJson, listJson) values (#{mapJson,typeHandler=com.hb.springredis.typeHandler.JsonTypeHandler}," +"#{objJson,typeHandler=com.hb.springredis.typeHandler.JsonTypeHandler}," +"#{listJson,typeHandler=com.hb.springredis.typeHandler.JsonTypeHandler})")int insert1(Json vo);
1.5 测试类
@SpringBootTest
public class ProductTest {
//这个就是刚才放sql的mapper@AutowiredJsonMapper jsonMapper;@Testvoid test11() throws JsonProcessingException {JsonObj js = JsonObj.builder().str("这真的是一个简单的测试对象").build();Map<String,Object> map = new HashMap<>();map.put("gaga","乱杀");List<JsonObj> jsonObjs = new ArrayList<>();for (int i = 0; i < 10; i++) {JsonObj js0 = JsonObj.builder().id(i).str("这真的是一个简单的测试对象").build();jsonObjs.add(js0);}Json build = Json.builder().mapJson(map).listJson(jsonObjs).objJson(js).build();jsonMapper.insert1(build);}@Testvoid test12(){List<Json> select = jsonMapper.select1();System.out.println(select);}}

2. 存储为携带类型的Json
因为在java在编译的时候是泛型擦除的,所以对于,List里面的类型无法确定,于是便可以把数据类型存入数据库之中,并且不需要再指出java类型

实体类还和上面一样,只需调整mapper中,对应的typeHandler即可
@Select(" SELECT * from json ")@Results(value = {@Result(property = "id", column = "id"),@Result(property = "mapJson", column = "mapJson", typeHandler = JsonTypeHandler2.class),@Result(property = "objJson", column = "objJson", typeHandler = JsonTypeHandler2.class),@Result(property = "listJson", column = "listJson", typeHandler = JsonTypeHandler2.class)})List<Json> select();@Insert("insert into json( mapJson, objJson, listJson) values (#{mapJson,typeHandler=com.hb.springredis.typeHandler.JsonTypeHandler2}," +"#{objJson,typeHandler=com.hb.springredis.typeHandler.JsonTypeHandler2}," +"#{listJson,typeHandler=com.hb.springredis.typeHandler.JsonTypeHandler2})")int insert(Json vo);

ListJsonTypehander2
public class ListJsonTypeHandler<T> extends BaseTypeHandler<List<T>>{private Class<T> clazz;public ListJsonTypeHandler(Class<T> clazz) {this.clazz = clazz;}@Overridepublic void setNonNullParameter(PreparedStatement ps, int i, List<T> parameter, JdbcType jdbcType) throws SQLException {ps.setString(i, JSONUtil.toJsonStr(parameter));}@Overridepublic List<T> getNullableResult(ResultSet rs, String columnName) throws SQLException {String data = rs.getString(columnName);return StrUtil.isBlank(data) ? null : JSONUtil.parseArray(data).toList(clazz);}@SneakyThrows@Overridepublic List<T> getNullableResult(ResultSet rs, int colIndex) {String data = rs.getString(colIndex);return StrUtil.isBlank(data) ? null : JSONUtil.parseArray(data).toList(clazz);}@SneakyThrows@Overridepublic List<T> getNullableResult(CallableStatement cs, int i) {String data = cs.getString(i);return StrUtil.isBlank(data) ? null : JSONUtil.parseArray(data).toList(clazz);}
}
测试类,和上面基本类似
@Testvoid test() throws JsonProcessingException {JsonObj js = JsonObj.builder().str("这真的是一个简单的测试对象").build();Map<String,Object> map = new HashMap<>();map.put("gaga","乱杀");List<JsonObj> jsonObjs = new ArrayList<>();for (int i = 0; i < 10; i++) {JsonObj js0 = JsonObj.builder().id(i).str("这真的是一个简单的测试对象").build();jsonObjs.add(js0);}Json build = Json.builder().mapJson(map).listJson(jsonObjs).objJson(js).build();jsonMapper.insert(build);}@Testvoid test1(){List<Json> select = jsonMapper.select();System.out.println(select);}
相关文章:
Mybatis自动映射Java对象 与 MySQL8后的JSON数据
文章目录 Mybatis自动映射Java对象 与 MySQL8后的JSON数据1.转化成为正常Json类型1.1 JsonTypeHander1.2 ListJsonTypeHandler 负责List<T> 类型1.3 实体类1.4 mapper1.5 测试类 2. 存储为携带类型的Json Mybatis自动映射Java对象 与 MySQL8后的JSON数据 1.转化成为正常…...
【JavaScript】深拷贝和浅拷贝
在 JavaScript 中,深拷贝(Deep Copy)和浅拷贝(Shallow Copy)是两种不同的对象复制方法,它们涉及到如何复制对象的属性以及如何处理对象内部的嵌套引用。以下是它们的解释: 浅拷贝(S…...
【SLAM】10.纵观SLAM,对比方案和未来方向
"天下谁人配白衣” SLAM方案研究方向 SLAM方案 站在历史角度,看一下为SLAM的发展带来贡献的方案: 2007年—A.J.Davison—MonoSLAM 视觉SLAM的先驱,建立在EKF基础上,此前基本无法在线运行,意义较大;…...
PyTorch中DistributedDataParallel使用笔记
1. 基本概念 在使用DistributedDataParallel时有一些概率必须掌握 多机多卡含义world_size代表有几台机器,可以理解为几台服务器rank第几台机器,即第几个服务器local_rank某台机器中的第几块GPU 单机多卡含义world_size代表机器一共有几块GPUrank第几…...
前端面试的话术集锦第 18 篇博文——高频考点(HTTP协议 TLS协议)
这是记录前端面试的话术集锦第十八篇博文——高频考点(HTTP协议 & TLS协议),我会不断更新该博文。❗❗❗ 1. HTTP 请求中的内容 HTTP请求由三部分构成,分别为: 请求行 首部 实体 请求行大概长这样GET /images/logo.gif HTTP/1.,基本由请求方法、URL、协议版本组成,…...
SQL Server 数据库变成单个用户怎么办
参考技术A 1、首先我们打开SQL SERVER的管理控制台,找到一个要设置角色的用户。 2、下面我们将为这个用户赋予创建数据库的角色,我们先用这个用户登录管理工具看一下是否具有创建用户的权限。 3、进行数据库创建的时候,提示如下的错误&…...
错过成考报名,今年你还有这两种方式升学!
2023年广东成人高考已经报名结束啦 错过报名或没有抢到考位的同学不用伤心 你还有另外两个提升学历的机会 开放大学or小自考 今天一起来了解一下吧~ 什么是开放大学? 开放教育其实也就是开放大学,也就是我们所说的中央广播电视大学,现在…...
【2023】从事务的特征以及解决方式上分析MySQL是如何保证事务的
----以MySQL的InnoDB介绍 目录 前言事务,事务到底是什么? 一、事务的特征:二、事务特征具体保证1、Redo Log(重做日志) ---保证事务的持久性1.1、🟡刷盘时机1.2、redo log记录形式1.3、redo log日志的好处 2、undo log(回滚日志)…...
MTR 网络连通性测试工具 基础入门 整理
MTR MTR的全称是 my traceroute,是一个集合了 ping 与 traceroute 功能的网络诊断工具,广泛应用于链路测试。相对于 traceroute 只会做一次链路跟踪测试,mtr会对链路上的相关节点做持续探测并给出相应的统计信息。因此,mtr能避免…...
Linux安装mysql数据库并实现主从搭建
一.环境说明 【环境说明】: 192.168.110.161 mysql-master ##网络配置到位,防火墙关闭,selinux关闭 192.168.110.162 mysql-slave ##网络配置到位,防火墙关闭,selinux关闭 两台主机,操作系统是centos7…...
windows使用小技巧之windows照片查看器无法显示此图片
碰到过好几次了,以前没有理会,今天特意去查了一下解决方法,不然确实不太方便。 1、打开“颜色管理”-“高级”: 2、将“设备配置文件”选择为“Agfa:Swop Standard” 3、关闭,重新打开图片,好…...
ez_pz_hackover_2016
ez_pz_hackover_2016 Arch: i386-32-little RELRO: Full RELRO Stack: No canary found NX: NX disabled PIE: No PIE (0x8048000) RWX: Has RWX segments32位,保护全关 int chall() {size_t v0; // eaxint result; // eaxchar s[1024]…...
解决方案| anyRTC远程检修应用场景
背景 在这个科技飞速发展的时代,各行各业都要求高效运转。然而,当出现问题时,我们却常常因为无法及时解决而感到困扰,传统解决问题的方式是邀请技术人员现场解决问题,如果技术人员解决不了,还要邀请专家从…...
IC芯片测试:如何对芯片静态功耗进行测试?
静态功耗也叫静态电流,是指芯片在静止状态下的电流或者是指芯片在不受外界因素影响下自身所消耗的电流。静态功耗对于芯片来说是衡量一款芯片的功耗与效率非常重要的指标。 传统手动测试静态功耗只需在芯片的输入端串上一台万用表,然后对芯片各个端口添加…...
Redis面试二“缓存击穿是什么”
条件 缓存击穿是应为Redis某个缓存数据设置了过期时间,而刚好有大并发数据请求这个数据,导致DB有大量请求,引发DB崩溃。 第一种方法就是设置互称锁 当缓存失效时不立即删除缓存而是用setnx设置一个互斥锁,当操作完成后在load db…...
python使用apscheduler每隔一段时间自动化运行程序
apscheduler使用比较简单,每隔一段时间自动化运行的步骤是: 创建调度器scheduler BlockingScheduler()添加任务scheduler.add_job(函数名, interval, minutes30) # 每隔30分钟运行一次直接执行:scheduler.start()示例代码 from datetime i…...
2023 Sui Builder House全球之旅圆满收官
2023年的最后一场Builder House于上周在新加坡举行,包括主题演讲、小组讨论和研讨会等聚焦Sui的现在和未来的活动。其中,zkLogin是本次活动的最大亮点。作为一种新的Sui原语,zkLogin允许用户使用Web2身份验证创建帐户,有望推动大规…...
OpenCV自学笔记二十三:K近邻算法
K近邻算法(K-Nearest Neighbors,简称KNN)是一种常用的监督学习算法,可以用于分类和回归问题。在OpenCV中,KNN算法有相应的函数实现,主要包含在ml模块中。 KNN算法的原理很简单,它基于样本之间的…...
ChatGLM-中英对话大模型-6B试用说明
ChatGLM-中英对话大模型-6B试用说明 搭建环境下载模型测试模型结果 搭建环境 pip install modelscope1.4.3 -f https://modelscope.oss-cn-beijing.aliyuncs.com/releases/repo.html pip install protobuf3.20.0 transformers4.27.1 icetk cpm_kernels下载模型 from modelsco…...
小白入门pytorch(一)
本文为小白入门Pytorch中的学习记录博客 小白入门pytorch 基础知识 导入torch,查看torch版本 import torch print(torch.__version__)输出结果: 1.12.1cu113张量 在pytorch中,张量(tensor)是最基本的数据结构。 …...
idea大量爆红问题解决
问题描述 在学习和工作中,idea是程序员不可缺少的一个工具,但是突然在有些时候就会出现大量爆红的问题,发现无法跳转,无论是关机重启或者是替换root都无法解决 就是如上所展示的问题,但是程序依然可以启动。 问题解决…...
MFC内存泄露
1、泄露代码示例 void X::SetApplicationBtn() {CMFCRibbonApplicationButton* pBtn GetApplicationButton();// 获取 Ribbon Bar 指针// 创建自定义按钮CCustomRibbonAppButton* pCustomButton new CCustomRibbonAppButton();pCustomButton->SetImage(IDB_BITMAP_Jdp26)…...
使用分级同态加密防御梯度泄漏
抽象 联邦学习 (FL) 支持跨分布式客户端进行协作模型训练,而无需共享原始数据,这使其成为在互联和自动驾驶汽车 (CAV) 等领域保护隐私的机器学习的一种很有前途的方法。然而,最近的研究表明&…...
令牌桶 滑动窗口->限流 分布式信号量->限并发的原理 lua脚本分析介绍
文章目录 前言限流限制并发的实际理解限流令牌桶代码实现结果分析令牌桶lua的模拟实现原理总结: 滑动窗口代码实现结果分析lua脚本原理解析 限并发分布式信号量代码实现结果分析lua脚本实现原理 双注解去实现限流 并发结果分析: 实际业务去理解体会统一注…...
DBAPI如何优雅的获取单条数据
API如何优雅的获取单条数据 案例一 对于查询类API,查询的是单条数据,比如根据主键ID查询用户信息,sql如下: select id, name, age from user where id #{id}API默认返回的数据格式是多条的,如下: {&qu…...
前端开发面试题总结-JavaScript篇(一)
文章目录 JavaScript高频问答一、作用域与闭包1.什么是闭包(Closure)?闭包有什么应用场景和潜在问题?2.解释 JavaScript 的作用域链(Scope Chain) 二、原型与继承3.原型链是什么?如何实现继承&a…...
第 86 场周赛:矩阵中的幻方、钥匙和房间、将数组拆分成斐波那契序列、猜猜这个单词
Q1、[中等] 矩阵中的幻方 1、题目描述 3 x 3 的幻方是一个填充有 从 1 到 9 的不同数字的 3 x 3 矩阵,其中每行,每列以及两条对角线上的各数之和都相等。 给定一个由整数组成的row x col 的 grid,其中有多少个 3 3 的 “幻方” 子矩阵&am…...
Python 包管理器 uv 介绍
Python 包管理器 uv 全面介绍 uv 是由 Astral(热门工具 Ruff 的开发者)推出的下一代高性能 Python 包管理器和构建工具,用 Rust 编写。它旨在解决传统工具(如 pip、virtualenv、pip-tools)的性能瓶颈,同时…...
算法:模拟
1.替换所有的问号 1576. 替换所有的问号 - 力扣(LeetCode) 遍历字符串:通过外层循环逐一检查每个字符。遇到 ? 时处理: 内层循环遍历小写字母(a 到 z)。对每个字母检查是否满足: 与…...
使用LangGraph和LangSmith构建多智能体人工智能系统
现在,通过组合几个较小的子智能体来创建一个强大的人工智能智能体正成为一种趋势。但这也带来了一些挑战,比如减少幻觉、管理对话流程、在测试期间留意智能体的工作方式、允许人工介入以及评估其性能。你需要进行大量的反复试验。 在这篇博客〔原作者&a…...
