|
@@ -94,21 +94,10 @@ public class OptimisticLockerInterceptor implements Interceptor {
|
|
|
return invocation.proceed();
|
|
|
}
|
|
|
Object param = args[1];
|
|
|
-
|
|
|
- // wrapper = ew
|
|
|
- AbstractWrapper<?, ?, ?> ew = null;
|
|
|
- // entity = et
|
|
|
- Object et = null;
|
|
|
if (param instanceof Map) {
|
|
|
Map map = (Map) param;
|
|
|
- if (map.containsKey(NAME_ENTITY)) {
|
|
|
- //updateById(et), update(et, wrapper);
|
|
|
- et = map.get(NAME_ENTITY);
|
|
|
- }
|
|
|
- if (map.containsKey(NAME_ENTITY_WRAPPER)) {
|
|
|
- // mapper.update(updEntity, QueryWrapper<>(whereEntity);
|
|
|
- ew = (AbstractWrapper<?, ?, ?>) map.get(NAME_ENTITY_WRAPPER);
|
|
|
- }
|
|
|
+ //updateById(et), update(et, wrapper);
|
|
|
+ Object et = map.getOrDefault(NAME_ENTITY,null);
|
|
|
if (et != null) {
|
|
|
// entity
|
|
|
String methodId = ms.getId();
|
|
@@ -126,28 +115,44 @@ public class OptimisticLockerInterceptor implements Interceptor {
|
|
|
}
|
|
|
Field field = versionField.getField();
|
|
|
Object originalVersionVal = versionField.getField().get(et);
|
|
|
+ if (originalVersionVal == null) {
|
|
|
+ return invocation.proceed();
|
|
|
+ }
|
|
|
Object updatedVersionVal = getUpdatedVersionVal(originalVersionVal);
|
|
|
if (PARAM_UPDATE_METHOD_NAME.equals(methodName)) {
|
|
|
// update(entity, wrapper)
|
|
|
- if (originalVersionVal != null) {
|
|
|
- if (ew == null) {
|
|
|
- UpdateWrapper<?> uw = new UpdateWrapper<>();
|
|
|
- uw.eq(versionField.getColumnName(), originalVersionVal);
|
|
|
- map.put(NAME_ENTITY_WRAPPER, uw);
|
|
|
- field.set(et, updatedVersionVal);
|
|
|
- } else {
|
|
|
- ew.apply(versionField.getColumnName() + " = {0}", originalVersionVal);
|
|
|
- field.set(et, updatedVersionVal);
|
|
|
- //TODO: should remove version=oldval condition from aw; 0827 by k神
|
|
|
- }
|
|
|
+ // mapper.update(updEntity, QueryWrapper<>(whereEntity);
|
|
|
+ AbstractWrapper<?, ?, ?> ew = (AbstractWrapper<?, ?, ?>) map.getOrDefault(NAME_ENTITY_WRAPPER, null);
|
|
|
+ if (ew == null) {
|
|
|
+ UpdateWrapper<?> uw = new UpdateWrapper<>();
|
|
|
+ uw.eq(versionField.getColumnName(), originalVersionVal);
|
|
|
+ map.put(NAME_ENTITY_WRAPPER, uw);
|
|
|
+ field.set(et, updatedVersionVal);
|
|
|
+ } else {
|
|
|
+ ew.apply(versionField.getColumnName() + " = {0}", originalVersionVal);
|
|
|
+ field.set(et, updatedVersionVal);
|
|
|
+ //TODO: should remove version=oldval condition from aw; 0827 by k神
|
|
|
}
|
|
|
return invocation.proceed();
|
|
|
} else {
|
|
|
- dealUpdateById(entityClass, et, versionField, originalVersionVal, updatedVersionVal, map);
|
|
|
+ List<EntityField> fields = entityFieldsCache.computeIfAbsent(entityClass, this::getFieldsFromClazz);
|
|
|
+ Map<String, Object> entityMap = new HashMap<>();
|
|
|
+ for (EntityField ef : fields) {
|
|
|
+ Field fd = ef.getField();
|
|
|
+ entityMap.put(fd.getName(), fd.get(et));
|
|
|
+ }
|
|
|
+ String versionColumnName = versionField.getColumnName();
|
|
|
+ //update to cache
|
|
|
+ versionField.setColumnName(versionColumnName);
|
|
|
+ entityMap.put(field.getName(), updatedVersionVal);
|
|
|
+ entityMap.put(Constants.MP_OPTLOCK_VERSION_ORIGINAL, originalVersionVal);
|
|
|
+ entityMap.put(Constants.MP_OPTLOCK_VERSION_COLUMN, versionColumnName);
|
|
|
+ entityMap.put(Constants.MP_OPTLOCK_ET_ORIGINAL, et);
|
|
|
+ map.put(NAME_ENTITY, entityMap);
|
|
|
Object resultObj = invocation.proceed();
|
|
|
if (resultObj instanceof Integer) {
|
|
|
Integer effRow = (Integer) resultObj;
|
|
|
- if (updatedVersionVal != null && effRow != 0 && field != null) {
|
|
|
+ if (updatedVersionVal != null && effRow != 0) {
|
|
|
//updated version value set to entity.
|
|
|
field.set(et, updatedVersionVal);
|
|
|
}
|
|
@@ -159,39 +164,6 @@ public class OptimisticLockerInterceptor implements Interceptor {
|
|
|
return invocation.proceed();
|
|
|
}
|
|
|
|
|
|
- /**
|
|
|
- * 处理updateById(entity)乐观锁逻辑
|
|
|
- *
|
|
|
- * @param entityClass 实体类
|
|
|
- * @param et 参数entity
|
|
|
- * @param entityVersionField ignore
|
|
|
- * @param originalVersionVal 原来版本的value
|
|
|
- * @param updatedVersionVal 乐观锁自动更新的新value
|
|
|
- * @param map
|
|
|
- */
|
|
|
- @SuppressWarnings({"unchecked", "rawtypes"})
|
|
|
- private void dealUpdateById(Class<?> entityClass, Object et, EntityField entityVersionField,
|
|
|
- Object originalVersionVal, Object updatedVersionVal, Map map) throws IllegalAccessException {
|
|
|
- if (originalVersionVal == null) {
|
|
|
- return;
|
|
|
- }
|
|
|
- List<EntityField> fields = getEntityFields(entityClass);
|
|
|
- Map<String, Object> entityMap = new HashMap<>();
|
|
|
- for (EntityField ef : fields) {
|
|
|
- Field fd = ef.getField();
|
|
|
- entityMap.put(fd.getName(), fd.get(et));
|
|
|
- }
|
|
|
- Field versionField = entityVersionField.getField();
|
|
|
- String versionColumnName = entityVersionField.getColumnName();
|
|
|
- //update to cache
|
|
|
- entityVersionField.setColumnName(versionColumnName);
|
|
|
- entityMap.put(versionField.getName(), updatedVersionVal);
|
|
|
- entityMap.put(Constants.MP_OPTLOCK_VERSION_ORIGINAL, originalVersionVal);
|
|
|
- entityMap.put(Constants.MP_OPTLOCK_VERSION_COLUMN, versionColumnName);
|
|
|
- entityMap.put(Constants.MP_OPTLOCK_ET_ORIGINAL, et);
|
|
|
- map.put(NAME_ENTITY, entityMap);
|
|
|
- }
|
|
|
-
|
|
|
/**
|
|
|
* This method provides the control for version value.<BR>
|
|
|
* Returned value type must be the same as original one.
|
|
@@ -200,18 +172,11 @@ public class OptimisticLockerInterceptor implements Interceptor {
|
|
|
* @return updated version val
|
|
|
*/
|
|
|
protected Object getUpdatedVersionVal(Object originalVersionVal) {
|
|
|
- if (null == originalVersionVal) {
|
|
|
- return null;
|
|
|
- }
|
|
|
Class<?> versionValClass = originalVersionVal.getClass();
|
|
|
- if (long.class.equals(versionValClass)) {
|
|
|
+ if (long.class.equals(versionValClass) || Long.class.equals(versionValClass)) {
|
|
|
return ((long) originalVersionVal) + 1;
|
|
|
- } else if (Long.class.equals(versionValClass)) {
|
|
|
- return ((Long) originalVersionVal) + 1;
|
|
|
- } else if (int.class.equals(versionValClass)) {
|
|
|
+ } else if (int.class.equals(versionValClass) || Integer.class.equals(versionValClass)) {
|
|
|
return ((int) originalVersionVal) + 1;
|
|
|
- } else if (Integer.class.equals(versionValClass)) {
|
|
|
- return ((Integer) originalVersionVal) + 1;
|
|
|
} else if (Date.class.equals(versionValClass)) {
|
|
|
return new Date();
|
|
|
} else if (Timestamp.class.equals(versionValClass)) {
|
|
@@ -235,20 +200,9 @@ public class OptimisticLockerInterceptor implements Interceptor {
|
|
|
public void setProperties(Properties properties) {
|
|
|
// to do nothing
|
|
|
}
|
|
|
-
|
|
|
+
|
|
|
private EntityField getVersionField(Class<?> parameterClass, TableInfo tableInfo) {
|
|
|
- synchronized (parameterClass.getName()) {
|
|
|
- if (versionFieldCache.containsKey(parameterClass)) {
|
|
|
- return versionFieldCache.get(parameterClass);
|
|
|
- }
|
|
|
- // 缓存类信息
|
|
|
- EntityField field = this.getVersionFieldRegular(parameterClass, tableInfo);
|
|
|
- if (field != null) {
|
|
|
- versionFieldCache.put(parameterClass, field);
|
|
|
- return field;
|
|
|
- }
|
|
|
- return null;
|
|
|
- }
|
|
|
+ return versionFieldCache.computeIfAbsent(parameterClass, mapping -> getVersionFieldRegular(parameterClass, tableInfo));
|
|
|
}
|
|
|
|
|
|
/**
|
|
@@ -265,25 +219,10 @@ public class OptimisticLockerInterceptor implements Interceptor {
|
|
|
}).findFirst().orElseGet(() -> this.getVersionFieldRegular(parameterClass.getSuperclass(), tableInfo));
|
|
|
}
|
|
|
|
|
|
- /**
|
|
|
- * 获取实体的反射属性(类似getter)
|
|
|
- *
|
|
|
- * @param parameterClass ignore
|
|
|
- * @return ignore
|
|
|
- */
|
|
|
- private List<EntityField> getEntityFields(Class<?> parameterClass) {
|
|
|
- if (entityFieldsCache.containsKey(parameterClass)) {
|
|
|
- return entityFieldsCache.get(parameterClass);
|
|
|
- }
|
|
|
- List<EntityField> fields = this.getFieldsFromClazz(parameterClass);
|
|
|
- entityFieldsCache.put(parameterClass, fields);
|
|
|
- return fields;
|
|
|
- }
|
|
|
-
|
|
|
private List<EntityField> getFieldsFromClazz(Class<?> parameterClass) {
|
|
|
return ReflectionKit.getFieldList(parameterClass).stream().map(field -> {
|
|
|
field.setAccessible(true);
|
|
|
- return field.isAnnotationPresent(Version.class) ? new EntityField(field, true) : new EntityField(field, false);
|
|
|
+ return new EntityField(field, field.isAnnotationPresent(Version.class));
|
|
|
}).collect(Collectors.toList());
|
|
|
}
|
|
|
|