Java reflection-use reflection to generate jdk dynamic proxy

Source: Internet
Author: User

Java reflection-use reflection to generate jdk dynamic proxy
1. Core classes & Interfaces

The Java. lang. reflect package provides a Proxy class and an InvocationHandler interface. By using this class and interface, you can generate jdk dynamic Proxy class or dynamic Proxy object.

Proxy is the parent class of all dynamic Proxy classes. It provides two static methods to create dynamic Proxy classes and dynamic Proxy objects, as follows:

  Ø static Class GetProxyClass(ClassLoader loader, Class ... interfaces)

  Ø static Object NewProxyInstance(ClassLoader loader, Class [] interfaces, InvocationHandler h)

GetProxyClassReturn the java. lang. Class Object of the proxy Class, and provide the Class loader and interface array to it.NewProxyInstanceReturns the proxy class instance of a specified interface. This interface can forward method calls to the specified calling handler. When each method of the proxy object is executed, the Invoke method of the InvocationHandler object is replaced. In fact, even if the first method is used to obtain a dynamic proxy class, an InvocationHandler object needs to be passed in when the program needs to create an object through this proxy class. That is to say, each proxy object generated by the system has an associated InvocationHandler object.

As shown in the preceding two method parameters, we can generate the proxy class and proxy object that implement this (or multiple) interface only by giving me one or more interfaces.

 

2. Generate proxy objects in two ways

