• 基于jdk1.8.0分析

动态代理Demo

1
2
3
4
5
6
7
8
9
/**
* 被代理对象
* Created by blacktoast on 2018/1/3.
*/

public interface ProxiedObject {
public void doSomething1();
public void doSomething2();
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
import android.util.Log;

/**
* Created by blacktoast on 2018/1/3.
*/

public class ConcreteProxiedObject implements ProxiedObject {
@Override
public void doSomething1() {
Log.e("TAG", "doSomething1");
}

@Override
public void doSomething2() {
Log.e("TAG", "doSomething2");
}
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
import android.util.Log;

import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;

/**
* Created by blacktoast on 2018/1/3.
*/

public class ProxyHandler implements InvocationHandler {
private Object proxied;

public ProxyHandler(Object object) {
this.proxied =object;
}

@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
Log.e("TAG", "do something before proxied object invoked.");
Object invoke = method.invoke(proxied, args);
Log.e("TAG", "do something after proxied object invoked.");
return invoke;
}
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.util.Log;

import com.example.yinhua.aoptest.dl.ConcreteProxiedObject;
import com.example.yinhua.aoptest.dl.ProxiedObject;
import com.example.yinhua.aoptest.dl.ProxyHandler;

import java.lang.reflect.Proxy;

public class MainActivity extends AppCompatActivity {

@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);

testDyProxy();
}

public void testDyProxy() {
ConcreteProxiedObject concreteProxiedObject = new ConcreteProxiedObject();
ProxiedObject proxiedObject = (ProxiedObject) Proxy.newProxyInstance(ProxiedObject.class.getClassLoader(),
new Class[]{ProxiedObject.class},// 或者concreteProxiedObject.getClass().getInterfaces()
new ProxyHandler(concreteProxiedObject));
proxiedObject.doSomething1();
Log.e("TAG", "here:" + proxiedObject.getClass().getName());
}

}
1
2
3
4
5
Log信息:
E/TAG: do something before proxied object invoked.
E/TAG: doSomething1
E/TAG: do something after proxied object invoked.
E/TAG: here:$Proxy0

注意事项

  1. Interface修饰符需为public修饰,没有public修饰时生成的clas.getName()不一样
  2. 生成的代理类的字节码是虚拟机运行时动态生成
  3. 被代理对象需实现接口,实质是对接口的代理(我是这么理解的)

动态代理机制

  1. 生成动态代理处理器/调度器InvocationHandler
  2. 利用Proxy静态方法生成代理对象

源码分析(==把分析写注释上了==)

  • Proxy.newProxyInstance源码分析

通过ClassLoader、Interface生成代理类类型对象;反射生成代理实例

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
public static Object newProxyInstance(ClassLoader loader,
Class<?>[] interfaces,
InvocationHandler h)
throws IllegalArgumentException
{
Objects.requireNonNull(h);

// 拷贝Interface
final Class<?>[] intfs = interfaces.clone();
// Android-changed: sm is always null
// final SecurityManager sm = System.getSecurityManager();
// if (sm != null) {
// checkProxyAccess(Reflection.getCallerClass(), loader, intfs);
// }

/*
* Look up or generate the designated proxy class.
* 依据ClassLoader、Interface生成代理类对象
* ------> 如何生成代理类是关键
*/
Class<?> cl = getProxyClass0(loader, intfs);

/*
* Invoke its constructor with the designated invocation handler.
*/
try {
// Android-changed: sm is always null
// if (sm != null) {
// checkNewProxyPermission(Reflection.getCallerClass(), cl);
// }

// 通过反射生成代理对象
// 反射处理代理对象构造函数
final Constructor<?> cons = cl.getConstructor(constructorParams);
final InvocationHandler ih = h;
// 判断修饰符不为public时设置私有可访问
if (!Modifier.isPublic(cl.getModifiers())) {
// Android-changed: Removed AccessController.doPrivileged
cons.setAccessible(true);
}
// 生成实例
return cons.newInstance(new Object[]{h});
} catch (IllegalAccessException|InstantiationException e) {
throw new InternalError(e.toString(), e);
} catch (InvocationTargetException e) {
Throwable t = e.getCause();
if (t instanceof RuntimeException) {
throw (RuntimeException) t;
} else {
throw new InternalError(t.toString(), t);
}
} catch (NoSuchMethodException e) {
throw new InternalError(e.toString(), e);
}
}
  • getProxyClass0源码分析

Class<?> cl = getProxyClass0(loader, intfs);获取代理类

