【spring data jpa】【mybatis】通过反射实现 更新/保存 实体的任意字段的操作
代码如下:
//代码示例:例如保存时,传入下面两个字段 String filed;
String content;
//User代表要更新的实体,user即本对象
//filed代表要更改的字段,例如user.name
//content代表要更改字段的值,例如“张三”
import org.springframework.beans.BeanUtils;
User user = new User();
//反射赋值
//反射 + javaBean机制 get set 方法
Class<? extends User> clz = user.getClass();
PropertyDescriptor propertyDescriptor = BeanUtils.getPropertyDescriptor(clz, filed); //获取当前字段的javabean写方法
Method writeMethod = propertyDescriptor.getWriteMethod();
if (writeMethod != null) {
try {
writeMethod.invoke(user, "张三");
} catch (Exception e) {
syatem.out.println(e);
}
}
JPA保存即保存对象即可,因为对象的值已经存入user对象。
User newUser = goodsMsgService.insert(oldGoodsMsg);
mybatis保存对象:
@Update("update goods_msg set ${filed} = #{context} where uid = #{uid}")
public int saveFiled(@Param("filed")String filed, @Param("uid")String uid, @Param("context")String context);
如下,有一个完整的代码示例可以参考:
//将实体字段存入List
public static final List<String> AUTH_FILEDS = Arrays.asList(new String[]{
"innerFrist",
"innerNormal",
"innerDanger",
"outFrist",
"outNormal",
"outDanger",
"notAct",
"share",
"notSub",
"exceedMaxQueryTime",
"scanCodeLimit",
"innerSafetyTime",
"outerSafetyTime",
"scanCodeLimitTime"
});
//将实体属性 对应数据库字段存入 map 方便下面mybatis更新单个字段调用
public static final Map<String,String> AUTH_FILEDS_MAPPING = new HashMap<>();
static{
AUTH_FILEDS_MAPPING.put("innerFrist","inner_frist");
AUTH_FILEDS_MAPPING.put("innerNormal", "inner_normal");
AUTH_FILEDS_MAPPING.put("innerDanger", "inner_danger");
AUTH_FILEDS_MAPPING.put("outFrist", "out_frist");
AUTH_FILEDS_MAPPING.put("outNormal", "out_normal");
AUTH_FILEDS_MAPPING.put("outDanger", "out_danger");
AUTH_FILEDS_MAPPING.put("notAct", "not_act");
AUTH_FILEDS_MAPPING.put("share", "share");
AUTH_FILEDS_MAPPING.put("notSub","not_sub");
AUTH_FILEDS_MAPPING.put("exceedMaxQueryTime", "exceed_max_query_time");
AUTH_FILEDS_MAPPING.put("scanCodeLimit","scan_code_limit");
AUTH_FILEDS_MAPPING.put("innerSafetyTime","inner_safety_time");
AUTH_FILEDS_MAPPING.put("outerSafetyTime","outer_safety_time");
AUTH_FILEDS_MAPPING.put("scanCodeLimitTime","scan_code_limit_time");
}
/**
* 保存或修改(针对单一字段)
*
* ===========================非空字段===========================
* [
* 要修改的字段 : filed
* 字段内容 : context
* 是否全局 : global (1全局 0不是全局)
* 绑定的商品或分类 : guid(全局为空)
* ]
* ===========================保存逻辑===========================
* 1 检查要修改的字段是否存在
* 2 判断操作话述是否属于当前租户
* 3 判断是否是全局,不是全局guid做非空验证
* 4 如果已经存在记录则修改 如果不存在新增
*
* ===========================安全验证===========================
* guid是否属于当前租户
*
*
*/
@Override
public AjaxResult<String> saveFiled(@RequestBody SaveFiledRequestBean requestBean) {
//当前租户
TenementUser tenementUser = RequestData.TENEMENT_USER.get();
//非空
LunaResultBean.checkField(requestBean,"filed","context","global","name");
// 不是全局的非空
if (1 != requestBean.getGlobal()) {
LunaResultBean.checkField(requestBean,"guid");
}
String filed = requestBean.getFiled();
String guid = requestBean.getGuid();
String context = requestBean.getContext();
AjaxResult<String> res = new AjaxResult<String>();
boolean isAdd = true;
boolean success = true;
GoodsMsg oldGoodsMsg = null;
if(AUTH_FILEDS.contains(filed)){
if (StringUtils.isNotBlank(guid)) {
boolean check = goodsConfigUtils.check(GoodsConfigUtils.CHECK_GUID, guid);
if (check) {
// 是否需要新增
oldGoodsMsg = goodsMsgService.findByGuid(guid);
if (oldGoodsMsg != null) {
isAdd = false;
}
} else {
success = false;
}
} else {
// 判断全局是否已经存在
oldGoodsMsg = goodsMsgService.findByGlobalMsg(tenementUser.getTenementId());
if (oldGoodsMsg != null) {
isAdd = false;
}
}
//判断参数验证是否通过
if (success) {
if (isAdd) {
// 添加
oldGoodsMsg = new GoodsMsg();
oldGoodsMsg.initInsertData();
oldGoodsMsg.setUid(UUID.randomUUID().toString().replaceAll("-", ""));
oldGoodsMsg.setGuid(guid);
oldGoodsMsg.setGlobal(requestBean.getGlobal());
//反射赋值
//反射 + javaBean机制 get set 方法
Class<? extends GoodsMsg> clz = oldGoodsMsg.getClass();
PropertyDescriptor propertyDescriptor = BeanUtils.getPropertyDescriptor(clz, filed);
//获取当前字段的javabean写方法
Method writeMethod = propertyDescriptor.getWriteMethod();
if (writeMethod != null) {
try {
writeMethod.invoke(oldGoodsMsg, requestBean.getContext());
} catch (Exception e) {
throw new LunaException("方法 "+ writeMethod.getName() +"无法执行",AjaxResult.ERROR_SYS_EXCPTION);
}
}
//新增
GoodsMsg insert = goodsMsgService.insert(oldGoodsMsg);
if (insert != null) {
res.initTrue("操作成功");
} else {
res.initFalse("操作失败", LunaResultBean.ERROR_BUSINESS);
}
} else {
//修改
//调用mybatis update 字段 by uid
int saveFiled = goodsMsgService.saveFiled(AUTH_FILEDS_MAPPING.get(filed), oldGoodsMsg.getUid(), context);
if(saveFiled > 0){
res.initTrue("操作成功");
} else {
res.initFalse("操作失败", LunaResultBean.ERROR_BUSINESS);
}
}
} else {
res.initFalse("请选择正确的商品或商品类型", LunaResultBean.ERROR_BUSINESS);
}
}else{
res.initFalse("无效字段 ["+ filed +"]", LunaResultBean.ERROR_BUSINESS);
}
return res;
}
【spring data jpa】【mybatis】通过反射实现 更新/保存 实体的任意字段的操作的更多相关文章
- Spring data Jpa,Mybatis,读写锁,@Lock 使用
Spring data jpa 支持注解式的读写锁(悲观锁),实际上这个东西硬编码也简单,但是基于Jpa 命名方式定义的Sql,只能用注解添加支持读写锁了, 不了解读写锁的可以点这里 mysql读写锁 ...
- 在Spring Data JPA 中使用Update Query更新实体类
对于 Spring Data JPA 使用的时间不长,只有两年时间.但是踩过坑的却不少. 使用下列代码 @Modifying @Query("update User u set u.firs ...
- Spring Data JPA查询指定列,并返回实体(改)
现有PostEntiy实力,包含各种属性,如: /** * @Auther: DingShuo * @Date: 2018/7/18 11:09 * @Description: */ @Entity ...
- 关于Spring Data JPA更新部分字段的问题
1.问题背景 个人比较喜欢Spring data JPA,这次的问题是在实体类中使用List类型作为字段,JPA也提供了操作的方法,即使用@ElementCollection注解,网上对于JPA的知识 ...
- 来说说JPA、Hibernate、Spring Data JPA之间的什么关系?
目录 JPA Hibernate Spring Data JPA 实践 来说说JPA.Hibernate.Spring Data JPA之间的什么关系 Java 持久层框架访问数据库的方式大致分为两种 ...
- spring data jpa(一)
第1章 Spring Data JPA的快速入门 1.1 需求说明 Spring Data JPA完成客户的基本CRUD操作 1.2 搭建Spring Data JPA的开发环境 1. ...
- SpringBoot学习笔记:Spring Data Jpa的使用
更多请关注公众号 Spring Data Jpa 简介 JPA JPA(Java Persistence API)意即Java持久化API,是Sun官方在JDK5.0后提出的Java持久化规范(JSR ...
- Spring Data JPA应用之常规CRUD操作初体验
基于对于一个陌生的技术框架,先使用后研究其实现的原则(大部分本人如此,就如小朋友学习骑自行车不会先研究自行车是怎么动起来的而是先骑会了),对于Spring JPA先通过案例实践其怎么用吧. 用之前得明 ...
- Spring Data JPA 自定义对象接收查询结果集
Spring Data JPA 简介 Spring Data JPA 是 Spring 基于 ORM 框架.JPA 规范的基础上封装的一套JPA应用框架,可使开发者用极简的代码即可实现对数据库的访问和 ...
随机推荐
- 剑指offer:二维数组中的查找
目录 题目 解题思路 具体代码 题目 题目链接 剑指offer:二维数组中的查找 题目描述 在一个二维数组中(每个一维数组的长度相同),每一行都按照从左到右递增的顺序排序,每一列都按照从上到下递增的顺 ...
- Spring2集成iBatis2
从数据库中查询一条记录,演示Spring与iBatis的集成 1 编写sqlmaps与Domain对象 <?xml version="1.0" encoding=" ...
- POJ 2987 Firing | 最大权闭合团
一个点带权的图,有一些指向关系,删掉一个点他指向的点也不能留下,问子图最大权值 题解: 这是最大权闭合团问题 闭合团:集合内所有点出边指向的点都在集合内 构图方法 1.S到权值为正的点,容量为权值 2 ...
- Three Garlands~Educational Codeforces Round 35
C. Three Garlands time limit per test 2 seconds memory limit per test 256 megabytes input standard i ...
- 7月15号day7总结
今天复习了springMVC的框架搭建. 思维导图:
- d3.js path路径
转自:http://www.d3js.cn/?p=68 svg的path标签被称为”可以组成任何形状的形状” SVG Path可以绘制任何形状的图形,包括矩形,圆形,椭圆,折线,多边形,直线,曲线等. ...
- 2015年4月1日 14:36:56 EF 主从表更新
公司封装框架的人把eF封在了工作单元里面,使用了Unitofwork这样的形式, 我用代码生成器生成了基础的单表操作的代码. 这种方式对多表有问题. 暂时只得,一张表一张表地操作, 我采用先用List ...
- Linux 设备驱动--- Poll 方法 --- Select【转】
转自:http://blog.csdn.net/yikai2009/article/details/8653842 版权声明:本文为博主原创文章,未经博主允许不得转载. 目录(?)[-] Sele ...
- 如何防止Android反编译
转自: http://my.eoe.cn/sandking/archive/19772.html http://www.cnblogs.com/zdz8207/archive/2012/01/28/d ...
- Scala学习随笔——Scala起步
实验楼学习Scala语言的笔记,课程网址为https://www.shiyanlou.com/courses/490 一.Scala简介 Scala 是一门多范式的编程语言,类似于 Java .设计初 ...