1 22 package org.jboss.xb.binding.introspection; 23 24 import java.lang.reflect.Method ; 25 import java.lang.reflect.Field ; 26 import java.lang.reflect.InvocationTargetException ; 27 import java.util.ArrayList ; 28 29 import org.jboss.util.Classes; 30 import org.jboss.xb.binding.JBossXBRuntimeException; 31 32 36 public class FieldInfo 37 { 38 private static final Object [] NO_ARGS = new Object [0]; 39 40 private interface GetValueAccess 41 { 42 Object get(Object owner) throws IllegalAccessException , InvocationTargetException ; 43 } 44 45 public static class GetValueAccessFactory 46 { 47 public static GetValueAccess fieldAccess(final Field field) 48 { 49 return new GetValueAccess() 50 { 51 public Object get(Object owner) throws IllegalAccessException 52 { 53 return field.get(owner); 54 } 55 }; 56 } 57 58 public static GetValueAccess methodAccess(final Method m) 59 { 60 return new GetValueAccess() 61 { 62 public Object get(Object owner) throws IllegalAccessException , InvocationTargetException 63 { 64 return m.invoke(owner, NO_ARGS); 65 } 66 }; 67 } 68 } 69 70 private interface SetValueAccess 71 { 72 void set(Object owner, Object value) throws IllegalAccessException , InvocationTargetException ; 73 } 74 75 public static class SetValueAccessFactory 76 { 77 public static SetValueAccess fieldAccess(final Field field) 78 { 79 return new SetValueAccess() 80 { 81 public void set(Object owner, Object value) throws IllegalAccessException 82 { 83 field.set(owner, value); 84 } 85 }; 86 } 87 88 public static SetValueAccess methodAccess(final Method m) 89 { 90 return new SetValueAccess() 91 { 92 public void set(Object owner, Object value) throws IllegalAccessException , InvocationTargetException 93 { 94 Object [] arguments = new Object [] { value }; 95 try 96 { 97 m.invoke(owner, new Object []{value}); 98 } 99 catch (IllegalArgumentException e) 100 { 101 if (owner == null) 102 throw new IllegalArgumentException ("Null target for " + m.getName()); 103 ArrayList expected = new ArrayList (); 104 Class [] parameters = m.getParameterTypes(); 105 if (parameters != null) 106 { 107 for (int i = 0; i < parameters.length; ++i) 108 expected.add(parameters[i].getName()); 109 } 110 ArrayList actual = new ArrayList (); 111 if (arguments != null) 112 { 113 for (int i = 0; i < arguments.length; ++i) 114 { 115 if (arguments[i] == null) 116 actual.add(null); 117 else 118 actual.add(arguments[i].getClass().getName()); 119 } 120 } 121 throw new IllegalArgumentException ("Wrong arguments. " + m.getName() + " for target " + owner + " expected=" + expected + " actual=" + actual); 122 } 123 } 124 }; 125 } 126 } 127 128 static FieldInfo getFieldInfo(ClassInfo clsInfo, String name) 129 { 130 FieldInfo fieldInfo = null; 131 try 132 { 133 Method getter = Classes.getAttributeGetter(clsInfo.getType(), name); 134 fieldInfo = new FieldInfo(clsInfo.getType(), name, getter); 135 clsInfo.addFieldInfo(fieldInfo); 136 } 137 catch(NoSuchMethodException e) 138 { 139 try 140 { 141 Field field = clsInfo.getType().getField(name); 142 fieldInfo = new FieldInfo(clsInfo.getType(), field); 143 clsInfo.addFieldInfo(fieldInfo); 144 } 145 catch(NoSuchFieldException e1) 146 { 147 fieldInfo = clsInfo.introspect(name); 148 } 149 } 150 return fieldInfo; 151 } 152 153 public static FieldInfo getFieldInfo(Class cls, String fieldName, boolean required) 154 { 155 return ClassInfos.getClassInfo(cls).getFieldInfo(fieldName, required); 156 } 157 158 private final Class owner; 159 private final String name; 160 private final Class type; 161 private final GetValueAccess getter; 162 private SetValueAccess setter; 163 private boolean setterInitialized; 164 165 public FieldInfo(Class owner, String name, Method getter) 166 { 167 this.owner = owner; 168 this.name = name; 169 this.type = getter.getReturnType(); 170 this.getter = GetValueAccessFactory.methodAccess(getter); 171 } 172 173 public FieldInfo(Class owner, String name, Method getter, Method setter) 174 { 175 this.owner = owner; 176 this.name = name; 177 this.type = getter.getReturnType(); 178 this.getter = GetValueAccessFactory.methodAccess(getter); 179 this.setter = SetValueAccessFactory.methodAccess(setter); 180 setterInitialized = true; 181 } 182 183 public FieldInfo(Class owner, Field field) 184 { 185 this.owner = owner; 186 this.name = field.getName(); 187 this.type = field.getType(); 188 this.getter = GetValueAccessFactory.fieldAccess(field); 189 this.setter = SetValueAccessFactory.fieldAccess(field); 190 setterInitialized = true; 191 } 192 193 public Class getOwner() 194 { 195 return owner; 196 } 197 198 public String getName() 199 { 200 return name; 201 } 202 203 public Class getType() 204 { 205 return type; 206 } 207 208 public boolean isReadable() 209 { 210 return true; 211 } 212 213 public boolean isWritable() 214 { 215 if(!setterInitialized) 216 { 217 initializeSetter(); 218 } 219 return setter != null; 220 } 221 222 public Object getValue(Object owner) 223 { 224 try 225 { 226 return getter.get(owner); 227 } 228 catch(Exception e) 229 { 230 throw new JBossXBRuntimeException( 231 "Failed to get value of the property '" + name + "' defined in " + owner + " from instance " + owner, e 232 ); 233 } 234 } 235 236 public void setValue(Object owner, Object value) 237 { 238 if(!isWritable()) 239 { 240 throw new JBossXBRuntimeException( 241 "Failed to find setter or field for property '" + name + "' in " + owner 242 ); 243 } 244 245 try 246 { 247 setter.set(owner, value); 248 } 249 catch(Exception e) 250 { 251 throw new JBossXBRuntimeException( 252 "Failed to set value '" + value + "' for property '" + name + "' defined in " + 253 owner.getClass().getName() + " on instance " + owner, e 254 ); 255 } 256 } 257 258 private void initializeSetter() 259 { 260 try 261 { 262 setter = SetValueAccessFactory.methodAccess(Classes.getAttributeSetter(owner, name, type)); 263 } 264 catch(NoSuchMethodException e) 265 { 266 } 267 setterInitialized = true; 268 } 269 } 270 | Popular Tags |