1
2
3
4
5
6
7
8
9
10
11
12
private static Class<?> getProxyClass0(ClassLoader loader,
Class<?>... interfaces) {
// 判断接口个数是否超出限制65535方法限制,这里不重要,哈哈哈
if (interfaces.length > 65535) {
throw new IllegalArgumentException("interface limit exceeded");
}

// If the proxy class defined by the given loader implementing
// the given interfaces exists, this will simply return the cached copy;
// otherwise, it will create the proxy class via the ProxyClassFactory
return proxyClassCache.get(loader, interfaces);
}
  • proxyClassCache分析

new KeyFactory()、new ProxyClassFactory()这两个对象处理所有代理类的映射

1
2
3
4
5
6
7
/**
* a cache of proxy classes
* 这是代理类的缓存管理
* 注意:new KeyFactory()、new ProxyClassFactory()这两个对象,后面分析用到
*/
private static final WeakCache<ClassLoader, Class<?>[], Class<?>>
proxyClassCache = new WeakCache<>(new KeyFactory(), new ProxyClassFactory());
  • WeakCache get方法分析

通过map获取一个ClassLoader对应的映射关系valuesMap;valuesMap中存储Key和Factory之间的映射;Factory.get()方法封装了通过ValueFactory获取代理对象的逻辑

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
/**
* WeakCache.get(loader, interfaces)
*/
public V get(K key, P parameter) {
Objects.requireNonNull(parameter);

expungeStaleEntries();

Object cacheKey = CacheKey.valueOf(key, refQueue);

// 通过key(ClassLoader)获取映射关系,即CacheKey和Factory之间的映射
// lazily install the 2nd level valuesMap for the particular cacheKey
ConcurrentMap<Object, Supplier<V>> valuesMap = map.get(cacheKey);
if (valuesMap == null) {
// 不存在则创建并put到map中
ConcurrentMap<Object, Supplier<V>> oldValuesMap
= map.putIfAbsent(cacheKey,
valuesMap = new ConcurrentHashMap<>());
if (oldValuesMap != null) {
// 此时map中的valuesMap引用即是oldValuesMap
valuesMap = oldValuesMap;
}
}

// 通过KeyFactory获取Key,Key其实是根据interface的hashcode来识别的
// create subKey and retrieve the possible Supplier<V> stored by that
// subKey from valuesMap
Object subKey = Objects.requireNonNull(subKeyFactory.apply(key, parameter));
// 获取Supplier对象,里面封装了通过ValueFactory获取代理对象的逻辑
Supplier<V> supplier = valuesMap.get(subKey);
Factory factory = null;

while (true) {
if (supplier != null) {
// supplier might be a Factory or a CacheValue<V> instance
// 获取真实的代理对象
V value = supplier.get();
if (value != null) {
return value;
}
}
// else no supplier in cache
// or a supplier that returned null (could be a cleared CacheValue
// or a Factory that wasn't successful in installing the CacheValue)

// lazily construct a Factory
if (factory == null) {
factory = new Factory(key, parameter, subKey, valuesMap);
}

// 生成Supplier接口的Factory对象,存储映射Key和Factory之间的关系
if (supplier == null) {
supplier = valuesMap.putIfAbsent(subKey, factory);
if (supplier == null) {
// successfully installed Factory
supplier = factory;
}
// else retry with winning supplier
} else {
if (valuesMap.replace(subKey, supplier, factory)) {
// successfully replaced
// cleared CacheEntry / unsuccessful Factory
// with our Factory
supplier = factory;
} else {
// retry with current supplier
supplier = valuesMap.get(subKey);
}
}
}
}
  • Factory源码分析

通过Factory生成代理对象

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
private final class Factory implements Supplier<V> {

private final K key;
private final P parameter;
private final Object subKey;
private final ConcurrentMap<Object, Supplier<V>> valuesMap;

Factory(K key, P parameter, Object subKey,
ConcurrentMap<Object, Supplier<V>> valuesMap) {
this.key = key;
this.parameter = parameter;
this.subKey = subKey;
this.valuesMap = valuesMap;
}

@Override
public synchronized V get() { // serialize access
// re-check
Supplier<V> supplier = valuesMap.get(subKey);
if (supplier != this) {
// something changed while we were waiting:
// might be that we were replaced by a CacheValue
// or were removed because of failure ->
// return null to signal WeakCache.get() to retry
// the loop
return null;
}
// else still us (supplier == this)

// create new value
V value = null;
try {
// 通过ValueFactory生成一个代理对象
value = Objects.requireNonNull(valueFactory.apply(key, parameter));
} finally {
if (value == null) { // remove us on failure
valuesMap.remove(subKey, this);
}
}
// the only path to reach here is with non-null value
assert value != null;

// wrap value with CacheValue (WeakReference)
// 对代理对象进行一层包裹,CacheValue实现Supplier接口重写了hashcode和equals方法,好像没什么用啊,没想明白
CacheValue<V> cacheValue = new CacheValue<>(value);

// try replacing us with CacheValue (this should always succeed)
if (valuesMap.replace(subKey, this, cacheValue)) {
// put also in reverseMap
reverseMap.put(cacheValue, Boolean.TRUE);
} else {
throw new AssertionError("Should not reach here");
}

// successfully replaced us with new CacheValue -> return the value
// wrapped by it
return value;
}
}
  • KeyFactory源码分析
