Nutz: 一个很不错的SSH替代方案
http://code.google.com/p/nutz/
研究了一段时间了, 整个项目现时只依赖
javassist.
但是,javassist的确很大,300多k, 整个nutz才500k, 有喧宾夺主之意.
而, nutz依赖javassist只有Aop.
故, 我在闲暇之余, 用asm 3.2实现了nutz的aop部分.
实现效果: 约30K, 压缩后15k, 加上asm 3.2的43k, 加起来不到60K. (*^__^*) 嘻嘻……
换句话说, 如果
换上这个实现, nutz+asm 才 640k左右. O(∩_∩)O哈哈~ 狂笑中
整个aop的实现, 分成几个部分:
1. 写入模板字段
2. 继承父类的构造方法
3. 覆写需要aop拦截的方法
4. 写入模板方法
5. 生成类的二进制数据, 交给ClassLoader生成Class实例
6. 注入模板字段的值
完成!
代码在:
http://code.google.com/p/nutzlab/source/browse/#svn/trunk/Nutz.Aop-ASM
或者可以在附件中找到源码. 版本rev 81
代码片段1:
public byte[] toByteArray(){
addField();
addConstructors();
addAopMethods();
enhandMethod();
return cw.toByteArray();
}
代码片段2(写入其中一个模板方法):
static void addMethod_before(ClassVisitor cv, String _Nut_myName){
MethodVisitor mv = cv.visitMethod(ACC_PRIVATE + ACC_VARARGS, "_Nut_before", "(I[Ljava/lang/Object;)Z", null, null);
mv.visitCode();
mv.visitFieldInsn(GETSTATIC, _Nut_myName, "_$$Nut_methodArray", "[Ljava/lang/reflect/Method;");
mv.visitVarInsn(ILOAD, 1);
mv.visitInsn(AALOAD);
mv.visitVarInsn(ASTORE, 3);
mv.visitFieldInsn(GETSTATIC, _Nut_myName, "_$$Nut_methodInterceptorList", "[Ljava/util/List;");
mv.visitVarInsn(ILOAD, 1);
mv.visitInsn(AALOAD);
mv.visitVarInsn(ASTORE, 4);
mv.visitInsn(ICONST_1);
mv.visitVarInsn(ISTORE, 5);
mv.visitVarInsn(ALOAD, 4);
mv.visitMethodInsn(INVOKEINTERFACE, "java/util/List", "iterator", "()Ljava/util/Iterator;");
mv.visitVarInsn(ASTORE, 7);
Label l0 = new Label();
mv.visitJumpInsn(GOTO, l0);
Label l1 = new Label();
mv.visitLabel(l1);
mv.visitFrame(F_FULL, 8, new Object[] { _Nut_myName, INTEGER, "[Ljava/lang/Object;", "java/lang/reflect/Method", "java/util/List", INTEGER, TOP, "java/util/Iterator" }, 0, new Object[] {});
mv.visitVarInsn(ALOAD, 7);
mv.visitMethodInsn(INVOKEINTERFACE, "java/util/Iterator", "next", "()Ljava/lang/Object;");
mv.visitTypeInsn(CHECKCAST, "org/nutz/aop/MethodInterceptor");
mv.visitVarInsn(ASTORE, 6);
mv.visitVarInsn(ILOAD, 5);
mv.visitVarInsn(ALOAD, 6);
mv.visitVarInsn(ALOAD, 0);
mv.visitVarInsn(ALOAD, 3);
mv.visitVarInsn(ALOAD, 2);
mv.visitMethodInsn(INVOKEINTERFACE, "org/nutz/aop/MethodInterceptor", "beforeInvoke", "(Ljava/lang/Object;Ljava/lang/reflect/Method;[Ljava/lang/Object;)Z");
mv.visitInsn(IAND);
mv.visitVarInsn(ISTORE, 5);
mv.visitLabel(l0);
mv.visitFrame(F_SAME, 0, null, 0, null);
mv.visitVarInsn(ALOAD, 7);
mv.visitMethodInsn(INVOKEINTERFACE, "java/util/Iterator", "hasNext", "()Z");
mv.visitJumpInsn(IFNE, l1);
mv.visitVarInsn(ILOAD, 5);
mv.visitInsn(IRETURN);
mv.visitMaxs(5, 8);
mv.visitEnd();
}
好. 欢迎拍砖. 狠狠地拍!!