MetaObjectHandler:mybatistPlus提供给我们的一个拓展接口,我们可以重写 insertFill updateFill 方法来对我们入库的对象的字段进行设置,比如createTime,createBy,lockVersion等这些通用字段,这些字段基本每个表都会有,每次调用新增或者修改等需要入库的方法前去设置太过于麻烦,因此在这里进行设置!
当然也可以自己封装一个方法在插入前进行设置!但是每次插入也需要调用方法,这个接口还是省去了些力气,但是本次业务开发过程中就遇到这样的问题:
当我开启异步调用的时候,进行入库操作,SessionUser sessionUser = SessionTools.tokenInfo();就发生了错误!这个是获取当前登录用户信息的方法,其中调用了Sa-Token的接口
- package com.jm.component;
-
- import com.baomidou.mybatisplus.core.handlers.MetaObjectHandler;
- import com.jm.base.dto.SessionUser;
- import com.jm.base.util.SessionTools;
- import org.apache.ibatis.reflection.MetaObject;
- import org.springframework.stereotype.Component;
- import java.time.LocalDateTime;
-
- /**
- * mybatis持久化对象处理器
- *
- * @author zwf
- * @date 2022/11/02
- */
- @Component
- public class MyMetaObjectHandler implements MetaObjectHandler {
-
- private static final String CREATE_BY = "createBy";
- private static final String CREATE_TIME = "createTime";
- private static final String UPDATE_BY = "updateBy";
- private static final String UPDATE_TIME = "updateTime";
- private static final String LOCK_VERSION = "lockVersion";
-
- @Override
- public void insertFill(MetaObject metaObject) {
- SessionUser sessionUser = SessionTools.tokenInfo();
- LocalDateTime now = LocalDateTime.now();
- if (metaObject.hasSetter(CREATE_BY) && metaObject.getValue(CREATE_BY) == null) {
- metaObject.setValue(CREATE_BY, sessionUser.getUser().getId());
- }
- if (metaObject.hasSetter(CREATE_TIME)) {
- metaObject.setValue(CREATE_TIME, now);
- }
- if (metaObject.hasSetter(UPDATE_BY) && metaObject.getValue(UPDATE_BY) == null) {
- metaObject.setValue(UPDATE_BY, sessionUser.getUser().getId());
- }
- if (metaObject.hasSetter(UPDATE_TIME)) {
- metaObject.setValue(UPDATE_TIME, now);
- }
- if (metaObject.hasSetter(LOCK_VERSION)) {
- metaObject.setValue(LOCK_VERSION, 0);
- }
- }
-
- @Override
- public void updateFill(MetaObject metaObject) {
- SessionUser sessionUser = SessionTools.tokenInfo();
- if (metaObject.hasSetter(UPDATE_BY)) {
- metaObject.setValue(UPDATE_BY, sessionUser.getUser().getId());
- }
- if (metaObject.hasSetter(UPDATE_TIME)) {
- metaObject.setValue(UPDATE_TIME, LocalDateTime.now());
- }
- }
- }
思路:异步调用的入库操作不使用MetaObjectHandler来设置这些字段,再调用入库前手动设置!但是只要是入库操作都会走这个类,所以我加了相关判断!
- package com.jm.component;
-
- import com.baomidou.mybatisplus.core.handlers.MetaObjectHandler;
- import com.jm.base.dto.SessionUser;
- import com.jm.base.option.meta.Flag;
- import com.jm.base.util.SessionTools;
- import org.apache.ibatis.reflection.MetaObject;
- import org.springframework.stereotype.Component;
- import java.time.LocalDateTime;
-
- /**
- * mybatis持久化对象处理器
- *
- * @author zwf
- * @date 2022/11/02
- */
- @Component
- public class MyMetaObjectHandler implements MetaObjectHandler {
-
- private static final String CREATE_BY = "createBy";
- private static final String CREATE_TIME = "createTime";
- private static final String UPDATE_BY = "updateBy";
- private static final String UPDATE_TIME = "updateTime";
- private static final String LOCK_VERSION = "lockVersion";
- private static final String IS_ASYNC_FLAG = "isAsyncFlag";
-
- @Override
- public void insertFill(MetaObject metaObject) {
- Flag flag = Flag.F;
- if(metaObject.hasSetter(IS_ASYNC_FLAG)){
- flag = (Flag) metaObject.getValue(IS_ASYNC_FLAG);
- }
- if(null != flag && Flag.F.equalCode(flag.getCode())){
- SessionUser sessionUser = SessionTools.tokenInfoNotNull();
- LocalDateTime now = LocalDateTime.now();
- if (metaObject.hasSetter(CREATE_BY) && metaObject.getValue(CREATE_BY) == null) {
- metaObject.setValue(CREATE_BY, sessionUser.getUser().getId());
- }
- if (metaObject.hasSetter(CREATE_TIME)) {
- metaObject.setValue(CREATE_TIME, now);
- }
- if (metaObject.hasSetter(UPDATE_BY) && metaObject.getValue(UPDATE_BY) == null) {
- metaObject.setValue(UPDATE_BY, sessionUser.getUser().getId());
- }
- if (metaObject.hasSetter(UPDATE_TIME)) {
- metaObject.setValue(UPDATE_TIME, now);
- }
- if (metaObject.hasSetter(LOCK_VERSION)) {
- metaObject.setValue(LOCK_VERSION, 0);
- }
- }
- }
-
- @Override
- public void updateFill(MetaObject metaObject) {
- Flag flag = Flag.F;
- if(metaObject.hasSetter(IS_ASYNC_FLAG)){
- flag = (Flag) metaObject.getValue(IS_ASYNC_FLAG);
- }
- if(null != flag && Flag.F.equalCode(flag.getCode())){
- SessionUser sessionUser = SessionTools.tokenInfoNotNull();
- if (metaObject.hasSetter(UPDATE_BY)) {
- metaObject.setValue(UPDATE_BY, sessionUser.getUser().getId());
- }
- if (metaObject.hasSetter(UPDATE_TIME)) {
- metaObject.setValue(UPDATE_TIME, LocalDateTime.now());
- }
- }
- }
- }
- package com.jm.base.option.meta;
-
- import com.baomidou.mybatisplus.annotation.EnumValue;
- import com.jm.base.option.KV;
-
- /**
- * @author zwf
- * @date 2022/10/13
- */
-
- public enum Flag implements KV {
- /**
- * 是否标记
- */
- T("1", "是"),
- F("0", "否");
-
- @EnumValue
- private final String code;
- private final String msg;
-
- Flag(String code, String msg) {
- this.code = code;
- this.msg = msg;
- }
-
- @Override
- public String getCode() {
- return this.code;
- }
-
- @Override
- public String getMsg() {
- return this.msg;
- }
-
- @Override
- public String getEnumName() {
- return null;
- }
- }
1、我再会进行异步入库的对象新加了属性isAsyncFlag ,当代码走到MyMetaObjectHandler类中时,判断这个对象是否具备该字段,如果有则不需要该类处理createBy这些字段,就不会调用到Sa-Token的API。
2、入库前设置相关属性:
- /**
- * 异步开启之前调用satoken的API获取用户信息然后作为参数进入异步
- *
- * @param param 业务参数
- * @param user 当前登录用户信息
- */
- asynManager.doQueryMsg(param, SessionTools.tokenInfo().getUser());
-
-
- /**
- * 为异步新增的对象设置当前用户信息,异步操作标记:解决异步无法获取saToken信息问题
- *
- * @param t 需要设置的对象
- * @param id 当前用户id
- * @param time 当前时间
- * @param
- */
- private
extends MetaEntity> void setUserInfoAndFlag(T t, Long id, LocalDateTime time){ - t.setCreateBy(id);
- t.setCreateTime(time);
- t.setUpdateBy(id);
- t.setUpdateTime(time);
- ReflectTools.setFieldValue(t, "isAsyncFlag", Flag.T);
- }
-
- // 使用
- setUserInfoAndFlag(teacher, user.getId(), LocalDateTime.now());
- teacherMapper.updateById(teacher);