1
2
3
4
5
6
7
8
9
10
11
12
13
14
private static final class KeyFactory
implements BiFunction<ClassLoader, Class<?>[], Object>
{
@Override
public Object apply(ClassLoader classLoader, Class<?>[] interfaces) {
switch (interfaces.length) {
// 生成Key,Key有自己重载的Object方法
case 1: return new Key1(interfaces[0]); // the most frequent
case 2: return new Key2(interfaces[0], interfaces[1]);
case 0: return key0;
default: return new KeyX(interfaces);
}
}
}
  • ProxyFactory(ValueFactory)源码分析
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
private static final class ProxyClassFactory
implements BiFunction<ClassLoader, Class<?>[], Class<?>>
{
// prefix for all proxy class names
private static final String proxyClassNamePrefix = "$Proxy";

// next number to use for generation of unique proxy class names
private static final AtomicLong nextUniqueNumber = new AtomicLong();

@Override
public Class<?> apply(ClassLoader loader, Class<?>[] interfaces) {

Map<Class<?>, Boolean> interfaceSet = new IdentityHashMap<>(interfaces.length);
for (Class<?> intf : interfaces) {
/*
* Verify that the class loader resolves the name of this
* interface to the same Class object.
*/
Class<?> interfaceClass = null;
try {
interfaceClass = Class.forName(intf.getName(), false, loader);
} catch (ClassNotFoundException e) {
}

if (interfaceClass != intf) {
throw new IllegalArgumentException(
intf + " is not visible from class loader");
}
/*
* Verify that the Class object actually represents an
* interface.
*/
// 判断是否为接口,只能代理接口
// 只能代理接口的根本原因是java中没有多继承
if (!interfaceClass.isInterface()) {
throw new IllegalArgumentException(
interfaceClass.getName() + " is not an interface");
}
/*
* Verify that this interface is not a duplicate.
*/
if (interfaceSet.put(interfaceClass, Boolean.TRUE) != null) {
throw new IllegalArgumentException(
"repeated interface: " + interfaceClass.getName());
}
}

String proxyPkg = null; // package to define proxy class in
int accessFlags = Modifier.PUBLIC | Modifier.FINAL;

/*
* Record the package of a non-public proxy interface so that the
* proxy class will be defined in the same package. Verify that
* all non-public proxy interfaces are in the same package.
*/
for (Class<?> intf : interfaces) {
int flags = intf.getModifiers();
// 判断interface是否public
// 不是public修饰时,生成的代理类为包名+类名$Proxy1
if (!Modifier.isPublic(flags)) {
accessFlags = Modifier.FINAL;
String name = intf.getName();
int n = name.lastIndexOf('.');
String pkg = ((n == -1) ? "" : name.substring(0, n + 1));
if (proxyPkg == null) {
proxyPkg = pkg;
} else if (!pkg.equals(proxyPkg)) {
throw new IllegalArgumentException(
"non-public interfaces from different packages");
}
}
}

if (proxyPkg == null) {
// if no non-public proxy interfaces, use the default package.
proxyPkg = "";
}

// 这部分逻辑和java不太一样,java生成的代理类为com.sun.proxy$Proxy1,而Android中则通常则生成$Proxy1
{
// Android-changed: Generate the proxy directly instead of calling
// through to ProxyGenerator.
List<Method> methods = getMethods(interfaces);
Collections.sort(methods, ORDER_BY_SIGNATURE_AND_SUBTYPE);
validateReturnTypes(methods);
List<Class<?>[]> exceptions = deduplicateAndGetExceptions(methods);

Method[] methodsArray = methods.toArray(new Method[methods.size()]);
Class<?>[][] exceptionsArray = exceptions.toArray(new Class<?>[exceptions.size()][]);

/*
* Choose a name for the proxy class to generate.
*/
// $Proxy都带有一个数字,这个数字每次生成都会加1
//因为nextUniqueNumber每次都会加1,就生成不同的代理对象
long num = nextUniqueNumber.getAndIncrement();
String proxyName = proxyPkg + proxyClassNamePrefix + num;

// 真正生成动态代理对象,有native层实现
return generateProxy(proxyName, interfaces, loader, methodsArray,
exceptionsArray);
}
}
}


# Java,动态代理  

tocToc: