From 0c1e34c2ccc09a780f92a967902f2cf60c83f200 Mon Sep 17 00:00:00 2001 From: redkale Date: Wed, 20 Dec 2023 17:19:43 +0800 Subject: [PATCH] lock --- src/main/java/module-info.java | 1 + .../java/org/redkale/asm/AsmMethodBean.java | 6 + .../java/org/redkale/asm/AsmMethodBoost.java | 11 +- .../java/org/redkale/boot/Application.java | 4 +- .../cache/spi/CacheAsmMethodBoost.java | 7 +- .../spi/{CacheDyn.java => DynForCache.java} | 2 +- .../java/org/redkale/lock/LockManager.java | 18 ++ .../java/org/redkale/lock/spi/DynForLock.java | 23 +++ .../redkale/lock/spi/LockAsmMethodBoost.java | 169 ++++++++++++++++++ .../redkale/lock/spi/LockManagerProvider.java | 22 +++ .../redkale/lock/spi/LockManagerService.java | 58 ++++++ .../redkale/lock/spi/LockModuleEngine.java | 106 +++++++++++ src/main/java/org/redkale/net/http/Rest.java | 77 +------- src/main/java/org/redkale/net/sncp/Sncp.java | 4 +- .../org/redkale/util/RedkaleClassLoader.java | 1 + .../org/redkale/test/cache/BaseService.java | 28 +++ .../org/redkale/test/cache/SimpleService.java | 13 ++ .../org/redkale/test/cache/TwoService.java | 45 +++++ 18 files changed, 512 insertions(+), 83 deletions(-) rename src/main/java/org/redkale/cache/spi/{CacheDyn.java => DynForCache.java} (92%) create mode 100644 src/main/java/org/redkale/lock/LockManager.java create mode 100644 src/main/java/org/redkale/lock/spi/DynForLock.java create mode 100644 src/main/java/org/redkale/lock/spi/LockAsmMethodBoost.java create mode 100644 src/main/java/org/redkale/lock/spi/LockManagerProvider.java create mode 100644 src/main/java/org/redkale/lock/spi/LockManagerService.java create mode 100644 src/main/java/org/redkale/lock/spi/LockModuleEngine.java create mode 100644 src/test/java/org/redkale/test/cache/BaseService.java create mode 100644 src/test/java/org/redkale/test/cache/SimpleService.java create mode 100644 src/test/java/org/redkale/test/cache/TwoService.java diff --git a/src/main/java/module-info.java b/src/main/java/module-info.java index 06456620b..69a9466c1 100644 --- a/src/main/java/module-info.java +++ b/src/main/java/module-info.java @@ -27,6 +27,7 @@ module org.redkale { exports org.redkale.convert.proto; exports org.redkale.inject; exports org.redkale.lock; + exports org.redkale.lock.spi; exports org.redkale.mq; exports org.redkale.net; exports org.redkale.net.client; diff --git a/src/main/java/org/redkale/asm/AsmMethodBean.java b/src/main/java/org/redkale/asm/AsmMethodBean.java index e6521d4ec..16eafbb4c 100644 --- a/src/main/java/org/redkale/asm/AsmMethodBean.java +++ b/src/main/java/org/redkale/asm/AsmMethodBean.java @@ -3,8 +3,10 @@ */ package org.redkale.asm; +import java.lang.reflect.Method; import java.util.ArrayList; import java.util.List; +import java.util.Map; import org.redkale.convert.json.JsonConvert; /** @@ -38,6 +40,10 @@ public class AsmMethodBean { this.fieldNames = new ArrayList<>(); } + public static AsmMethodBean get(Map map, Method method) { + return map == null ? null : map.get(method.getName() + ":" + Type.getMethodDescriptor(method)); + } + void removeEmptyNames() { if (fieldNames != null) { while (fieldNames.remove(" ")); diff --git a/src/main/java/org/redkale/asm/AsmMethodBoost.java b/src/main/java/org/redkale/asm/AsmMethodBoost.java index 2456005f6..21508eb33 100644 --- a/src/main/java/org/redkale/asm/AsmMethodBoost.java +++ b/src/main/java/org/redkale/asm/AsmMethodBoost.java @@ -30,15 +30,16 @@ public interface AsmMethodBoost { } /** - * 返回的List中参数列表可能会比方法参数量多,因为方法内的临时变量也会存入list中, 所以需要list的元素集合比方法的参数多 * - * @param map - * @param clazz + * 返回一个类所有方法的字节信息, key为: method.getName+':'+Type.getMethodDescriptor(method) * - * @return + * @param clazz Class + * + * @return Map */ - public static Map getMethodBean(Class clazz) { + public static Map getMethodBeans(Class clazz) { Map rs = MethodParamClassVisitor.getMethodParamNames(new HashMap<>(), clazz); + //返回的List中参数列表可能会比方法参数量多,因为方法内的临时变量也会存入list中, 所以需要list的元素集合比方法的参数多 rs.values().forEach(AsmMethodBean::removeEmptyNames); return rs; } diff --git a/src/main/java/org/redkale/boot/Application.java b/src/main/java/org/redkale/boot/Application.java index 47604c7f6..36f1e65d4 100644 --- a/src/main/java/org/redkale/boot/Application.java +++ b/src/main/java/org/redkale/boot/Application.java @@ -32,6 +32,7 @@ import org.redkale.convert.proto.ProtobufFactory; import org.redkale.inject.ResourceEvent; import org.redkale.inject.ResourceFactory; import org.redkale.inject.ResourceTypeLoader; +import org.redkale.lock.spi.LockModuleEngine; import org.redkale.mq.*; import org.redkale.net.*; import org.redkale.net.http.*; @@ -315,8 +316,9 @@ public final class Application { moduleEngines.add(this.sourceModule); //放第一,很多module依赖于source moduleEngines.add(new MessageModuleEngine(this)); moduleEngines.add(new ClusterModuleEngine(this)); - moduleEngines.add(new CacheModuleEngine(this)); moduleEngines.add(new ScheduleModuleEngine(this)); + moduleEngines.add(new CacheModuleEngine(this)); + moduleEngines.add(new LockModuleEngine(this)); //根据本地日志配置文件初始化日志 loggingModule.reconfigLogging(true, appConfig.locaLogProperties); diff --git a/src/main/java/org/redkale/cache/spi/CacheAsmMethodBoost.java b/src/main/java/org/redkale/cache/spi/CacheAsmMethodBoost.java index 836ed5470..4772af7d3 100644 --- a/src/main/java/org/redkale/cache/spi/CacheAsmMethodBoost.java +++ b/src/main/java/org/redkale/cache/spi/CacheAsmMethodBoost.java @@ -71,11 +71,10 @@ public class CacheAsmMethodBoost implements AsmMethodBoost { final String rsMethodName = method.getName() + "_cache"; { - Map methodBeans = AsmMethodBoost.getMethodBean(serviceType); - String desc = Type.getMethodDescriptor(method); - AsmMethodBean methodBean = methodBeans.get(method.getName() + ":" + desc); + Map methodBeans = AsmMethodBoost.getMethodBeans(serviceType); + AsmMethodBean methodBean = AsmMethodBean.get(methodBeans, method); - final String cacheDynDesc = Type.getDescriptor(CacheDyn.class); + final String cacheDynDesc = Type.getDescriptor(DynForCache.class); MethodDebugVisitor mv; AnnotationVisitor av; String signature = null; diff --git a/src/main/java/org/redkale/cache/spi/CacheDyn.java b/src/main/java/org/redkale/cache/spi/DynForCache.java similarity index 92% rename from src/main/java/org/redkale/cache/spi/CacheDyn.java rename to src/main/java/org/redkale/cache/spi/DynForCache.java index a981dc98b..233e5966c 100644 --- a/src/main/java/org/redkale/cache/spi/CacheDyn.java +++ b/src/main/java/org/redkale/cache/spi/DynForCache.java @@ -18,5 +18,5 @@ import java.lang.annotation.Target; @Documented @Target({METHOD}) @Retention(RUNTIME) -public @interface CacheDyn { +public @interface DynForCache { } diff --git a/src/main/java/org/redkale/lock/LockManager.java b/src/main/java/org/redkale/lock/LockManager.java new file mode 100644 index 000000000..8d8543810 --- /dev/null +++ b/src/main/java/org/redkale/lock/LockManager.java @@ -0,0 +1,18 @@ +/* + * + */ +package org.redkale.lock; + +/** + * 锁管理器 + * + *

+ * 详情见: https://redkale.org + * + * @author zhangjx + * + * @since 2.8.0 + */ +public interface LockManager { + +} diff --git a/src/main/java/org/redkale/lock/spi/DynForLock.java b/src/main/java/org/redkale/lock/spi/DynForLock.java new file mode 100644 index 000000000..8cde7a87b --- /dev/null +++ b/src/main/java/org/redkale/lock/spi/DynForLock.java @@ -0,0 +1,23 @@ +/* + * + */ +package org.redkale.lock.spi; + +import java.lang.annotation.Documented; +import static java.lang.annotation.ElementType.METHOD; +import java.lang.annotation.Inherited; +import java.lang.annotation.Retention; +import static java.lang.annotation.RetentionPolicy.RUNTIME; +import java.lang.annotation.Target; + +/** + * + * @author zhangjx + */ +@Inherited +@Documented +@Target({METHOD}) +@Retention(RUNTIME) +public @interface DynForLock { + +} diff --git a/src/main/java/org/redkale/lock/spi/LockAsmMethodBoost.java b/src/main/java/org/redkale/lock/spi/LockAsmMethodBoost.java new file mode 100644 index 000000000..3c5988800 --- /dev/null +++ b/src/main/java/org/redkale/lock/spi/LockAsmMethodBoost.java @@ -0,0 +1,169 @@ +/* + * + */ +package org.redkale.lock.spi; + +import java.lang.annotation.Annotation; +import java.lang.reflect.Method; +import java.lang.reflect.Modifier; +import java.util.ArrayList; +import java.util.List; +import java.util.Map; +import org.redkale.asm.AnnotationVisitor; +import org.redkale.asm.AsmMethodBean; +import org.redkale.asm.AsmMethodBoost; +import org.redkale.asm.Asms; +import org.redkale.asm.ClassWriter; +import org.redkale.asm.Label; +import org.redkale.asm.MethodDebugVisitor; +import static org.redkale.asm.Opcodes.*; +import org.redkale.asm.Type; +import org.redkale.lock.Locked; +import org.redkale.util.RedkaleException; + +/** + * + * @author zhangjx + */ +public class LockAsmMethodBoost implements AsmMethodBoost { + + protected final Class serviceType; + + public LockAsmMethodBoost(Class serviceType) { + this.serviceType = serviceType; + } + + @Override + public String doMethod(ClassWriter cw, String newDynName, String fieldPrefix, Method method, final String newMethodName) { + Locked cached = method.getAnnotation(Locked.class); + if (cached == null) { + return newMethodName; + } + if (Modifier.isFinal(method.getModifiers()) || Modifier.isStatic(method.getModifiers())) { + throw new RedkaleException("@" + Locked.class.getSimpleName() + " can not on final or static method, but on " + method); + } + if (!Modifier.isProtected(method.getModifiers()) && !Modifier.isPublic(method.getModifiers())) { + throw new RedkaleException("@" + Locked.class.getSimpleName() + " must on protected or public method, but on " + method); + } + int acc; + String nowMethodName; + if (newMethodName == null) { + nowMethodName = method.getName(); + acc = Modifier.isProtected(method.getModifiers()) ? ACC_PROTECTED : ACC_PUBLIC; + } else { + acc = ACC_PRIVATE; + nowMethodName = newMethodName; + } + + final String rsMethodName = method.getName() + "_lock"; + { + Map methodBeans = AsmMethodBoost.getMethodBeans(serviceType); + AsmMethodBean methodBean = AsmMethodBean.get(methodBeans, method); + + final String cacheDynDesc = Type.getDescriptor(DynForLock.class); + MethodDebugVisitor mv; + AnnotationVisitor av; + String signature = null; + String[] exceptions = null; + if (methodBean == null) { + Class[] expTypes = method.getExceptionTypes(); + if (expTypes.length > 0) { + exceptions = new String[expTypes.length]; + for (int i = 0; i < expTypes.length; i++) { + exceptions[i] = expTypes[i].getName().replace('.', '/'); + } + } + } else { + signature = methodBean.getSignature(); + exceptions = methodBean.getExceptions(); + } + //需要定义一个新方法调用 this.rsMethodName + mv = new MethodDebugVisitor(cw.visitMethod(acc, nowMethodName, Type.getMethodDescriptor(method), signature, exceptions)); + //mv.setDebug(true); + Label l0 = new Label(); + mv.visitLabel(l0); + { + av = mv.visitAnnotation(cacheDynDesc, true); + av.visitEnd(); + final Annotation[] anns = method.getAnnotations(); + for (Annotation ann : anns) { + if (ann.annotationType() != Locked.class) { + Asms.visitAnnotation(mv.visitAnnotation(Type.getDescriptor(ann.annotationType()), true), ann); + } + } + } + { //给参数加上原有的Annotation + final Annotation[][] anns = method.getParameterAnnotations(); + for (int k = 0; k < anns.length; k++) { + for (Annotation ann : anns[k]) { + Asms.visitAnnotation(mv.visitParameterAnnotation(k, Type.getDescriptor(ann.annotationType()), true), ann); + } + } + } + mv.visitVarInsn(ALOAD, 0); + //传参数 + Class[] paramTypes = method.getParameterTypes(); + List insns = new ArrayList<>(); + int insn = 0; + for (Class pt : paramTypes) { + insn++; + if (pt.isPrimitive()) { + if (pt == long.class) { + mv.visitVarInsn(LLOAD, insn++); + } else if (pt == float.class) { + mv.visitVarInsn(FLOAD, insn++); + } else if (pt == double.class) { + mv.visitVarInsn(DLOAD, insn++); + } else { + mv.visitVarInsn(ILOAD, insn); + } + } else { + mv.visitVarInsn(ALOAD, insn); + } + insns.add(insn); + } + mv.visitMethodInsn(INVOKESPECIAL, newDynName, rsMethodName, Type.getMethodDescriptor(method), false); + if (method.getGenericReturnType() == void.class) { + mv.visitInsn(RETURN); + } else { + Class returnclz = method.getReturnType(); + if (returnclz.isPrimitive()) { + if (returnclz == long.class) { + mv.visitInsn(LRETURN); + } else if (returnclz == float.class) { + mv.visitInsn(FRETURN); + } else if (returnclz == double.class) { + mv.visitInsn(DRETURN); + } else { + mv.visitInsn(IRETURN); + } + } else { + mv.visitInsn(ARETURN); + } + } + if (methodBean != null && paramTypes.length > 0) { + Label l2 = new Label(); + mv.visitLabel(l2); + //mv.visitLocalVariable("this", thisClassDesc, null, l0, l2, 0); + List fieldNames = methodBean.getFieldNames(); + for (int i = 0; i < paramTypes.length; i++) { + mv.visitLocalVariable(fieldNames.get(i), Type.getDescriptor(paramTypes[i]), null, l0, l2, insns.get(i)); + } + } + mv.visitMaxs(20, 20); + mv.visitEnd(); + } + return rsMethodName; + } + + @Override + public void doAfterMethods(ClassWriter cw, String newDynName, String fieldPrefix) { + //do nothing + } + + @Override + public void doInstance(Object service) { + //do nothing + } + +} diff --git a/src/main/java/org/redkale/lock/spi/LockManagerProvider.java b/src/main/java/org/redkale/lock/spi/LockManagerProvider.java new file mode 100644 index 000000000..bd7ac38ba --- /dev/null +++ b/src/main/java/org/redkale/lock/spi/LockManagerProvider.java @@ -0,0 +1,22 @@ +/* + + */ + +package org.redkale.lock.spi; + +import org.redkale.lock.LockManager; +import org.redkale.util.InstanceProvider; + +/** + * + * 自定义的LockManager加载器, 如果标记@Priority加载器的优先级需要大于1000, 1000以下预留给官方加载器 + * + *

+ * 详情见: https://redkale.org + * + * @author zhangjx + * @since 2.8.0 + */ +public interface LockManagerProvider extends InstanceProvider { + +} diff --git a/src/main/java/org/redkale/lock/spi/LockManagerService.java b/src/main/java/org/redkale/lock/spi/LockManagerService.java new file mode 100644 index 000000000..73035c851 --- /dev/null +++ b/src/main/java/org/redkale/lock/spi/LockManagerService.java @@ -0,0 +1,58 @@ +/* + * + */ +package org.redkale.lock.spi; + +import org.redkale.annotation.AutoLoad; +import org.redkale.annotation.Component; +import org.redkale.annotation.Nullable; +import org.redkale.annotation.Resource; +import org.redkale.annotation.ResourceType; +import org.redkale.boot.Application; +import org.redkale.lock.LockManager; +import org.redkale.service.Local; +import org.redkale.service.Service; +import org.redkale.source.CacheSource; +import org.redkale.util.AnyValue; + +/** + * + * @author zhangjx + */ +@Local +@Component +@AutoLoad(false) +@ResourceType(LockManager.class) +public class LockManagerService implements LockManager, Service { + + //是否开启锁 + protected boolean enabled = true; + + //配置 + protected AnyValue config; + + @Resource(required = false) + protected Application application; + + //远程缓存Source + protected CacheSource remoteSource; + + protected LockManagerService(@Nullable CacheSource remoteSource) { + this.remoteSource = remoteSource; + } + + //一般用于独立组件 + public static LockManagerService create(@Nullable CacheSource remoteSource) { + return new LockManagerService(remoteSource); + } + + public boolean enabled() { + return this.enabled; + } + + public LockManagerService enabled(boolean val) { + this.enabled = val; + return this; + } + +} diff --git a/src/main/java/org/redkale/lock/spi/LockModuleEngine.java b/src/main/java/org/redkale/lock/spi/LockModuleEngine.java new file mode 100644 index 000000000..440b3de77 --- /dev/null +++ b/src/main/java/org/redkale/lock/spi/LockModuleEngine.java @@ -0,0 +1,106 @@ +/* + * + */ +package org.redkale.lock.spi; + +import java.util.ArrayList; +import java.util.Iterator; +import java.util.List; +import java.util.ServiceLoader; +import org.redkale.asm.AsmMethodBoost; +import org.redkale.boot.Application; +import org.redkale.boot.ModuleEngine; +import org.redkale.lock.LockManager; +import org.redkale.service.Service; +import org.redkale.util.AnyValue; +import org.redkale.util.InstanceProvider; +import org.redkale.util.RedkaleClassLoader; + +/** + * + * @author zhangjx + */ +public class LockModuleEngine extends ModuleEngine { + + //全局锁管理器 + private LockManager lockManager; + + private AnyValue config; + + public LockModuleEngine(Application application) { + super(application); + } + + /** + * 判断模块的配置项合并策略, 返回null表示模块不识别此配置项 + * + * @param path 配置项路径 + * @param key 配置项名称 + * @param val1 配置项原值 + * @param val2 配置项新值 + * + * @return MergeEnum + */ + @Override + public AnyValue.MergeEnum mergeAppConfigStrategy(String path, String key, AnyValue val1, AnyValue val2) { + if ("".equals(path) && "lock".equals(key)) { + return AnyValue.MergeEnum.REPLACE; + } + return null; + } + + /** + * 动态扩展类的方法 + * + * @param serviceClass 类 + * + * @return 方法动态扩展器 + */ + public AsmMethodBoost createAsmMethodBoost(Class serviceClass) { + return new LockAsmMethodBoost(serviceClass); + } + + /** + * 结束Application.init方法前被调用 + */ + @Override + public void onAppPostInit() { + //设置锁管理器 + this.config = application.getAppConfig().getAnyValue("lock"); + this.lockManager = createManager(this.config); + if (!application.isCompileMode()) { + this.resourceFactory.inject(this.lockManager); + if (this.lockManager instanceof Service) { + ((Service) this.lockManager).init(this.config); + } + } + this.resourceFactory.register("", LockManager.class, this.lockManager); + } + + /** + * 进入Application.shutdown方法被调用 + */ + @Override + public void onAppPreShutdown() { + if (!application.isCompileMode() && this.lockManager instanceof Service) { + ((Service) this.lockManager).destroy(this.config); + } + } + + private LockManager createManager(AnyValue conf) { + Iterator it = ServiceLoader.load(LockManagerProvider.class, application.getClassLoader()).iterator(); + RedkaleClassLoader.putServiceLoader(LockManagerProvider.class); + List providers = new ArrayList<>(); + while (it.hasNext()) { + LockManagerProvider provider = it.next(); + if (provider != null && provider.acceptsConf(conf)) { + RedkaleClassLoader.putReflectionPublicConstructors(provider.getClass(), provider.getClass().getName()); + providers.add(provider); + } + } + for (LockManagerProvider provider : InstanceProvider.sort(providers)) { + return provider.createInstance(); + } + return LockManagerService.create(null).enabled(false); + } +} diff --git a/src/main/java/org/redkale/net/http/Rest.java b/src/main/java/org/redkale/net/http/Rest.java index 7d0921473..ae3bc8871 100644 --- a/src/main/java/org/redkale/net/http/Rest.java +++ b/src/main/java/org/redkale/net/http/Rest.java @@ -113,64 +113,6 @@ public final class Rest { private Rest() { } - static class MethodParamClassVisitor extends ClassVisitor { - - private final Map> fieldMap; - - public MethodParamClassVisitor(int api, final Map> fieldmap) { - super(api); - this.fieldMap = fieldmap; - } - - @Override - public MethodVisitor visitMethod(int access, String name, String desc, String signature, String[] exceptions) { - if (java.lang.reflect.Modifier.isStatic(access)) { - return null; - } - List fieldnames = new ArrayList<>(); - String key = name + ":" + desc; - if (fieldMap.containsKey(key)) { - return null; - } - fieldMap.put(key, fieldnames); - return new MethodVisitor(Opcodes.ASM6) { - @Override - public void visitLocalVariable(String name, String description, String signature, Label start, Label end, int index) { - if (index < 1) { - return; - } - int size = fieldnames.size(); - //index并不会按顺序执行的 - if (index > size) { - for (int i = size; i < index; i++) { - fieldnames.add(" "); - } - fieldnames.set(index - 1, name); - } - fieldnames.set(index - 1, name); - } - }; - } - - //返回的List中参数列表可能会比方法参数量多,因为方法内的临时变量也会存入list中, 所以需要list的元素集合比方法的参数多 - public static Map> getMethodParamNames(Map> map, Class clazz) { - String n = clazz.getName(); - InputStream in = clazz.getResourceAsStream(n.substring(n.lastIndexOf('.') + 1) + ".class"); - if (in == null) { - return map; - } - try { - new ClassReader(Utility.readBytesThenClose(in)).accept(new MethodParamClassVisitor(Opcodes.ASM6, map), 0); - } catch (Exception e) { //无需理会 - } - Class superClass = clazz.getSuperclass(); - if (superClass == Object.class) { - return map; - } - return getMethodParamNames(map, superClass); - } - } - public static JsonFactory createJsonFactory(RestConvert[] converts, RestConvertCoder[] coders) { return createJsonFactory(-1, converts, coders); } @@ -428,7 +370,7 @@ public final class Rest { } catch (Exception e) { //do nothing } - final Map> asmParamMap = namePresent ? null : MethodParamClassVisitor.getMethodParamNames(new HashMap<>(), webSocketType); + final Map asmParamMap = namePresent ? null : AsmMethodBoost.getMethodBeans(webSocketType); final Set messageNames = new HashSet<>(); Method wildcardMethod = null; List mmethods = new ArrayList<>(); @@ -681,11 +623,8 @@ public final class Rest { cw2.visit(V11, ACC_PUBLIC + ACC_FINAL + ACC_SUPER, newDynSuperMessageFullName, null, "java/lang/Object", new String[]{webSocketParamName, "java/lang/Runnable"}); cw2.visitInnerClass(newDynSuperMessageFullName, newDynName, newDynMessageSimpleName + endfix, ACC_PUBLIC + ACC_STATIC); Set paramnames = new HashSet<>(); - String methodesc = method.getName() + ":" + Type.getMethodDescriptor(method); - List names = asmParamMap == null ? null : asmParamMap.get(methodesc); - if (names != null) { - while (names.remove(" ")); //删掉空元素 - } + AsmMethodBean methodBean = asmParamMap == null ? null : AsmMethodBean.get(asmParamMap, method); + List names = methodBean == null ? null : methodBean.getFieldNames(); Parameter[] params = method.getParameters(); final LinkedHashMap paramap = new LinkedHashMap(); //必须使用LinkedHashMap确保顺序 for (int j = 0; j < params.length; j++) { //字段列表 @@ -1896,7 +1835,7 @@ public final class Rest { } catch (Exception e) { //do nothing } - final Map> asmParamMap = namePresent ? null : MethodParamClassVisitor.getMethodParamNames(new HashMap<>(), serviceType); + final Map asmParamMap = namePresent ? null : AsmMethodBoost.getMethodBeans(serviceType); Map innerClassBytesMap = new LinkedHashMap<>(); boolean containsMupload = false; @@ -1949,11 +1888,9 @@ public final class Rest { final int maxStack = 3 + params.length; List varInsns = new ArrayList<>(); int maxLocals = 4; - - List asmParamNames = asmParamMap == null ? null : asmParamMap.get(method.getName() + ":" + Type.getMethodDescriptor(method)); - if (asmParamNames != null) { - while (asmParamNames.remove(" ")); //删掉空元素 - } + + AsmMethodBean methodBean = asmParamMap == null ? null : AsmMethodBean.get(asmParamMap, method); + List asmParamNames = methodBean == null ? null : methodBean.getFieldNames(); List paramlist = new ArrayList<>(); //解析方法中的每个参数 for (int i = 0; i < params.length; i++) { diff --git a/src/main/java/org/redkale/net/sncp/Sncp.java b/src/main/java/org/redkale/net/sncp/Sncp.java index 5aee67542..edc91aa28 100644 --- a/src/main/java/org/redkale/net/sncp/Sncp.java +++ b/src/main/java/org/redkale/net/sncp/Sncp.java @@ -560,7 +560,7 @@ public abstract class Sncp { Class clazz = serviceImplClass; Set methodKeys = new HashSet<>(); do { - Map methodBeans = AsmMethodBoost.getMethodBean(clazz); + Map methodBeans = AsmMethodBoost.getMethodBeans(clazz); for (final Method method : clazz.getDeclaredMethods()) { String mk = Utility.methodKey(method); if (methodKeys.contains(mk)) { @@ -571,7 +571,7 @@ public abstract class Sncp { String newMethodName = methodBoost.doMethod(cw, newDynName, FIELDPREFIX, method, null); if (newMethodName != null) { String desc = Type.getMethodDescriptor(method); - AsmMethodBean methodBean = methodBeans.get(method.getName() + ":" + desc); + AsmMethodBean methodBean = AsmMethodBean.get(methodBeans, method); String signature = null; String[] exceptions = null; if (methodBean == null) { diff --git a/src/main/java/org/redkale/util/RedkaleClassLoader.java b/src/main/java/org/redkale/util/RedkaleClassLoader.java index 3d00dec3c..f71a62e0c 100644 --- a/src/main/java/org/redkale/util/RedkaleClassLoader.java +++ b/src/main/java/org/redkale/util/RedkaleClassLoader.java @@ -57,6 +57,7 @@ public class RedkaleClassLoader extends URLClassLoader { "org.redkale.convert.proto", "org.redkale.inject", "org.redkale.lock", + "org.redkale.lock.spi", "org.redkale.mq", "org.redkale.net", "org.redkale.net.client", diff --git a/src/test/java/org/redkale/test/cache/BaseService.java b/src/test/java/org/redkale/test/cache/BaseService.java new file mode 100644 index 000000000..6cde83d23 --- /dev/null +++ b/src/test/java/org/redkale/test/cache/BaseService.java @@ -0,0 +1,28 @@ +/* + * + */ +package org.redkale.test.cache; + +import java.util.List; +import java.util.Map; +import java.util.Set; + +/** + * + * @author zhangjx + */ +public class BaseService { + + private void run1() { + } + + protected void run2() { + } + + public void run3() { + } + + public Map toMap(List a, Set set){ + return null; + } +} diff --git a/src/test/java/org/redkale/test/cache/SimpleService.java b/src/test/java/org/redkale/test/cache/SimpleService.java new file mode 100644 index 000000000..7e672cb98 --- /dev/null +++ b/src/test/java/org/redkale/test/cache/SimpleService.java @@ -0,0 +1,13 @@ +/* + + */ + +package org.redkale.test.cache; + +/** + * + * @author zhangjx + */ +public class SimpleService extends BaseService { + +} diff --git a/src/test/java/org/redkale/test/cache/TwoService.java b/src/test/java/org/redkale/test/cache/TwoService.java new file mode 100644 index 000000000..5b42f8cd5 --- /dev/null +++ b/src/test/java/org/redkale/test/cache/TwoService.java @@ -0,0 +1,45 @@ +/* + * + */ +package org.redkale.test.cache; + +import java.lang.reflect.Method; +import org.redkale.asm.AsmMethodBoost; +import org.redkale.asm.Type; + +/** + * + * @author zhangjx + */ +public class TwoService extends BaseService { + + @Override + protected void run2() { + } + + @Override + public void run3() { + } + + public static void main(String[] args) throws Throwable { + System.out.println("-------------------------------"); + for (Method m : TwoService.class.getDeclaredMethods()) { + System.out.println(m); + } + System.out.println("-------------------------------"); + for (Method m : SimpleService.class.getDeclaredMethods()) { + System.out.println(m); + } + System.out.println("-------------------------------"); + for (Method m : BaseService.class.getDeclaredMethods()) { + System.out.println(m); + if(m.getName().equals("toMap")) { + System.out.println("张颠三倒四: " + Type.getType(m).getInternalName()); + System.out.println("张颠三倒四: " + Type.getType(m).getDescriptor()); + System.out.println("张颠三倒四: " + Type.getType(m).getClassName()); + } + } + System.out.println("-------------------------------"); + System.out.println(AsmMethodBoost.getMethodBeans(BaseService.class)); + } +}