1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18 package org.apache.commons.lang3.event;
19
20 import java.lang.reflect.InvocationHandler;
21 import java.lang.reflect.Method;
22 import java.lang.reflect.Proxy;
23 import java.util.Arrays;
24 import java.util.HashSet;
25 import java.util.Set;
26
27 import org.apache.commons.lang3.reflect.MethodUtils;
28
29
30
31
32
33
34 public class EventUtils {
35
36 private static final class EventBindingInvocationHandler implements InvocationHandler {
37 private final Object target;
38 private final String methodName;
39 private final Set<String> eventTypes;
40
41
42
43
44
45
46
47
48 EventBindingInvocationHandler(final Object target, final String methodName, final String[] eventTypes) {
49 this.target = target;
50 this.methodName = methodName;
51 this.eventTypes = new HashSet<>(Arrays.asList(eventTypes));
52 }
53
54
55
56
57
58
59
60 private boolean hasMatchingParametersMethod(final Method method) {
61 return MethodUtils.getAccessibleMethod(target.getClass(), methodName, method.getParameterTypes()) != null;
62 }
63
64
65
66
67
68
69
70
71
72
73 @Override
74 public Object invoke(final Object proxy, final Method method, final Object[] parameters) throws Throwable {
75 if (eventTypes.isEmpty() || eventTypes.contains(method.getName())) {
76 if (hasMatchingParametersMethod(method)) {
77 return MethodUtils.invokeMethod(target, methodName, parameters);
78 }
79 return MethodUtils.invokeMethod(target, methodName);
80 }
81 return null;
82 }
83 }
84
85
86
87
88
89
90
91
92
93
94
95 public static <L> void addEventListener(final Object eventSource, final Class<L> listenerType, final L listener) {
96 try {
97 MethodUtils.invokeMethod(eventSource, "add" + listenerType.getSimpleName(), listener);
98 } catch (final ReflectiveOperationException e) {
99 throw new IllegalArgumentException("Unable to add listener for class " + eventSource.getClass().getName()
100 + " and public add" + listenerType.getSimpleName()
101 + " method which takes a parameter of type " + listenerType.getName() + ".");
102 }
103 }
104
105
106
107
108
109
110
111
112
113
114
115
116 public static <L> void bindEventsToMethod(final Object target, final String methodName, final Object eventSource,
117 final Class<L> listenerType, final String... eventTypes) {
118 final L listener = listenerType.cast(Proxy.newProxyInstance(target.getClass().getClassLoader(),
119 new Class[] { listenerType }, new EventBindingInvocationHandler(target, methodName, eventTypes)));
120 addEventListener(eventSource, listenerType, listener);
121 }
122
123
124
125
126
127
128 @Deprecated
129 public EventUtils() {
130
131 }
132 }