Home | History | Annotate | Download | only in beans
      1 /*
      2  *  Licensed to the Apache Software Foundation (ASF) under one or more
      3  *  contributor license agreements.  See the NOTICE file distributed with
      4  *  this work for additional information regarding copyright ownership.
      5  *  The ASF licenses this file to You under the Apache License, Version 2.0
      6  *  (the "License"); you may not use this file except in compliance with
      7  *  the License.  You may obtain a copy of the License at
      8  *
      9  *     http://www.apache.org/licenses/LICENSE-2.0
     10  *
     11  *  Unless required by applicable law or agreed to in writing, software
     12  *  distributed under the License is distributed on an "AS IS" BASIS,
     13  *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     14  *  See the License for the specific language governing permissions and
     15  *  limitations under the License.
     16  */
     17 
     18 package java.beans;
     19 
     20 import java.lang.reflect.Method;
     21 import java.lang.reflect.Modifier;
     22 import org.apache.harmony.beans.internal.nls.Messages;
     23 
     24 public class IndexedPropertyDescriptor extends PropertyDescriptor {
     25     private Method indexedGetter;
     26 
     27     private Method indexedSetter;
     28 
     29     public IndexedPropertyDescriptor(String propertyName, Class<?> beanClass,
     30             String getterName, String setterName, String indexedGetterName,
     31             String indexedSetterName) throws IntrospectionException {
     32         super(propertyName, beanClass, getterName, setterName);
     33 
     34         // RI behaves like this
     35         if (indexedGetterName == null && indexedSetterName == null &&
     36                 (getterName != null || setterName != null)) {
     37             throw new IntrospectionException(Messages.getString("beans.50"));
     38         }
     39         setIndexedReadMethod(beanClass, indexedGetterName);
     40         setIndexedWriteMethod(beanClass, indexedSetterName);
     41     }
     42 
     43     public IndexedPropertyDescriptor(String propertyName, Method getter, Method setter,
     44             Method indexedGetter, Method indexedSetter) throws IntrospectionException {
     45         super(propertyName, getter, setter);
     46 
     47         // we need this in order to be compatible with RI
     48         if (indexedGetter == null && indexedSetter == null &&
     49                 (getter != null || setter != null)) {
     50             throw new IntrospectionException(Messages.getString("beans.50"));
     51         }
     52         setIndexedReadMethod(indexedGetter);
     53         setIndexedWriteMethod(indexedSetter);
     54     }
     55 
     56     public IndexedPropertyDescriptor(String propertyName, Class<?> beanClass)
     57             throws IntrospectionException {
     58         super(propertyName, beanClass, null, null);
     59         String getterName;
     60         String setterName;
     61         String indexedGetterName;
     62         String indexedSetterName;
     63 
     64         // array getter
     65         getterName = createDefaultMethodName(propertyName, "get"); //$NON-NLS-1$
     66         if (hasMethod(beanClass, getterName)) {
     67             setReadMethod(beanClass, getterName);
     68         }
     69         // array setter
     70         setterName = createDefaultMethodName(propertyName, "set"); //$NON-NLS-1$
     71         if (hasMethod(beanClass, setterName)) {
     72             setWriteMethod(beanClass, setterName);
     73         }
     74         // indexed getter
     75         indexedGetterName = createDefaultMethodName(propertyName, "get"); //$NON-NLS-1$
     76         if (hasMethod(beanClass, indexedGetterName)) {
     77             setIndexedReadMethod(beanClass, indexedGetterName);
     78         }
     79         // indexed setter
     80         indexedSetterName = createDefaultMethodName(propertyName, "set"); //$NON-NLS-1$
     81         if (hasMethod(beanClass, indexedSetterName)) {
     82             setIndexedWriteMethod(beanClass, indexedSetterName);
     83         }
     84         // RI seems to behave a bit differently
     85         if (indexedGetter == null && indexedSetter == null &&
     86                 getReadMethod() == null && getWriteMethod() == null) {
     87             throw new IntrospectionException(
     88                     Messages.getString("beans.01", propertyName)); //$NON-NLS-1$
     89         }
     90         if (indexedGetter == null && indexedSetter == null) {
     91             // not an indexed property indeed
     92             throw new IntrospectionException(Messages.getString("beans.50"));
     93         }
     94     }
     95 
     96     public void setIndexedReadMethod(Method indexedGetter) throws IntrospectionException {
     97         if (indexedGetter != null) {
     98             int modifiers = indexedGetter.getModifiers();
     99             Class<?>[] parameterTypes;
    100             Class<?> returnType;
    101             Class<?> indexedPropertyType;
    102 
    103             if (!Modifier.isPublic(modifiers)) {
    104                 throw new IntrospectionException(Messages.getString("beans.21")); //$NON-NLS-1$
    105             }
    106             parameterTypes = indexedGetter.getParameterTypes();
    107             if (parameterTypes.length != 1) {
    108                 throw new IntrospectionException(Messages.getString("beans.22")); //$NON-NLS-1$
    109             }
    110             if (!parameterTypes[0].equals(int.class)) {
    111                 throw new IntrospectionException(Messages.getString("beans.23")); //$NON-NLS-1$
    112             }
    113             returnType = indexedGetter.getReturnType();
    114             indexedPropertyType = getIndexedPropertyType();
    115             if ((indexedPropertyType != null) && !returnType.equals(indexedPropertyType)) {
    116                 throw new IntrospectionException(Messages.getString("beans.24")); //$NON-NLS-1$
    117             }
    118         }
    119         this.indexedGetter = indexedGetter;
    120     }
    121 
    122     public void setIndexedWriteMethod(Method indexedSetter) throws IntrospectionException {
    123         if (indexedSetter != null) {
    124             int modifiers = indexedSetter.getModifiers();
    125             Class<?>[] parameterTypes;
    126             Class<?> firstParameterType;
    127             Class<?> secondParameterType;
    128             Class<?> propType;
    129 
    130             if (!Modifier.isPublic(modifiers)) {
    131                 throw new IntrospectionException(Messages.getString("beans.25")); //$NON-NLS-1$
    132             }
    133             parameterTypes = indexedSetter.getParameterTypes();
    134             if (parameterTypes.length != 2) {
    135                 throw new IntrospectionException(Messages.getString("beans.26")); //$NON-NLS-1$
    136             }
    137             firstParameterType = parameterTypes[0];
    138             if (!firstParameterType.equals(int.class)) {
    139                 throw new IntrospectionException(Messages.getString("beans.27")); //$NON-NLS-1$
    140             }
    141             secondParameterType = parameterTypes[1];
    142             propType = getIndexedPropertyType();
    143             if (propType != null && !secondParameterType.equals(propType)) {
    144                 throw new IntrospectionException(Messages.getString("beans.28")); //$NON-NLS-1$
    145             }
    146         }
    147         this.indexedSetter = indexedSetter;
    148     }
    149 
    150     public Method getIndexedWriteMethod() {
    151         return indexedSetter;
    152     }
    153 
    154     public Method getIndexedReadMethod() {
    155         return indexedGetter;
    156     }
    157 
    158     @Override
    159     public boolean equals(Object obj) {
    160         boolean result = super.equals(obj);
    161 
    162         if (result) {
    163             IndexedPropertyDescriptor pd = (IndexedPropertyDescriptor) obj;
    164 
    165             if (indexedGetter != null) {
    166                 result = indexedGetter.equals(pd.getIndexedReadMethod());
    167             } else if (result && indexedGetter == null) {
    168                 result = pd.getIndexedReadMethod() == null;
    169             }
    170 
    171             if (result) {
    172                 if (indexedSetter != null) {
    173                     result = indexedSetter.equals(pd.getIndexedWriteMethod());
    174                 } else if (indexedSetter == null) {
    175                     result = pd.getIndexedWriteMethod() == null;
    176                 }
    177             }
    178         }
    179 
    180         return result;
    181     }
    182 
    183     public Class<?> getIndexedPropertyType() {
    184         Class<?> result = null;
    185 
    186         if (indexedGetter != null) {
    187             result = indexedGetter.getReturnType();
    188         } else if (indexedSetter != null) {
    189             Class<?>[] parameterTypes = indexedSetter.getParameterTypes();
    190 
    191             result = parameterTypes[1];
    192         }
    193         return result;
    194     }
    195 
    196     private void setIndexedReadMethod(Class<?> beanClass, String indexedGetterName) {
    197         Method[] getters = findMethods(beanClass, indexedGetterName);
    198         boolean result = false;
    199 
    200         for (Method element : getters) {
    201             try {
    202                 setIndexedReadMethod(element);
    203                 result = true;
    204             } catch (IntrospectionException ie) {}
    205 
    206             if (result) {
    207                 break;
    208             }
    209         }
    210     }
    211 
    212     private void setIndexedWriteMethod(Class<?> beanClass, String indexedSetterName) {
    213         Method[] setters = findMethods(beanClass, indexedSetterName);
    214         boolean result = false;
    215 
    216         for (Method element : setters) {
    217             try {
    218                 setIndexedWriteMethod(element);
    219                 result = true;
    220             } catch (IntrospectionException ie) {}
    221 
    222             if (result) {
    223                 break;
    224             }
    225         }
    226     }
    227 }
    228