1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16 package net.sf.composite.extract.extractors;
17
18 import java.lang.reflect.Method;
19
20 import net.sf.composite.extract.ComponentAccessorException;
21 import net.sf.composite.util.ObjectUtils;
22 import net.sf.composite.util.StringUtils;
23
24 /***
25 * Extracts the components of a composite by using reflection to access the
26 * getter method for a set property name
27 *
28 * @author Matt Sgarlata
29 * @since Feb 2, 2006
30 */
31 public abstract class BasePropertyComponentAccessor extends BaseComponentAccessor {
32
33 private static final String DEFAULT_COMPONENT_PROPERTY = "components";
34
35 private String componentProperty;
36
37 public BasePropertyComponentAccessor() {
38 super();
39 }
40
41 public BasePropertyComponentAccessor(String componentProperty) {
42 super();
43 this.componentProperty = componentProperty;
44 }
45
46 /***
47 * Returns the type of the property of the target object, as determined by
48 * the return type of the getter method for that property
49 *
50 * @param object
51 * the object
52 * @param propertyName
53 * the name of the property for which we would like to know the
54 * type
55 * @throws Exception
56 * if an error occurrs
57 */
58 protected Class getType(Object object, String propertyName) throws Exception {
59
60 String methodName = "get" + StringUtils.capitalize(propertyName);
61
62 Method method = object.getClass().getMethod(methodName, (Class[]) null);
63
64 return method.getReturnType();
65 }
66
67 /***
68 * Returns the value of the property <code>propertyName</code> in target
69 * <code>object</code>.
70 *
71 * @param object
72 * the object
73 * @param propertyName
74 * the name of the property to read
75 * @throws Exception
76 * if an error occurrs
77 */
78 protected Object invokeGetter(Object object, String propertyName) throws Exception {
79
80 String methodName = "get" + StringUtils.capitalize(propertyName);
81
82 Method method = object.getClass().getMethod(methodName, (Class[]) null);
83
84 return method.invoke(object, (Object[]) null);
85 }
86
87 /***
88 * Sets the value of the property <code>propertyname</code> to the value
89 * <code>value</code> for the target <code>object</code>.
90 *
91 * @param object
92 * the object
93 * @param propertyName
94 * the name of the property to change
95 * @param value
96 * the new value for the property
97 * @throws Exception
98 * if an error occurrs
99 */
100 protected void invokeSetter(Object object, String propertyName, Object value) throws Exception {
101
102 String methodName = "set" + StringUtils.capitalize(propertyName);
103
104
105
106 Method[] methods = object.getClass().getMethods();
107 Method method = null;
108 for (int i=0; i<methods.length; i++) {
109 String candidateMethodName = methods[i].getName();
110 if (candidateMethodName.equals(methodName)) {
111 Class[] parameterTypes = methods[i].getParameterTypes();
112 if (parameterTypes != null &&
113 parameterTypes.length == 1 &&
114 parameterTypes[0].isAssignableFrom(value.getClass())) {
115 method = methods[i];
116 break;
117 }
118 }
119 }
120
121
122 if (method == null) {
123 throw new ComponentAccessorException(
124 "Could not find the setter method for property '"
125 + propertyName + "' of object "
126 + ObjectUtils.getObjectDescription(object));
127 }
128
129
130 method.invoke(object, new Object[] { value });
131 }
132
133 public String getComponentProperty() {
134 if (componentProperty == null) {
135 componentProperty = DEFAULT_COMPONENT_PROPERTY;
136 }
137 return componentProperty;
138 }
139
140 public void setComponentProperty(String componentProperty) {
141 this.componentProperty = componentProperty;
142 }
143
144 }