Next we will use the two methods mentioned above to generate a proxy object for an interface (Person.

2.1 interface Person
Package com. tgb. reflect;/*** Target interface ** @ author wangzhipeng **/public interface Person {public void walk (); public void sayHello ();}

 

2.2 construct an InvocationHandler class
Package com. tgb. reflect; import java. lang. reflect. invocationHandler; import java. lang. reflect. method; public class MyInvocationHandler implements InvocationHandler {/*** replace all methods of the proxy object with the following invoke method ** proxy: representing the dynamic proxy object; Method: represents the Method being executed; args: represents the real parameter passed in when the proxy Object method is executed */@ Overridepublic Object invoke (Object proxy, Method method, Object [] args) throws Throwable {// TODO Auto-generated method stubSystem. out. Println (executing method: + method. getName (); if (args! = Null) {System. out. println (the real parameter passed in when the method is executed); for (Object object: args) {System. out. println (object) ;}} else {System. out. println (this method call has no real parameters !);} Return null ;}}

 

2.3 Method 1: Use getProxyClass to generate a proxy object
Package com. tgb. reflect; import java. lang. reflect. constructor; import java. lang. reflect. invocationHandler; import java. lang. reflect. proxy;/*** use getProxyClass to generate Proxy object ** @ author wangzhipeng **/public class TestReflectProxy {@ SuppressWarnings (unchecked) public static void main (String [] args) throws Exception {// 1. Create an InvocationHandler object InvocationHandler myInvocationHandler = new MyInvocationHandler (); // 2. Create a Proxy Class for the Person interface (obtain the bytecode of the Proxy Class) Class proxyClass = Proxy. getProxyClass (Person. class. getClassLoader (), new Class [] {Person. class}); // 3. Obtain the Constructor constructor = proxyClass parameter of the InvocationHandler type according to the byte code of the proxy class. getConstructor (new Class [] {InvocationHandler. class}); // 4. Create the proxy object Person = (person) constructor Based on the constructor. newInstance (myInvocationHandler); // 5. Call the person method of the proxy object. walk (); person. sayHello () ;/*** The output result is as follows: ** the method is being executed: walk. This method call has no real parameters! ** The method is being executed: sayHello. This method call has no real parameters! */}}

 

2.4 Method 2: Use newProxyInstance to generate a proxy object
Package com. tgb. reflect; import java. lang. reflect. invocationHandler; import java. lang. reflect. proxy;/*** use newProxyInstance to generate Proxy object ** @ author wangzhipeng **/public class TestReflectProxy2 {public static void main (String [] args) {// 1. Create an InvocationHandler object InvocationHandler myInvocationHandler = new MyInvocationHandler (); // 2. Use the static method newProxyInstance of the Proxy class to directly generate the Proxy object "Person = (person) Pr" for the Person Interface Oxy. newProxyInstance (Person. class. getClassLoader (), new Class [] {Person. class}, myInvocationHandler); // 3. Call the person method of the proxy object. walk (); person. sayHello ();/*** the output result is as follows: ** the method is being executed: walk. No real parameter is provided for this method call! ** The method is being executed: sayHello. This method call has no real parameters! */}}
3. Dynamic proxy and aop

Next we will expand a small step based on the above example to simulate the following aop principles. In fact, it is very simple. As mentioned above, the Invoke Method for executing the InvocationHandler object is replaced when every method of the proxy object is executed. Therefore, we only need to add our enhancement method before and after the "Reflection execution target method (method. Invoke (target, args)" in the invoke method. The instance code is as follows:

3.1 Target Interface Person
Package com. tgb. reflect. aop;/*** Target interface ** @ author wangzhipeng **/public interface Person {public void walk (); public void sayHello ();}

 

3.2 target category ZhanSan
Package com. tgb. reflect. aop;/*** target class (implementing the Person Interface) ** @ author wangzhipeng **/public class ZhanSan implements Person {@ Overridepublic void sayHello () {System. out. println (I am Zhang San ----> sayHello) ;}@ Overridepublic void walk () {System. out. println (I am Zhang San ----> walk );}}

 

3.3 Extend
Package com. tgb. reflect. aop;/*** enhancement class ** @ author wangzhipeng **/public class Extend {/*** enhancement method 1 */public void ExtendMethod1 () {System. out. println (I am enhancement method 1);}/*** enhancement method 2 */public void ExtendMethod2 () {System. out. println (enhancement method 2 );}}

 

3.4 InvocationHandler class MyInvocationHandler
Package com. tgb. reflect. aop; import java. lang. reflect. invocationHandler; import java. lang. reflect. method; public class MyInvocationHandler implements InvocationHandler {// target Object (Object to be proxy) private Object target; public void setTarget (Object target) implements this.tar get = target ;} /*** all methods for executing the proxy Object will be replaced with the following invoke Method */@ Overridepublic Object invoke (Object proxy, method Method, Object [] args) throws Throwable {// instantiate an Extend extend Extend = new extend (); // execute the Extend method 1 (simulate spring pre-enhancement) extend. extendMethod1 (); Object result = method. invoke (target, args); // [execution target method] // execution enhancement method 2 (Simulating spring post enhancement) extend. extendMethod2 (); return result ;}}

 

3.5 proxy generation factory MyProxyFactory
Package com. tgb. reflect. aop; import java. lang. reflect. proxy;/*** generate the Proxy factory ** @ author wangzhipeng **/public class MyProxyFactory {/** get a target object (the target class must implement the interface) */public static Object getProxy (Object target) {// instantiate an InvocationHandler class, and pass in the target Object MyInvocationHandler myInvocationHandler = new MyInvocationHandler (); myInvocationHandler. setTarget (target); // generate Proxy Object proxyObject = Proxy. newProxyInstance (target. getClass (). getClassLoader (), target. getClass (). getInterfaces (), myInvocationHandler); return proxyObject ;}}

 

3.6 Test
Package com. tgb. reflect. aop;/*** Test class ** @ author wangzhipeng **/public class Test {public static void main (String [] args) {// create an original ZhanSan (implementing the Person Interface) object as TargetPerson zhanSan = new ZhanSan (); // use the proxy factory to generate a zhansan object (Target) proxy object of Person proxyZhanSan = (Person) MyProxyFactory. getProxy (zhanSan); // execute the proxy object method (two enhancement methods of the woven Extend will be executed) proxyZhanSan. walk (); proxyZhanSan. sayHello ();}}

 

3.7 The result is as follows:

 

4. Summary

There are four main Proxy methods (for example). jdk dynamic Proxy mainly uses the getProxyClass and newProxyInstance methods of the Proxy class to generate dynamic Proxy objects for interfaces, replace each method of the executed proxy object with the InvocationHandler method of the InvocationHandler object. This laid the foundation for Spring aop. In addition, in practice, we generally do not directly generate a proxy object for one or more interfaces, but instead generate a proxy object for an interface implementation class (target class.

 

 

 

In fact, we seldom use dynamic proxies in common java programming. The biggest charm of dynamic proxies lies in compiling frameworks or underlying basic code.

 

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.