This commit is contained in:
wentch
2016-01-06 10:03:42 +08:00
parent e9956db441
commit e66ee1bab3
2 changed files with 51 additions and 27 deletions

View File

@@ -109,13 +109,13 @@ public abstract class Sncp {
* <blockquote><pre> * <blockquote><pre>
* public class TestService implements Service{ * public class TestService implements Service{
* *
* public String queryNode(){ * public String findSomeThing(){
* return "hello"; * return "hello";
* } * }
* *
* &#64;MultiRun(selfrun = false) * &#64;MultiRun(selfrun = false)
* public void createSomeThing(TestBean bean){ * public void createSomeThing(TestBean bean){
* "xxxxx" + bean; * //do something
* } * }
* *
* &#64;MultiRun * &#64;MultiRun
@@ -148,28 +148,28 @@ public abstract class Sncp {
* *
* &#64;Override * &#64;Override
* public void createSomeThing(TestBean bean){ * public void createSomeThing(TestBean bean){
* _createSomeThing(false, true, true, bean); * this._createSomeThing(false, true, true, bean);
* } * }
* *
* &#64;SncpDyn(remote = false, index = 0) * &#64;SncpDyn(remote = false, index = 0)
* public void _createSomeThing(boolean selfrunnable, boolean samerunnable, boolean diffrunnable, TestBean bean){ * public void _createSomeThing(boolean selfrunnable, boolean samerunnable, boolean diffrunnable, TestBean bean){
* if(selfrunnable) super.createSomeThing(bean); * if(selfrunnable) super.createSomeThing(bean);
* if (_client== null) return; * if (_client== null) return;
* if (samerunnable) _client.remote(_convert, _sameGroupTransports, 1, true, false, false, bean); * if (samerunnable) _client.remote(_convert, _sameGroupTransports, 0, true, false, false, bean);
* if (diffrunnable) _client.remote(_convert, _diffGroupTransports, 1, true, true, false, bean); * if (diffrunnable) _client.remote(_convert, _diffGroupTransports, 0, true, true, false, bean);
* } * }
* *
* &#64;Override * &#64;Override
* public String updateSomeThing(String id){ * public String updateSomeThing(String id){
* return _updateSomeThing(true, true, true, id); * return this._updateSomeThing(true, true, true, id);
* } * }
* *
* &#64;SncpDyn(remote = false, index = 1) * &#64;SncpDyn(remote = false, index = 1)
* public String _updateSomeThing(boolean selfrunnable, boolean samerunnable, boolean diffrunnable, String id){ * public String _updateSomeThing(boolean selfrunnable, boolean samerunnable, boolean diffrunnable, String id){
* String rs = super.updateSomeThing(id); * String rs = super.updateSomeThing(id);
* if (_client== null) return; * if (_client== null) return;
* if (samerunnable) _client.remote(_convert, _sameGroupTransports, 0, true, false, false, id); * if (samerunnable) _client.remote(_convert, _sameGroupTransports, 1, true, false, false, id);
* if (diffrunnable) _client.remote(_convert, _diffGroupTransports, 0, true, true, false, id); * if (diffrunnable) _client.remote(_convert, _diffGroupTransports, 1, true, true, false, id);
* return rs; * return rs;
* } * }
* } * }
@@ -189,7 +189,7 @@ public abstract class Sncp {
int mod = serviceClass.getModifiers(); int mod = serviceClass.getModifiers();
if (!java.lang.reflect.Modifier.isPublic(mod)) return serviceClass; if (!java.lang.reflect.Modifier.isPublic(mod)) return serviceClass;
if (java.lang.reflect.Modifier.isAbstract(mod)) return serviceClass; if (java.lang.reflect.Modifier.isAbstract(mod)) return serviceClass;
final List<Method> methods = SncpClient.parseMethod(serviceClass, false); final List<Method> methods = SncpClient.parseMethod(serviceClass);
final boolean hasMultiRun = methods.stream().filter(x -> x.getAnnotation(MultiRun.class) != null).findAny().isPresent(); final boolean hasMultiRun = methods.stream().filter(x -> x.getAnnotation(MultiRun.class) != null).findAny().isPresent();
final String supDynName = serviceClass.getName().replace('.', '/'); final String supDynName = serviceClass.getName().replace('.', '/');
final String clientName = SncpClient.class.getName().replace('.', '/'); final String clientName = SncpClient.class.getName().replace('.', '/');
@@ -293,6 +293,7 @@ public abstract class Sncp {
final Annotation[][] anns = method.getParameterAnnotations(); final Annotation[][] anns = method.getParameterAnnotations();
for (int k = 0; k < anns.length; k++) { for (int k = 0; k < anns.length; k++) {
for (Annotation ann : anns[k]) { for (Annotation ann : anns[k]) {
if (ann instanceof SncpDyn || ann instanceof MultiRun) continue; //必须过滤掉 MultiRun、SncpDyn否则生成远程模式Service时会出错
visitAnnotation(mv.visitParameterAnnotation(k, Type.getDescriptor(ann.annotationType()), true), ann); visitAnnotation(mv.visitParameterAnnotation(k, Type.getDescriptor(ann.annotationType()), true), ann);
} }
} }
@@ -345,6 +346,7 @@ public abstract class Sncp {
final Annotation[][] anns = method.getParameterAnnotations(); final Annotation[][] anns = method.getParameterAnnotations();
for (int k = 0; k < anns.length; k++) { for (int k = 0; k < anns.length; k++) {
for (Annotation ann : anns[k]) { for (Annotation ann : anns[k]) {
if (ann instanceof SncpDyn || ann instanceof MultiRun) continue; //必须过滤掉 MultiRun、SncpDyn否则生成远程模式Service时会出错
visitAnnotation(mv.visitParameterAnnotation(k, Type.getDescriptor(ann.annotationType()), true), ann); visitAnnotation(mv.visitParameterAnnotation(k, Type.getDescriptor(ann.annotationType()), true), ann);
} }
} }
@@ -722,7 +724,7 @@ public abstract class Sncp {
try { try {
Field e = newClazz.getDeclaredField("_client"); Field e = newClazz.getDeclaredField("_client");
e.setAccessible(true); e.setAccessible(true);
client = new SncpClient(name, executor, hash(serviceClass), false, newClazz, true, clientAddress, groups); client = new SncpClient(name, executor, hash(serviceClass), false, newClazz, clientAddress, groups);
e.set(rs, client); e.set(rs, client);
} catch (NoSuchFieldException ne) { } catch (NoSuchFieldException ne) {
} }
@@ -794,19 +796,29 @@ public abstract class Sncp {
* return _selfstring == null ? super.toString() : _selfstring; * return _selfstring == null ? super.toString() : _selfstring;
* } * }
* *
* &#64;Override * &#64;SncpDyn(remote = false, index = 0)
* public boolean testChange(TestBean bean) { * public void _createSomeThing(boolean selfrunnable, boolean samerunnable, boolean diffrunnable, TestBean bean){
* return _client.remote(_convert, _transport, 0, bean); * _client.remote(_convert, _transport, 0, selfrunnable, samerunnable, diffrunnable, bean);
* }
*
* &#64;SncpDyn(remote = false, index = 1)
* public String _updateSomeThing(boolean selfrunnable, boolean samerunnable, boolean diffrunnable, String id){
* return _client.remote(_convert, _transport, 1, selfrunnable, samerunnable, diffrunnable, id);
* } * }
* *
* &#64;Override * &#64;Override
* public TestBean findTestBean(long id) { * public void createSomeThing(TestBean bean){
* return _client.remote(_convert, _transport, 1, id); * _client.remote(_convert, _transport, 2, bean);
* } * }
* *
* &#64;Override * &#64;Override
* public void runTestBean(long id, TestBean bean) { * public String findSomeThing(){
* _client.remote(_convert, _transport, 2, id, bean); * return _client.remote(_convert, _transport, 3);
* }
*
* &#64;Override
* public String updateSomeThing(String id){
* return _client.remote(_convert, _transport, 4, id);
* } * }
* } * }
* </pre></blockquote> * </pre></blockquote>
@@ -840,7 +852,7 @@ public abstract class Sncp {
final String anyValueDesc = Type.getDescriptor(AnyValue.class); final String anyValueDesc = Type.getDescriptor(AnyValue.class);
ClassLoader loader = Sncp.class.getClassLoader(); ClassLoader loader = Sncp.class.getClassLoader();
String newDynName = supDynName.substring(0, supDynName.lastIndexOf('/') + 1) + REMOTEPREFIX + serviceClass.getSimpleName(); String newDynName = supDynName.substring(0, supDynName.lastIndexOf('/') + 1) + REMOTEPREFIX + serviceClass.getSimpleName();
final SncpClient client = new SncpClient(name, executor, hash(serviceClass), true, createLocalServiceClass(name, serviceClass), false, clientAddress, groups); final SncpClient client = new SncpClient(name, executor, hash(serviceClass), true, createLocalServiceClass(name, serviceClass), clientAddress, groups);
try { try {
Class newClazz = Class.forName(newDynName.replace('/', '.')); Class newClazz = Class.forName(newDynName.replace('/', '.'));
T rs = (T) newClazz.newInstance(); T rs = (T) newClazz.newInstance();
@@ -946,6 +958,14 @@ public abstract class Sncp {
{ {
mv = new AsmMethodVisitor(cw.visitMethod(ACC_PUBLIC, method.getName(), Type.getMethodDescriptor(method), null, null)); mv = new AsmMethodVisitor(cw.visitMethod(ACC_PUBLIC, method.getName(), Type.getMethodDescriptor(method), null, null));
//mv.setDebug(true); //mv.setDebug(true);
{ //给参数加上 Annotation
final Annotation[][] anns = method.getParameterAnnotations();
for (int k = 0; k < anns.length; k++) {
for (Annotation ann : anns[k]) {
visitAnnotation(mv.visitParameterAnnotation(k, Type.getDescriptor(ann.annotationType()), true), ann);
}
}
}
mv.visitVarInsn(ALOAD, 0); mv.visitVarInsn(ALOAD, 0);
mv.visitFieldInsn(GETFIELD, newDynName, "_client", clientDesc); mv.visitFieldInsn(GETFIELD, newDynName, "_client", clientDesc);
mv.visitVarInsn(ALOAD, 0); mv.visitVarInsn(ALOAD, 0);

View File

@@ -144,7 +144,7 @@ public final class SncpClient {
protected final Consumer<Runnable> executor; protected final Consumer<Runnable> executor;
public SncpClient(final String serviceName, final Consumer<Runnable> executor, final DLong serviceid, boolean remote, final Class serviceClass, public SncpClient(final String serviceName, final Consumer<Runnable> executor, final DLong serviceid, boolean remote, final Class serviceClass,
boolean onlySncpDyn, final InetSocketAddress clientAddress, final HashSet<String> groups) { final InetSocketAddress clientAddress, final HashSet<String> groups) {
this.remote = remote; this.remote = remote;
this.executor = executor; this.executor = executor;
this.serviceClass = serviceClass; this.serviceClass = serviceClass;
@@ -156,7 +156,7 @@ public final class SncpClient {
this.serviceid = serviceid; this.serviceid = serviceid;
final List<SncpAction> methodens = new ArrayList<>(); final List<SncpAction> methodens = new ArrayList<>();
//------------------------------------------------------------------------------ //------------------------------------------------------------------------------
for (java.lang.reflect.Method method : parseMethod(serviceClass, onlySncpDyn)) { //远程模式下onlySncpDyn = false for (java.lang.reflect.Method method : parseMethod(serviceClass)) {
SncpAction en = new SncpAction(method, Sncp.hash(method)); SncpAction en = new SncpAction(method, Sncp.hash(method));
methodens.add(en); methodens.add(en);
} }
@@ -190,7 +190,7 @@ public final class SncpClient {
+ ", groups = " + groups + ", actions.size = " + actions.length + ")"; + ", groups = " + groups + ", actions.size = " + actions.length + ")";
} }
public static List<Method> parseMethod(final Class serviceClass, boolean onlySncpDyn) { //远程模式下onlySncpDyn = false public static List<Method> parseMethod(final Class serviceClass) {
final List<Method> list = new ArrayList<>(); final List<Method> list = new ArrayList<>();
final List<Method> multis = new ArrayList<>(); final List<Method> multis = new ArrayList<>();
final Map<DLong, Method> actionids = new HashMap<>(); final Map<DLong, Method> actionids = new HashMap<>();
@@ -204,7 +204,7 @@ public final class SncpClient {
if (method.getName().equals("equals") || method.getName().equals("hashCode")) continue; if (method.getName().equals("equals") || method.getName().equals("hashCode")) continue;
if (method.getName().equals("notify") || method.getName().equals("notifyAll") || method.getName().equals("wait")) continue; if (method.getName().equals("notify") || method.getName().equals("notifyAll") || method.getName().equals("wait")) continue;
if (method.getName().equals("init") || method.getName().equals("destroy")) continue; if (method.getName().equals("init") || method.getName().equals("destroy")) continue;
if (onlySncpDyn && method.getAnnotation(SncpDyn.class) == null) continue; //if (onlySncpDyn && method.getAnnotation(SncpDyn.class) == null) continue;
DLong actionid = Sncp.hash(method); DLong actionid = Sncp.hash(method);
Method old = actionids.get(actionid); Method old = actionids.get(actionid);
if (old != null) { if (old != null) {
@@ -219,11 +219,15 @@ public final class SncpClient {
list.add(method); list.add(method);
} }
} }
list.addAll(multis); multis.sort((m1, m2) -> m1.getAnnotation(SncpDyn.class).index() - m2.getAnnotation(SncpDyn.class).index());
if (onlySncpDyn && list.size() > 1) { list.sort((Method o1, Method o2) -> {
list.sort((m1, m2) -> m1.getAnnotation(SncpDyn.class).index() - m2.getAnnotation(SncpDyn.class).index()); if (!o1.getName().equals(o2.getName())) return o1.getName().compareTo(o2.getName());
} if (o1.getParameterCount() != o2.getParameterCount()) return o1.getParameterCount() - o2.getParameterCount();
return list; return 0;
});
//带SncpDyn必须排在前面
multis.addAll(list);
return multis;
} }
public <T> T remote(final BsonConvert convert, Transport transport, final int index, final Object... params) { public <T> T remote(final BsonConvert convert, Transport transport, final int index, final Object... params) {