diff --git a/opsli-core/pom.xml b/opsli-base-support/opsli-core/pom.xml similarity index 81% rename from opsli-core/pom.xml rename to opsli-base-support/opsli-core/pom.xml index 08441876..c9d1c8b6 100644 --- a/opsli-core/pom.xml +++ b/opsli-base-support/opsli-core/pom.xml @@ -3,9 +3,10 @@ xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> - opsli-boot-parent + opsli-base-support org.opsliframework.boot 1.0.0 + ../pom.xml @@ -25,6 +26,13 @@ ${version} + + + org.opsliframework.boot + opsli-api + ${version} + + org.opsliframework.boot @@ -39,7 +47,6 @@ ${plugins.version} - \ No newline at end of file diff --git a/opsli-core/src/main/java/org/opsli/core/aspect/CacheDataAop.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/aspect/CacheDataAop.java similarity index 85% rename from opsli-core/src/main/java/org/opsli/core/aspect/CacheDataAop.java rename to opsli-base-support/opsli-core/src/main/java/org/opsli/core/aspect/CacheDataAop.java index eb23cc49..e01d1341 100644 --- a/opsli-core/src/main/java/org/opsli/core/aspect/CacheDataAop.java +++ b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/aspect/CacheDataAop.java @@ -7,10 +7,10 @@ import org.aspectj.lang.annotation.Around; import org.aspectj.lang.annotation.Aspect; import org.aspectj.lang.annotation.Pointcut; import org.aspectj.lang.reflect.MethodSignature; +import org.opsli.api.base.warpper.ApiWrapper; import org.opsli.common.annotation.EnableHotData; import org.opsli.common.annotation.HotDataDel; import org.opsli.common.annotation.HotDataPut; -import org.opsli.core.base.entity.BaseEntity; import org.opsli.common.constants.CacheConstants; import org.opsli.core.cache.local.CacheUtil; import org.opsli.core.cache.pushsub.entity.CacheDataEntity; @@ -71,27 +71,28 @@ public class CacheDataAop { return returnValue; } - // ====== 如果 使用了 EnableHotData ,表示开启热数据加载 则执行下段代码 CacheDataEntity cacheDataEntity = this.putHandlerData(point, returnValue); - if(cacheDataEntity != null){ - // 更新缓存数据 - // 热点数据 - if(CacheConstants.HOT_DATA.equals(cacheDataEntity.getCacheName())){ - CacheUtil.putByKeyOriginal(cacheDataEntity.getKey(), returnValue); - } - // 永久数据 - else if(CacheConstants.EDEN_DATA.equals(cacheDataEntity.getCacheName())) { - CacheUtil.putEdenByKeyOriginal(cacheDataEntity.getKey(), returnValue); - } + if(cacheDataEntity == null){ + return returnValue; + } - // 广播缓存数据 - 通知其他服务器同步数据 - redisPlugin.sendMessage( - CacheDataMsgFactory.createMsg(cacheDataEntity.getType(), - cacheDataEntity.getKey(), returnValue, CacheType.UPDATE) - ); + // 更新缓存数据 + // 热点数据 + if(CacheConstants.HOT_DATA.equals(cacheDataEntity.getCacheName())){ + CacheUtil.putByKeyOriginal(cacheDataEntity.getKey(), returnValue); + } + // 永久数据 + else if(CacheConstants.EDEN_DATA.equals(cacheDataEntity.getCacheName())) { + CacheUtil.putEdenByKeyOriginal(cacheDataEntity.getKey(), returnValue); } + // 广播缓存数据 - 通知其他服务器同步数据 + redisPlugin.sendMessage( + CacheDataMsgFactory.createMsg(cacheDataEntity.getType(), + cacheDataEntity.getKey(), returnValue, CacheType.UPDATE) + ); + return returnValue; } @@ -114,17 +115,19 @@ public class CacheDataAop { // ====== 如果 使用了 EnableHotData ,表示开启热数据加载 则执行下段代码 List cacheDataEntityList = this.delHandlerData(point, args); - if(cacheDataEntityList != null && cacheDataEntityList.size() > 0){ - for (CacheDataEntity cacheDataEntity : cacheDataEntityList) { - // 更新缓存数据 - 删除缓存 - CacheUtil.del(cacheDataEntity.getKey()); - - // 广播缓存数据 - 通知其他服务器同步数据 - redisPlugin.sendMessage( - CacheDataMsgFactory.createMsg(cacheDataEntity.getType(), - cacheDataEntity.getKey(), returnValue, CacheType.DELETE) - ); - } + if(cacheDataEntityList == null || cacheDataEntityList.size() == 0){ + return returnValue; + } + + for (CacheDataEntity cacheDataEntity : cacheDataEntityList) { + // 更新缓存数据 - 删除缓存 + CacheUtil.del(cacheDataEntity.getKey()); + + // 广播缓存数据 - 通知其他服务器同步数据 + redisPlugin.sendMessage( + CacheDataMsgFactory.createMsg(cacheDataEntity.getType(), + cacheDataEntity.getKey(), returnValue, CacheType.DELETE) + ); } return returnValue; @@ -144,8 +147,8 @@ public class CacheDataAop { if(returnValue == null){ return null; } - // 这里 只对 继承了 BaseEntity 的类做处理 - if(!(returnValue instanceof BaseEntity)){ + // 这里 只对 继承了 ApiWrapper 的类做处理 + if(!(returnValue instanceof ApiWrapper)){ return null; } // 报错不处理 @@ -177,10 +180,10 @@ public class CacheDataAop { try { // 这里 只对 继承了 BaseEntity 的类做处理 - BaseEntity baseEntity = (BaseEntity) returnValue; + ApiWrapper apiWrapper = (ApiWrapper) returnValue; // key 存储ID - String key = keyBuf.append(baseEntity.getId()).toString(); + String key = keyBuf.append(apiWrapper.getId()).toString(); ret = new CacheDataEntity(); ret.setKey(key); @@ -261,10 +264,10 @@ public class CacheDataAop { ret.setCacheName(aCache.name()); cacheDataEntities.add(ret); } - } else if (arg instanceof BaseEntity) { + } else if (arg instanceof ApiWrapper) { // key 存储ID - BaseEntity baseEntity = (BaseEntity) arg; - String key = keyBuf.toString() + baseEntity.getId(); + ApiWrapper apiWrapper = (ApiWrapper) arg; + String key = keyBuf.toString() + apiWrapper.getId(); CacheDataEntity ret = new CacheDataEntity(); ret.setKey(key); ret.setType(type); @@ -272,8 +275,8 @@ public class CacheDataAop { cacheDataEntities.add(ret); } else if (arg instanceof Collection) { try { - Collection baseEntityList = (Collection) arg; - for (BaseEntity baseEntity : baseEntityList) { + Collection baseEntityList = (Collection) arg; + for (ApiWrapper baseEntity : baseEntityList) { // key 存储ID String key = keyBuf.toString() + baseEntity.getId(); CacheDataEntity ret = new CacheDataEntity(); diff --git a/opsli-base-support/opsli-core/src/main/java/org/opsli/core/aspect/SQLDataAop.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/aspect/SQLDataAop.java new file mode 100644 index 00000000..c46e113c --- /dev/null +++ b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/aspect/SQLDataAop.java @@ -0,0 +1,82 @@ +package org.opsli.core.aspect; + +import lombok.extern.slf4j.Slf4j; +import org.aspectj.lang.annotation.AfterReturning; +import org.aspectj.lang.annotation.Aspect; +import org.aspectj.lang.annotation.Pointcut; +import org.opsli.common.exception.ServiceException; +import org.opsli.core.msg.CoreMsg; +import org.springframework.core.annotation.Order; +import org.springframework.stereotype.Component; + +import static org.opsli.common.constants.OrderConstants.SQL_ORDER; + +/** + * SQL数据 拦截处理 + * + * @author parker + * @date 2020-09-16 + */ +@Slf4j +@Order(SQL_ORDER) +@Aspect +@Component +public class SQLDataAop { + + @Pointcut("execution(public * org.opsli.core.base.service.impl.CrudServiceImpl.insert(..))") + public void insert() { + } + + @Pointcut("execution(public * org.opsli.core.base.service.impl.CrudServiceImpl.update*(..))") + public void update() { + } + + @Pointcut("execution(public * org.opsli.core.base.service.impl.CrudServiceImpl.delete*(..))") + public void delete() { + } + + @AfterReturning(returning = "ret", pointcut = "insert()") + public void insertHadnler(Object ret){ + try { + if(ret == null){ + throw new ServiceException(CoreMsg.SQL_EXCEPTION_UPDATE); + } + } catch (ServiceException e) { + throw e; + } catch (Throwable e) { + log.error(e.getMessage(),e); + } + } + + @AfterReturning(returning = "ret", pointcut = "update()") + public void updateHadnler(Object ret){ + try { + if(ret == null){ + throw new ServiceException(CoreMsg.SQL_EXCEPTION_UPDATE); + } + } catch (ServiceException e) { + throw e; + } catch (Throwable e) { + log.error(e.getMessage(),e); + } + } + + @AfterReturning(returning = "ret", pointcut = "delete()") + public void deleteHadnler(Object ret){ + try { + if(ret != null){ + Integer retCount = (Integer) ret; + if(retCount == 0){ + throw new ServiceException(CoreMsg.SQL_EXCEPTION_DELETE); + } + }else{ + throw new ServiceException(CoreMsg.SQL_EXCEPTION_DELETE); + } + } catch (ServiceException e) { + throw e; + } catch (Throwable e) { + log.error(e.getMessage(),e); + } + } + +} diff --git a/opsli-core/src/main/java/org/opsli/core/base/concroller/BaseRestController.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/base/concroller/BaseRestController.java similarity index 68% rename from opsli-core/src/main/java/org/opsli/core/base/concroller/BaseRestController.java rename to opsli-base-support/opsli-core/src/main/java/org/opsli/core/base/concroller/BaseRestController.java index 6fd419ed..eda8d831 100644 --- a/opsli-core/src/main/java/org/opsli/core/base/concroller/BaseRestController.java +++ b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/base/concroller/BaseRestController.java @@ -3,9 +3,11 @@ package org.opsli.core.base.concroller; import lombok.extern.slf4j.Slf4j; import org.apache.commons.lang3.StringUtils; +import org.opsli.api.base.warpper.ApiWrapper; import org.opsli.common.annotation.EnableHotData; import org.opsli.common.exception.ServiceException; import org.opsli.common.msg.CommonMsg; +import org.opsli.common.utils.WrapperUtil; import org.opsli.core.base.entity.BaseEntity; import org.opsli.core.base.service.interfaces.CrudServiceInterface; import org.opsli.core.cache.local.CacheUtil; @@ -15,7 +17,7 @@ import org.springframework.web.bind.annotation.RequestParam; import org.springframework.web.bind.annotation.RestController; import javax.annotation.PostConstruct; -import java.lang.reflect.*; +import java.lang.reflect.ParameterizedType; /** * @BelongsProject: opsli-boot @@ -29,11 +31,13 @@ import java.lang.reflect.*; */ @Slf4j @RestController -public abstract class BaseRestController >{ +public abstract class BaseRestController >{ /** 开启热点数据状态 */ protected boolean hotDataFlag = false; + /** Model Clazz 类 */ + protected Class modelClazz; /** Entity Clazz 类 */ protected Class entityClazz; @@ -49,47 +53,45 @@ public abstract class BaseRestController serviceClazz = IService.getServiceClazz(); // 判断是否开启热点数据 if(serviceClazz != null){ @@ -106,12 +108,12 @@ public abstract class BaseRestController modelClazz = this.entityClazz; + Class modelClazz = this.modelClazz; return modelClazz.newInstance(); } catch (Exception e) { log.error(e.getMessage(),e); @@ -119,12 +121,22 @@ public abstract class BaseRestController getModelClass(){ + Class tClass = (Class)((ParameterizedType)getClass().getGenericSuperclass()).getActualTypeArguments()[0]; + return tClass; + } + /** * 获得 泛型 Clazz * @return */ - private Class getModelClass(){ - Class tClass = (Class)((ParameterizedType)getClass().getGenericSuperclass()).getActualTypeArguments()[0]; + private Class getEntityClass(){ + Class tClass = (Class)((ParameterizedType)getClass().getGenericSuperclass()).getActualTypeArguments()[1]; return tClass; } diff --git a/opsli-base-support/opsli-core/src/main/java/org/opsli/core/base/entity/BaseEntity.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/base/entity/BaseEntity.java new file mode 100644 index 00000000..33f11ad4 --- /dev/null +++ b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/base/entity/BaseEntity.java @@ -0,0 +1,38 @@ +package org.opsli.core.base.entity; + +import com.baomidou.mybatisplus.annotation.*; +import lombok.Data; +import lombok.EqualsAndHashCode; +import lombok.experimental.Accessors; +import org.opsli.api.base.warpper.ApiWrapper; + +/** + * + * Entity 基础类 + * + * @author Parker + * @date 2019-05-11 + * + */ +@Data +@Accessors(chain = true) +@EqualsAndHashCode(callSuper = false) +public abstract class BaseEntity extends ApiWrapper { + + private static final long serialVersionUID = 1L; + + + /** 逻辑删除 子类需要 逻辑删除时 需要重写 父类 deleted 属性 并且加上 @TableLogic + * 数据库增加字段 deleted 类型为 Char 0 标示未删除 1 标示已删除 + * + * Entity 增加的 deleted 字段, 不需要同步更新到 Wrapper的Model中 + * Wrapper的Model 只是用于 对外展示 + * */ + /** + + @TableLogic + private Integer deleted; + + **/ + +} diff --git a/opsli-core/src/main/java/org/opsli/core/base/service/base/BaseService.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/base/service/base/BaseService.java similarity index 100% rename from opsli-core/src/main/java/org/opsli/core/base/service/base/BaseService.java rename to opsli-base-support/opsli-core/src/main/java/org/opsli/core/base/service/base/BaseService.java diff --git a/opsli-base-support/opsli-core/src/main/java/org/opsli/core/base/service/impl/CrudServiceImpl.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/base/service/impl/CrudServiceImpl.java new file mode 100644 index 00000000..b300e20d --- /dev/null +++ b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/base/service/impl/CrudServiceImpl.java @@ -0,0 +1,190 @@ +package org.opsli.core.base.service.impl; + +import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper; +import com.baomidou.mybatisplus.core.mapper.BaseMapper; +import com.google.common.collect.Lists; +import lombok.extern.slf4j.Slf4j; +import org.opsli.api.base.warpper.ApiWrapper; +import org.opsli.common.annotation.EnableHotData; +import org.opsli.common.constants.MyBatisConstants; +import org.opsli.common.utils.WrapperUtil; +import org.opsli.core.base.entity.BaseEntity; +import org.opsli.core.base.service.base.BaseService; +import org.opsli.core.base.service.interfaces.CrudServiceInterface; + +import javax.annotation.PostConstruct; +import java.lang.reflect.ParameterizedType; +import java.util.Arrays; +import java.util.Collection; +import java.util.List; + +/** + * @BelongsProject: opsli-boot + * @BelongsPackage: org.opsli.common.base.service.impl + * @Author: Parker + * @CreateTime: 2020-09-14 17:31 + * @Description: CurdServiceImpl 基类 - 实现类 + * + * 这里 可能觉得 增改 最次返回的也是实体对象 设计的有问题 + * + * 其实是为了 热点数据 切面用的 用来 增加或者清理数据 + * + * 没有 直接用一个save类的原因,可能是觉得 新增和修改分开一些会比较好 防止串了数据 + * + */ +@Slf4j +public abstract class CrudServiceImpl, E extends ApiWrapper, T extends BaseEntity> + extends BaseService implements CrudServiceInterface { + + /** entity Class 类 */ + protected Class entityClazz; + + /** entity Class 类 */ + protected Class modelClazz; + + @Override + public E get(String id) { + return transformT2M( + baseMapper.selectById(id) + ); + } + + @Override + public E get(E model) { + if(model == null) return null; + return transformT2M( + baseMapper.selectById(model.getId()) + ); + } + + @Override + public E insert(E model) { + if(model == null) return null; + T entity = transformM2T(model); + int count = baseMapper.insert(entity); + if(count > 0){ + return transformT2M(entity); + } + return null; + } + + @Override + public E update(E model) { + if(model == null) return null; + T entity = transformM2T(model); + int count = baseMapper.updateById(entity); + if(count > 0){ + return transformT2M(entity); + } + return null; + } + + @Override + public int delete(String id) { + return baseMapper.deleteById(id); + } + + @Override + public int delete(E model) { + if(model == null) return 0; + return baseMapper.deleteById(model.getId()); + } + + @Override + public int deleteAll(String[] ids) { + if(ids == null) return 0; + List idList = Arrays.asList(ids); + return baseMapper.deleteBatchIds(idList); + } + + @Override + public int deleteAll(Collection models) { + if(models == null || models.isEmpty()) return 0; + List idList = Lists.newArrayListWithCapacity(models.size()); + for (E entity : models) { + idList.add(entity.getId()); + } + return baseMapper.deleteBatchIds(idList); + } + + @Override + public List findList(E model) { + return null; + } + + // ======================== 对象转化 ======================== + + /** + * 转化 entity 为 model + * @param entity + * @return + */ + protected E transformT2M(T entity){ + return WrapperUtil.transformInstance(entity, modelClazz); + } + + /** + * 集合对象 + * 转化 entitys 为 models + * @param entitys + * @return + */ + protected List transformTs2Ms(List entitys){ + return WrapperUtil.transformInstance(entitys, modelClazz); + } + + + /** + * 转化 model 为 entity + * @param model + * @return + */ + protected T transformM2T(E model){ + return WrapperUtil.transformInstance(model, entityClazz); + } + + /** + * 集合对象 + * 转化 models 为 entitys + * @param models + * @return + */ + protected List transformMs2Ts(List models){ + return WrapperUtil.transformInstance(models, entityClazz); + } + + + // ======================== 初始化 ======================== + + /** + * 初始化 + */ + @PostConstruct + public void init(){ + try { + this.modelClazz = this.getModelClass(); + this.entityClazz = this.getEntityClass(); + }catch (Exception e){ + log.error(e.getMessage(),e); + } + } + + /** + * 获得 泛型 Clazz + * @return + */ + private Class getModelClass(){ + Class tClass = (Class)((ParameterizedType)getClass().getGenericSuperclass()).getActualTypeArguments()[1]; + return tClass; + } + + /** + * 获得 泛型 Clazz + * @return + */ + private Class getEntityClass(){ + Class tClass = (Class)((ParameterizedType)getClass().getGenericSuperclass()).getActualTypeArguments()[2]; + return tClass; + } + +} diff --git a/opsli-core/src/main/java/org/opsli/core/base/service/interfaces/BaseServiceInterface.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/base/service/interfaces/BaseServiceInterface.java similarity index 100% rename from opsli-core/src/main/java/org/opsli/core/base/service/interfaces/BaseServiceInterface.java rename to opsli-base-support/opsli-core/src/main/java/org/opsli/core/base/service/interfaces/BaseServiceInterface.java diff --git a/opsli-base-support/opsli-core/src/main/java/org/opsli/core/base/service/interfaces/CrudServiceInterface.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/base/service/interfaces/CrudServiceInterface.java new file mode 100644 index 00000000..05181bc2 --- /dev/null +++ b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/base/service/interfaces/CrudServiceInterface.java @@ -0,0 +1,148 @@ +package org.opsli.core.base.service.interfaces; + + + +import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper; + +import java.util.Collection; +import java.util.List; + +/** + * 增删改查 总接口 + * + * 对于 增加、修改、删除处理 === + * + * 不需要做锁状态处理 + * 不需要判断是否成功 + * 能往下走的只能是成功 + * 异常问题 已经统一被处理 + * + * @param + * @param + */ +public interface CrudServiceInterface extends BaseServiceInterface { + + + /** + * 获取单条数据 + * + * @param id + * @return + */ + E get(String id); + + /** + * 获取单条数据 + * + * @param model + * @return + */ + E get(E model); + + + /** + * 插入数据 + * + * 不需要做锁状态处理 + * 不需要判断是否成功 + * 能往下走的只能是成功 + * 异常问题 已经统一被处理 + * + * @param model + * @return + */ + E insert(E model); + + /** + * 更新数据 + * + * 不需要做锁状态处理 + * 不需要判断是否成功 + * 能往下走的只能是成功 + * 异常问题 已经统一被处理 + * + * @param model + * @return + */ + E update(E model); + + + /** + * 删除数据(物理删除,从数据库中彻底删除) + * + * 不需要做锁状态处理 + * 不需要判断是否成功 + * 能往下走的只能是成功 + * 异常问题 已经统一被处理 + * + * @param id + * @return + * @see int delete(T entity) + */ + int delete(String id); + + + /** + * 删除数据(物理删除,从数据库中彻底删除) + * + * 不需要做锁状态处理 + * 不需要判断是否成功 + * 能往下走的只能是成功 + * 异常问题 已经统一被处理 + * + * @param model + * @return + */ + int delete(E model); + + + /** + * 批量物理删除 + * + * 不需要做锁状态处理 + * 不需要判断是否成功 + * 能往下走的只能是成功 + * 异常问题 已经统一被处理 + * + * @param ids + * @return + */ + int deleteAll(String[] ids); + + /** + * 批量物理删除 + * + * 不需要做锁状态处理 + * 不需要判断是否成功 + * 能往下走的只能是成功 + * 异常问题 已经统一被处理 + * + * @param models + * @return + */ + int deleteAll(Collection models); + + + /** + * 查询数据列表 + * + * @param model + * @return + */ + List findList(E model); + + /** + * 查询所有数据列表 + * + * @return + * @see List findAllList(T entity) + */ + //Page findPage(Page page, T t); + + +} + + + + + diff --git a/opsli-core/src/main/java/org/opsli/core/cache/local/CacheUtil.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/cache/local/CacheUtil.java similarity index 100% rename from opsli-core/src/main/java/org/opsli/core/cache/local/CacheUtil.java rename to opsli-base-support/opsli-core/src/main/java/org/opsli/core/cache/local/CacheUtil.java diff --git a/opsli-core/src/main/java/org/opsli/core/cache/pushsub/entity/CacheDataEntity.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/cache/pushsub/entity/CacheDataEntity.java similarity index 100% rename from opsli-core/src/main/java/org/opsli/core/cache/pushsub/entity/CacheDataEntity.java rename to opsli-base-support/opsli-core/src/main/java/org/opsli/core/cache/pushsub/entity/CacheDataEntity.java diff --git a/opsli-core/src/main/java/org/opsli/core/cache/pushsub/enums/CacheType.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/cache/pushsub/enums/CacheType.java similarity index 100% rename from opsli-core/src/main/java/org/opsli/core/cache/pushsub/enums/CacheType.java rename to opsli-base-support/opsli-core/src/main/java/org/opsli/core/cache/pushsub/enums/CacheType.java diff --git a/opsli-core/src/main/java/org/opsli/core/cache/pushsub/enums/MsgArgsType.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/cache/pushsub/enums/MsgArgsType.java similarity index 100% rename from opsli-core/src/main/java/org/opsli/core/cache/pushsub/enums/MsgArgsType.java rename to opsli-base-support/opsli-core/src/main/java/org/opsli/core/cache/pushsub/enums/MsgArgsType.java diff --git a/opsli-core/src/main/java/org/opsli/core/cache/pushsub/enums/PushSubType.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/cache/pushsub/enums/PushSubType.java similarity index 100% rename from opsli-core/src/main/java/org/opsli/core/cache/pushsub/enums/PushSubType.java rename to opsli-base-support/opsli-core/src/main/java/org/opsli/core/cache/pushsub/enums/PushSubType.java diff --git a/opsli-core/src/main/java/org/opsli/core/cache/pushsub/handler/DictHandler.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/cache/pushsub/handler/DictHandler.java similarity index 100% rename from opsli-core/src/main/java/org/opsli/core/cache/pushsub/handler/DictHandler.java rename to opsli-base-support/opsli-core/src/main/java/org/opsli/core/cache/pushsub/handler/DictHandler.java diff --git a/opsli-core/src/main/java/org/opsli/core/cache/pushsub/handler/EdenDataHandler.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/cache/pushsub/handler/EdenDataHandler.java similarity index 100% rename from opsli-core/src/main/java/org/opsli/core/cache/pushsub/handler/EdenDataHandler.java rename to opsli-base-support/opsli-core/src/main/java/org/opsli/core/cache/pushsub/handler/EdenDataHandler.java diff --git a/opsli-core/src/main/java/org/opsli/core/cache/pushsub/handler/HotDataHandler.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/cache/pushsub/handler/HotDataHandler.java similarity index 100% rename from opsli-core/src/main/java/org/opsli/core/cache/pushsub/handler/HotDataHandler.java rename to opsli-base-support/opsli-core/src/main/java/org/opsli/core/cache/pushsub/handler/HotDataHandler.java diff --git a/opsli-core/src/main/java/org/opsli/core/cache/pushsub/handler/RedisPushSubHandler.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/cache/pushsub/handler/RedisPushSubHandler.java similarity index 100% rename from opsli-core/src/main/java/org/opsli/core/cache/pushsub/handler/RedisPushSubHandler.java rename to opsli-base-support/opsli-core/src/main/java/org/opsli/core/cache/pushsub/handler/RedisPushSubHandler.java diff --git a/opsli-core/src/main/java/org/opsli/core/cache/pushsub/msgs/CacheDataMsgFactory.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/cache/pushsub/msgs/CacheDataMsgFactory.java similarity index 100% rename from opsli-core/src/main/java/org/opsli/core/cache/pushsub/msgs/CacheDataMsgFactory.java rename to opsli-base-support/opsli-core/src/main/java/org/opsli/core/cache/pushsub/msgs/CacheDataMsgFactory.java diff --git a/opsli-core/src/main/java/org/opsli/core/cache/pushsub/msgs/DictMsgFactory.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/cache/pushsub/msgs/DictMsgFactory.java similarity index 100% rename from opsli-core/src/main/java/org/opsli/core/cache/pushsub/msgs/DictMsgFactory.java rename to opsli-base-support/opsli-core/src/main/java/org/opsli/core/cache/pushsub/msgs/DictMsgFactory.java diff --git a/opsli-core/src/main/java/org/opsli/core/cache/pushsub/receiver/RedisPushSubReceiver.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/cache/pushsub/receiver/RedisPushSubReceiver.java similarity index 100% rename from opsli-core/src/main/java/org/opsli/core/cache/pushsub/receiver/RedisPushSubReceiver.java rename to opsli-base-support/opsli-core/src/main/java/org/opsli/core/cache/pushsub/receiver/RedisPushSubReceiver.java diff --git a/opsli-base-support/opsli-core/src/main/java/org/opsli/core/conf/MyBatisPlusConfig.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/conf/MyBatisPlusConfig.java new file mode 100644 index 00000000..b086e07d --- /dev/null +++ b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/conf/MyBatisPlusConfig.java @@ -0,0 +1,44 @@ +package org.opsli.core.conf; + +import com.baomidou.mybatisplus.extension.plugins.OptimisticLockerInterceptor; +import com.baomidou.mybatisplus.extension.plugins.inner.OptimisticLockerInnerInterceptor; +import lombok.extern.slf4j.Slf4j; +import org.apache.ibatis.session.SqlSessionFactory; +import org.opsli.core.conf.mybatis.AutoFillInterceptor; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; +import org.springframework.transaction.annotation.EnableTransactionManagement; + + +/** + * @Author parker + * + * MyBatis - Plus 配置 + * + */ +@Slf4j +@EnableTransactionManagement //开启事务 +@Configuration +public class MyBatisPlusConfig { + + /*** + * 乐观锁 + * @return + */ + @Bean + public OptimisticLockerInterceptor optimisticLockerInterceptor(){ + return new OptimisticLockerInterceptor(); + } + + /** + * Mybatis 拦截器 + * @param sqlSessionFactory + * @return + */ + @Bean + public String myInterceptor(SqlSessionFactory sqlSessionFactory) { + sqlSessionFactory.getConfiguration().addInterceptor(new AutoFillInterceptor()); + return "interceptor"; + } + +} diff --git a/opsli-core/src/main/java/org/opsli/core/conf/RedisMessageListenerConfig.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/conf/RedisMessageListenerConfig.java similarity index 100% rename from opsli-core/src/main/java/org/opsli/core/conf/RedisMessageListenerConfig.java rename to opsli-base-support/opsli-core/src/main/java/org/opsli/core/conf/RedisMessageListenerConfig.java diff --git a/opsli-base-support/opsli-core/src/main/java/org/opsli/core/conf/mybatis/AutoFillInterceptor.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/conf/mybatis/AutoFillInterceptor.java new file mode 100644 index 00000000..dbdf6578 --- /dev/null +++ b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/conf/mybatis/AutoFillInterceptor.java @@ -0,0 +1,161 @@ +package org.opsli.core.conf.mybatis; + +import cn.hutool.core.bean.BeanUtil; +import cn.hutool.core.util.ReflectUtil; +import lombok.extern.slf4j.Slf4j; +import org.apache.ibatis.executor.Executor; +import org.apache.ibatis.mapping.MappedStatement; +import org.apache.ibatis.mapping.SqlCommandType; +import org.apache.ibatis.plugin.*; +import org.opsli.common.constants.MyBatisConstants; +import org.springframework.stereotype.Component; + +import java.lang.reflect.Field; +import java.lang.reflect.InvocationTargetException; +import java.util.*; + +/** + * MyBatis 拦截器 注入属性用 + * + * PS:Plus中的自动注入器太难用了 + * + * 参考地址:https://www.cnblogs.com/qingshan-tang/p/13299701.html + */ +@Component +@Slf4j +@Intercepts(@Signature(type = Executor.class, method = "update", args = {MappedStatement.class, Object.class})) +public class AutoFillInterceptor implements Interceptor { + + @Override + public Object intercept(Invocation invocation) throws IllegalAccessException, InvocationTargetException { + fillField(invocation); + return invocation.proceed(); + } + + /** + * 注入字段 + * @param invocation + */ + private void fillField(Invocation invocation) { + Object[] args = invocation.getArgs(); + SqlCommandType sqlCommandType = null; + for (int i = 0; i < args.length; i++) { + Object arg = args[i]; + String className = arg.getClass().getName(); + log.info(i + " 参数类型:" + className); + //第一个参数处理。根据它判断是否给“操作属性”赋值。 + if (arg instanceof MappedStatement) {//如果是第一个参数 MappedStatement + MappedStatement ms = (MappedStatement) arg; + sqlCommandType = ms.getSqlCommandType(); + log.info("操作类型:" + sqlCommandType); + if (sqlCommandType == SqlCommandType.INSERT || sqlCommandType == SqlCommandType.UPDATE) {//如果是“增加”或“更新”操作,则继续进行默认操作信息赋值。否则,则退出 + continue; + } else { + break; + } + } + + if (sqlCommandType == SqlCommandType.INSERT) { + // 新增 + this.insertFill(arg); + + } else if (sqlCommandType == SqlCommandType.UPDATE) { + // 修改 + this.updateFill(arg); + } + } + } + + /** + * 新增数据 + * @param arg + */ + public void insertFill(Object arg) { + Field[] fields = ReflectUtil.getFields(arg.getClass()); + for (Field f : fields) { + f.setAccessible(true); + switch (f.getName()) { + // 创建人 + case MyBatisConstants.FIELD_CREATE_BY: + setProperty(arg, MyBatisConstants.FIELD_CREATE_BY, "测试"); + break; + // 创建日期 + case MyBatisConstants.FIELD_CREATE_TIME: + setProperty(arg, MyBatisConstants.FIELD_CREATE_TIME, new Date()); + break; + // 更新人 + case MyBatisConstants.FIELD_UPDATE_BY: + setProperty(arg, MyBatisConstants.FIELD_UPDATE_BY, "测试"); + break; + // 更新日期 + case MyBatisConstants.FIELD_UPDATE_TIME: + setProperty(arg, MyBatisConstants.FIELD_UPDATE_TIME, new Date()); + break; + // 乐观锁 + case MyBatisConstants.FIELD_OPTIMISTIC_LOCK: + setProperty(arg, MyBatisConstants.FIELD_OPTIMISTIC_LOCK, 0); + break; + // 逻辑删除 + case MyBatisConstants.FIELD_DELETE_LOGIC: + setProperty(arg, MyBatisConstants.FIELD_DELETE_LOGIC, MyBatisConstants.LOGIC_NOT_DELETE_VALUE); + break; + default: + break; + } + f.setAccessible(false); + } + } + + /** + * 修改数据 + * @param arg + */ + public void updateFill(Object arg) { + /** + * TODO 新增 修改的 时间有问题 + * + * 并且 修改 名字不同步 + * + */ + + Field[] fields = ReflectUtil.getFields(arg.getClass()); + for (Field f : fields) { + f.setAccessible(true); + switch (f.getName()) { + // 更新人 + case MyBatisConstants.FIELD_UPDATE_BY: + setProperty(arg, MyBatisConstants.FIELD_UPDATE_BY, "测试修改"); + break; + // 更新日期 + case MyBatisConstants.FIELD_UPDATE_TIME: + setProperty(arg, MyBatisConstants.FIELD_UPDATE_TIME, new Date()); + break; + default: + break; + } + f.setAccessible(false); + } + } + + // ======================================= + + /** + * 为对象的操作属性赋值 + * + * @param bean + */ + private void setProperty(Object bean, String name, Object value) { + //根据需要,将相关属性赋上默认值 + BeanUtil.setProperty(bean, name, value); + } + + @Override + public Object plugin(Object o) { + return Plugin.wrap(o, this); + } + + @Override + public void setProperties(Properties properties) { + } + +} \ No newline at end of file diff --git a/opsli-core/src/main/java/org/opsli/core/handler/GlobalExceptionHandler.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/handler/GlobalExceptionHandler.java similarity index 93% rename from opsli-core/src/main/java/org/opsli/core/handler/GlobalExceptionHandler.java rename to opsli-base-support/opsli-core/src/main/java/org/opsli/core/handler/GlobalExceptionHandler.java index 138af06d..3fd91df4 100644 --- a/opsli-core/src/main/java/org/opsli/core/handler/GlobalExceptionHandler.java +++ b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/handler/GlobalExceptionHandler.java @@ -1,7 +1,7 @@ package org.opsli.core.handler; import lombok.extern.slf4j.Slf4j; -import org.opsli.common.api.ResultVo; +import org.opsli.api.base.result.ResultVo; import org.opsli.common.exception.EmptyException; import org.opsli.common.exception.ServiceException; import org.opsli.core.msg.CoreMsg; @@ -70,7 +70,7 @@ public class GlobalExceptionHandler { @ResponseBody public ResultVo sqlIntegrityConstraintViolationException(EmptyException e) { log.error("数据异常:{}",e.getMessage(),e); - ResultVo errorR = ResultVo.error(CoreMsg.MySQL_EXCEPTION_SQL_INTEGRITY_CONSTRAINT_VIOLATION.getMessage()); + ResultVo errorR = ResultVo.error(CoreMsg.SQL_EXCEPTION_INTEGRITY_CONSTRAINT_VIOLATION.getMessage()); errorR.setCode(e.getCode()); return errorR; } diff --git a/opsli-core/src/main/java/org/opsli/core/msg/CoreMsg.java b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/msg/CoreMsg.java similarity index 66% rename from opsli-core/src/main/java/org/opsli/core/msg/CoreMsg.java rename to opsli-base-support/opsli-core/src/main/java/org/opsli/core/msg/CoreMsg.java index b838aa68..864a8ca0 100644 --- a/opsli-core/src/main/java/org/opsli/core/msg/CoreMsg.java +++ b/opsli-base-support/opsli-core/src/main/java/org/opsli/core/msg/CoreMsg.java @@ -11,11 +11,11 @@ import org.opsli.common.base.msg.BaseMsg; */ public enum CoreMsg implements BaseMsg { - /** - * Mybatis-Plus - */ - /** Mybatis-Plus 乐观锁 */ - MYBATIS_OPTIMISTIC_LOCKER(10100,"当前数据已被更改,请刷新重试!"), + /** SQL */ + SQL_EXCEPTION_UPDATE(10100,"更新数据失败,请稍后再次尝试!"), + SQL_EXCEPTION_INSERT(10101,"新增数据失败,请稍后再次尝试!"), + SQL_EXCEPTION_DELETE(10102,"删除数据失败,请稍后再次尝试!"), + SQL_EXCEPTION_INTEGRITY_CONSTRAINT_VIOLATION(10105,"数据主键冲突或者已有该数据!"), /** * Redis @@ -25,7 +25,7 @@ public enum CoreMsg implements BaseMsg { /** * MySQL */ - MySQL_EXCEPTION_SQL_INTEGRITY_CONSTRAINT_VIOLATION(10300,"数据主键冲突或者已有该数据!"), + ; diff --git a/opsli-core/src/main/resources/banner.txt b/opsli-base-support/opsli-core/src/main/resources/banner.txt similarity index 100% rename from opsli-core/src/main/resources/banner.txt rename to opsli-base-support/opsli-core/src/main/resources/banner.txt