BeanAdapterpublic class BeanAdapter extends AbstractAdapterElement This class is the most general type of adapter, utilizing reflective introspection to present a DOM view of all of
the public properties of its value. For example, a property returning a JavaBean such as:
public Person getMyPerson() { ... }
...
class Person {
public String getFirstName();
public String getLastName();
}
would be rendered as: ... ... |
Fields Summary |
---|
private static final Object[] | NULLPARAMS | private static Map | propertyDescriptorCacheCache can savely be static because the cached information is the same for all instances of this class. | private Log | log |
Constructors Summary |
---|
public BeanAdapter()
//~ Constructors ///////////////////////////////////////////////////////////
| public BeanAdapter(AdapterFactory adapterFactory, AdapterNode parent, String propertyName, Object value)
setContext(adapterFactory, parent, propertyName, value);
|
Methods Summary |
---|
protected java.util.List | buildChildAdapters()
log.debug("BeanAdapter building children. PropName = " + getPropertyName());
List<Node> newAdapters = new ArrayList<Node>();
Class type = getPropertyValue().getClass();
PropertyDescriptor[] props = getPropertyDescriptors(getPropertyValue());
if (props.length > 0) {
for (PropertyDescriptor prop : props) {
Method m = prop.getReadMethod();
if (m == null) {
//FIXME: write only property or indexed access
continue;
}
log.debug("Bean reading property method: " + m.getName());
String propertyName = prop.getName();
Object propertyValue;
/*
Unwrap any invocation target exceptions and log them.
We really need a way to control which properties are accessed.
Perhaps with annotations in Java5?
*/
try {
propertyValue = m.invoke(getPropertyValue(), NULLPARAMS);
} catch (Exception e) {
if (e instanceof InvocationTargetException)
e = (Exception) ((InvocationTargetException) e).getTargetException();
log.error(e);
continue;
}
Node childAdapter;
if (propertyValue == null) {
childAdapter = getAdapterFactory().adaptNullValue(this, propertyName);
} else {
childAdapter = getAdapterFactory().adaptNode(this, propertyName, propertyValue);
}
if (childAdapter != null)
newAdapters.add(childAdapter);
if (log.isDebugEnabled()) {
log.debug(this + " adding adapter: " + childAdapter);
}
}
} else {
// No properties found
log.info(
"Class " + type.getName() + " has no readable properties, " + " trying to adapt " + getPropertyName() + " with StringAdapter...");
}
return newAdapters;
| public org.w3c.dom.NodeList | getChildNodes()
NodeList nl = super.getChildNodes();
// Log child nodes for debug:
if (log.isDebugEnabled() && nl != null) {
log.debug("BeanAdapter getChildNodes for: " + getTagName());
log.debug(nl.toString());
}
return nl;
| private synchronized java.beans.PropertyDescriptor[] | getPropertyDescriptors(java.lang.Object bean)Caching facade method to Introspector.getBeanInfo(Class, Class).getPropertyDescriptors();
try {
if (propertyDescriptorCache == null) {
propertyDescriptorCache = new HashMap<Class, PropertyDescriptor[]>();
}
PropertyDescriptor[] props = propertyDescriptorCache.get(bean.getClass());
if (props == null) {
log.debug("Caching property descriptor for " + bean.getClass().getName());
props = Introspector.getBeanInfo(bean.getClass(), Object.class).getPropertyDescriptors();
propertyDescriptorCache.put(bean.getClass(), props);
}
return props;
} catch (IntrospectionException e) {
e.printStackTrace();
throw new StrutsException("Error getting property descriptors for " + bean + " : " + e.getMessage());
}
| public java.lang.String | getTagName()
return getPropertyName();
|
|