001 /** 002 * Attribute.java 003 * jCOLIBRI2 framework. 004 * @author Juan A. Recio-García. 005 * GAIA - Group for Artificial Intelligence Applications 006 * http://gaia.fdi.ucm.es 007 * 03/01/2007 008 */ 009 package jcolibri.cbrcore; 010 011 import java.lang.reflect.Field; 012 013 import jcolibri.exception.AttributeAccessException; 014 015 /** 016 * This class identifies an attribute of a CaseComponent (Java Bean). Attributes are part of CaseComponents and CaseComponentes build a case. 017 * Note that each CaseComponent must be a Java Bean, so this class represents a field of a Java Bean (with its getXXX() and setXXX() methods). 018 * 019 * @see jcolibri.cbrcore.CaseComponent 020 * @author Juan A. Recio-García 021 */ 022 public class Attribute { 023 024 private Field field; 025 026 /** 027 * Creates an Attribute using the Field obtained with Reflection (getClass.getDeclaredField(name)). It is recommended to use the other constructor. 028 */ 029 public Attribute(Field f) 030 { 031 field = f; 032 } 033 034 /** 035 * Creates an attribute. The attribute name must be an existing field of the class and have the get/set() methods. 036 * @param attributeName Name of the field 037 * @param _class Class that the attribute belongs to. 038 */ 039 public Attribute(String attributeName, Class _class) 040 { 041 try { 042 field = _class.getDeclaredField(attributeName); 043 } catch (Exception e) { 044 org.apache.commons.logging.LogFactory.getLog(this.getClass()).error(e + "Attribute: "+ attributeName+ " Class:" + _class.getName()); 045 } 046 } 047 048 /** 049 * Returns the name of the field. 050 */ 051 public String getName() 052 { 053 return field.getName(); 054 } 055 056 /** 057 * Returns the class that this attribute belongs to. 058 */ 059 public Class<?> getDeclaringClass() 060 { 061 return field.getDeclaringClass(); 062 } 063 064 /** 065 * Returns the type of the attribute. 066 */ 067 public Class<?> getType() 068 { 069 return field.getType(); 070 } 071 072 /** 073 * Returns the value of the attribute for a concrete object. Of course, the object must be instance of the class that this attribute belongs to. 074 * @param obj Instance to obtain the attribute from 075 * @throws AttributeAccessException 076 */ 077 public Object getValue(Object obj) throws AttributeAccessException 078 { 079 Object res = null; 080 try{ 081 res = field.get(obj); 082 return res; 083 }catch(Exception e) 084 {} 085 086 try{ 087 java.beans.PropertyDescriptor pd = new java.beans.PropertyDescriptor(field.getName(),field.getDeclaringClass()); 088 res = pd.getReadMethod().invoke(obj, (Object[])null); 089 return res; 090 }catch(Exception e) 091 {} 092 throw new AttributeAccessException("Error getting value from object: "+obj+", attribute: "+field.getName()); 093 094 } 095 096 /** 097 * Sets the value of the attribute in a concrete object. 098 * @param obj Object that defines the attribute to set. 099 * @param value Value to set. 100 * @throws AttributeAccessException 101 */ 102 public void setValue(Object obj, Object value) throws AttributeAccessException 103 { 104 try{ 105 field.set(obj, value); 106 }catch(Exception e) 107 {} 108 109 try{ 110 java.beans.PropertyDescriptor pd = new java.beans.PropertyDescriptor(field.getName(),field.getDeclaringClass()); 111 Object[] args = {value}; 112 pd.getWriteMethod().invoke(obj, args); 113 }catch(Exception e) 114 { 115 throw new AttributeAccessException("Error setting value from object: "+obj+", attribute: "+field.getName()); 116 } 117 118 } 119 120 /** 121 * Returns the hashCode of the attribute. 122 */ 123 public int hashCode() 124 { 125 return field.getName().hashCode(); 126 } 127 128 129 public boolean equals(Object o) 130 { 131 if(! (o instanceof Attribute)) 132 return false; 133 return (field.getName().equals(((Attribute)o).getName())) 134 &&(field.getDeclaringClass().equals(((Attribute)o).getDeclaringClass())); 135 } 136 137 138 }