How to Configure Network Static IP Address and Manage Services on RHEL/CentOS 7.0
2014-10-16 13:27
513 查看
使用动态字节码生成技术实现AOP原理是在运行期间目标字节码加载后,生成目标类的子类,将切面逻辑加入到子类中,所以使用Cglib实现AOP不需要基于接口
定义两个接口
定义实现类:
定义日志拦截:
定义动态实现类
CglibTest
Intercept
业务逻辑
3.3 自定义类加载器
如果我们实现了一个自定义类加载器,在类加载到JVM之前直接修改某些类的方法,并将切入逻辑织入到这个方法里,然后将修改后的字节码文件交给虚拟机运行,那岂不是更直接。
Javassist是一个编辑字节码的框架,可以让你很简单地操作字节码。它可以在运行期定义或修改Class。使用Javassist实现AOP的原理是在字节码加载前直接修改需要切入的方法。这比使用Cglib实现AOP更加高效,并且没太多限制,实现原理如下图:
Business
3.4 字节码转换
自定义的类加载器实现AOP只能拦截自己加载的字节码,那么有没有一种方式能够监控所有类加载器加载字节码呢?有,使用Instrumentation,它是 Java 5 提供的新特性,使用 Instrumentation,开发者可以构建一个字节码转换器,在字节码加载前进行转换。本节使用Instrumentation和javassist来实现AOP。
3.4.1 构建字节码转换器
首先需要创建字节码转换器,该转换器负责拦截Business类,并在Business类的doSomeThing方法前使用javassist加入记录日志的代码。
4 AOP实战
说了这么多理论,那AOP到底能做什么呢? AOP能做的事情非常多。
性能监控,在方法调用前后记录调用时间,方法执行太长或超时报警。
缓存代理,缓存某方法的返回值,下次执行该方法时,直接从缓存里获取。
软件破解,使用AOP修改软件的验证类的判断逻辑。
记录日志,在方法执行前后记录系统日志。
工作流系统,工作流系统需要将业务代码和流程引擎代码混合在一起执行,那么我们可以使用AOP将其分离,并动态挂接业务。
权限验证,方法执行前验证是否有权限执行当前方法,没有则抛出没有权限执行异常,由业务代码捕捉。
定义两个接口
package AOP; public interface Business1 { public void show_Business1(); }
package AOP; public interface Business2 { public void show_Business2(); }
定义实现类:
package AOP; public class Business implements Business1, Business2 { @Override public void show_Business2() { System.out.println("show_Business2"); } @Override public void show_Business1() { System.out.println("show_Business1"); } }
定义日志拦截:
package AOP; import java.lang.reflect.InvocationHandler; import java.lang.reflect.Method; public class LogInvocationHandler implements InvocationHandler { private Object target; // 目标对象 LogInvocationHandler(Object target) { this.target = target; } @Override public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { // 执行原有逻辑 Object rev = method.invoke(target, args); System.out.println(method.getName()+":"); return rev; } }
定义动态实现类
package AOP; import java.lang.reflect.Proxy; public class DynamicProxyDemo { /** * @param args */ public static void main(String[] args) { Class[] proxyInterface = new Class[] { Business1.class, Business2.class }; ClassLoader classLoader = DynamicProxyDemo.class.getClassLoader(); LogInvocationHandler logInvocationHandler = new LogInvocationHandler( new Business()); Business1 business1=(Business1)Proxy.newProxyInstance(classLoader, proxyInterface, logInvocationHandler); business1.show_Business1(); ((Business2)business1).show_Business2(); } }
CglibTest
package Cglib; import net.sf.cglib.proxy.Enhancer; public class CglibTest { public static void main(String[] args) { byteCodeGe(); } public static void byteCodeGe() { // 创建一个织入器 Enhancer enhancer = new Enhancer(); // 设置父类 enhancer.setSuperclass(Business.class); // 设置需要织入的逻辑 enhancer.setCallback(new LogIntercept()); // 使用织入器创建子类 Business newBusiness = (Business) enhancer.create(); newBusiness.show_Business1(); newBusiness.show_Business2(); } }
Intercept
package Cglib; import java.lang.reflect.Method; import net.sf.cglib.proxy.MethodInterceptor; import net.sf.cglib.proxy.MethodProxy; /** * 记录日志 */ public class LogIntercept implements MethodInterceptor { @Override public Object intercept(Object target, Method method, Object[] args, MethodProxy proxy) throws Throwable { // 执行原有逻辑,注意这里是invokeSuper Object rev = proxy.invokeSuper(target, args); // 执行织入的日志 System.out.println("记录日志"); return rev; } }
业务逻辑
package Cglib; public class Business { public void show_Business2() { System.out.println("show_Business2"); } public void show_Business1() { System.out.println("show_Business1"); } }
3.3 自定义类加载器
如果我们实现了一个自定义类加载器,在类加载到JVM之前直接修改某些类的方法,并将切入逻辑织入到这个方法里,然后将修改后的字节码文件交给虚拟机运行,那岂不是更直接。
Javassist是一个编辑字节码的框架,可以让你很简单地操作字节码。它可以在运行期定义或修改Class。使用Javassist实现AOP的原理是在字节码加载前直接修改需要切入的方法。这比使用Cglib实现AOP更加高效,并且没太多限制,实现原理如下图:
public static void main(String[] args) throws Throwable { //获取存放CtClass的容器ClassPool ClassPool cp = ClassPool.getDefault(); CtClass cc = cp.get(className); // CtMethod targetM = null; CtMethod targetM = cc.getDeclaredMethod("doSomeThing"); targetM.insertBefore("{ System.out.println(\"记录日志前\"); }"); targetM.insertAfter("{ System.out.println(\"记录日志后\"); }"); Class c = cc.toClass(); Business b = (Business) c.newInstance(); b.doSomeThing2(); b.doSomeThing(); }
Business
public class Business { public boolean doSomeThing() { System.out.println("doSomeThing"); return true; } public void doSomeThing2() { System.out.println("doSomeThing2"); } }
3.4 字节码转换
自定义的类加载器实现AOP只能拦截自己加载的字节码,那么有没有一种方式能够监控所有类加载器加载字节码呢?有,使用Instrumentation,它是 Java 5 提供的新特性,使用 Instrumentation,开发者可以构建一个字节码转换器,在字节码加载前进行转换。本节使用Instrumentation和javassist来实现AOP。
3.4.1 构建字节码转换器
首先需要创建字节码转换器,该转换器负责拦截Business类,并在Business类的doSomeThing方法前使用javassist加入记录日志的代码。
4 AOP实战
说了这么多理论,那AOP到底能做什么呢? AOP能做的事情非常多。
性能监控,在方法调用前后记录调用时间,方法执行太长或超时报警。
缓存代理,缓存某方法的返回值,下次执行该方法时,直接从缓存里获取。
软件破解,使用AOP修改软件的验证类的判断逻辑。
记录日志,在方法执行前后记录系统日志。
工作流系统,工作流系统需要将业务代码和流程引擎代码混合在一起执行,那么我们可以使用AOP将其分离,并动态挂接业务。
权限验证,方法执行前验证是否有权限执行当前方法,没有则抛出没有权限执行异常,由业务代码捕捉。
相关文章推荐
- How to Configure Static IP Address on CentOS 6.3 Linux Server
- How to Setup NFS (Network File System) on RHEL/CentOS/Fedora and Debian/Ubuntu
- How to Setup NFS (Network File System) on RHEL/CentOS/Fedora and Debian/Ubuntu
- How To Configure Static IP On CentOS 6.4
- How To Install / Configure VNC Server On CentOS 7.0
- howto install Oracle VirtualBox Guest Additions on Fedora, CentOS and Red Hat (RHEL).
- How to Install WineHQ 1.5.27 on Fedora, CentOS and RHEL Linux Distributions
- How to Install and Configure a VNC Server on RedHat Enterprise Linux (RHEL) 6
- How to Install LAMP (Apache 2.4, MySQL 5.6, and PHP 5.4) on CentOS/RHEL 7
- How to Install Tomcat 8.0.27 on CentOS/RHEL and Ubuntu【转】
- How to change CentOS IP address on a cloned VM
- How to Install PostgreSQL 9.5 on CentOS/RHEL 7/6/5 and Fedora 23/22
- How to Install PostgreSQL 10 on CentOS/RHEL 7/6 and Fedora 26/25
- How to configure an NTP client and server on CentOS/RedHat
- How to install and configure NGINX on CentOS 7
- Installing Kubernetes Cluster with 3 minions on CentOS 7 to manage pods and services
- How to Install and Configure Nginx from Source on centos--转
- How to setup Ruby and RubyGems on CentOS?
- How to install and configure Apache, PHP, MySql and phpMyadmin on ubuntu
- Howto Install and Configure ROS on Ubuntu