View Javadoc
1   package org.apache.commons.beanutils2;
2   
3   /*
4    * Licensed to the Apache Software Foundation (ASF) under one
5    * or more contributor license agreements.  See the NOTICE file
6    * distributed with this work for additional information
7    * regarding copyright ownership.  The ASF licenses this file
8    * to you under the Apache License, Version 2.0 (the
9    * "License"); you may not use this file except in compliance
10   * with the License.  You may obtain a copy of the License at
11   *
12   *   http://www.apache.org/licenses/LICENSE-2.0
13   *
14   * Unless required by applicable law or agreed to in writing,
15   * software distributed under the License is distributed on an
16   * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
17   * KIND, either express or implied.  See the License for the
18   * specific language governing permissions and limitations
19   * under the License.
20   */
21  
22  import java.util.Map;
23  
24  /**
25   * Provides access to properties and methods of a bean.
26   *
27   * @param <B> the type of the bean this BeanAcessor is associated with.
28   */
29  public interface BeanAccessor<B>
30  {
31  
32      // get
33  
34      /**
35       * Gets the value of the property with name {@code propertyName} from the bean wrapped by this BeanAccessor. The
36       * value will be wrapped in a {@code BeanAccessor} to enable fluent calls.
37       *
38       * @param propertyName the name of the property to get the value from. Must not be {@code null}!
39       * @return a {@code BeanAccessor} wrapping the properties value.
40       */
41      BeanAccessor<?> get( String propertyName );
42  
43      /**
44       * Selects the indexed property with name {@code propertyName} from the bean wrapped by this {@code BeanAccessor}. A
45       * {@link IndexedPropertyGetterAccessor} will be returned for specifying the index to return the value of.
46       *
47       * @param propertyName the name of the indexed property to select. Must not be {@code null}!
48       * @return a {@link IndexedPropertyGetterAccessor} for specifying the index to return the value of.
49       */
50      IndexedPropertyGetterAccessor<?> getIndexed( String propertyName );
51  
52      /**
53       * Selects the mapped property with name {@code propertyName} from the bean wrapped by this {@code BeanAccessor}. A
54       * {@link MappedPropertyGetterAccessor} will be returned for specifying the key to return the value of.
55       *
56       * @param propertyName the name of the mapped property to select. Must not be {@code null}!
57       * @return a {@link MappedPropertyGetterAccessor} for specifying the key to return the value of.
58       */
59      MappedPropertyGetterAccessor getMapped( String propertyName );
60  
61      /**
62       * Gets the bean wrapped by this {@code BeanAccessor}.
63       *
64       * @return the bean.
65       */
66      B get();
67  
68      /**
69       * Tries to cast the bean wrapped by this {@code BeanAccessor} an returns the result.
70       *
71       * @param <V> the type to cast the wrapped bean to.
72       * @return the wrapped bean, casted to type {@code V}.
73       */
74      <V> V cast();
75  
76      // set
77  
78      /**
79       * Selects the property with name {@code propertyName} for setting a new value. A {@link BeanPropertySetter} will be
80       * returned for specifying the new value.
81       *
82       * @param propertyName the name of the property to select for setting a new value. Must not be {@code null}.
83       * @return a {@link BeanPropertySetter} for setting a new value.
84       */
85      BeanPropertySetter<B> set( String propertyName );
86  
87      /**
88       * Selects the indexed property with name {@code propertyName} for setting a new value. A
89       * {@link IndexedPropertySetterAccessor} will be returned for specifying the index to set a new value to.
90       *
91       * @param propertyName the name of the indexed property to select for setting a new value. Must not be {@code null}.
92       * @return a {@link IndexedPropertySetterAccessor} for setting a new value.
93       */
94      IndexedPropertySetterAccessor<B> setIndexed( String propertyName );
95  
96      /**
97       * Selects the mapped property with name {@code propertyName} for setting a new value. A
98       * {@link MappedPropertySetterAccessor} will be returned for specifying the key to set a new value to.
99       *
100      * @param propertyName the name of the mapped property to select for setting a new value. Must not be {@code null}.
101      * @return a {@link MappedPropertySetterAccessor} for setting a new value.
102      */
103     MappedPropertySetterAccessor<B> setMapped( String propertyName );
104 
105     // clone
106 
107     /**
108      * Clones a bean based on the available property getters and setters, even if the bean class itself does not
109      * implement Cloneable.
110      * <p>
111      * <strong>Note:</strong> this method creates a <strong>shallow</strong> clone. In other words, any objects referred
112      * to by the bean are shared with the clone rather than being cloned in turn.
113      *
114      * @return the cloned bean
115      */
116     B cloneBean();
117 
118     /**
119      * Copies property values from the bean wrapped by this {@code BeanAccessor} to {@code target} for all cases where
120      * the property names are the same. For each property, a conversion is attempted as necessary.
121      * <p>
122      * <strong>Note</strong> that this method is intended to perform a "shallow copy" of the properties and so complex
123      * properties (for example, nested ones) will not be copied.
124      * <p>
125      * <strong>TODO</strong> should we implement something like the following?
126      * <p>
127      * If you know that no type conversions are required, the <code>copyProperties()</code> method in
128      * {@link PropertyUtils} will execute faster than this method.
129      * <p>
130      * <strong>FIXME</strong> - Indexed and mapped properties that do not have getter and setter methods for the
131      * underlying array or Map are not copied by this method.
132      *
133      * @param <T> the type of the bean to copy properties to.
134      * @param target the target to copy properties to from the wrapped bean
135      */
136     <T extends B> void copyPropertiesTo( T target );
137 
138     // description
139 
140     /**
141      * Return the entire set of properties for which the specified bean provides a read method. This map contains the
142      * property names as keys and the property values as values, for all properties the bean provides a read method for
143      * (i.e. where the getReadMethod() returns non-null).
144      * <p>
145      * This map can be fed back to a call to <code>BeanAccessor.populate()</code> to reconstitute the same set of
146      * properties, modulo differences for read-only and write-only properties, but only if there are no indexed
147      * properties.
148      * <p>
149      * <strong>Warning:</strong> if any of the bean property implementations contain (directly or indirectly) a call to
150      * this method then a stack overflow may result. For example: <code><pre>
151      * class MyBean
152      * {
153      *    public Map&lt;String, Object&gt; getParameterMap()
154      *    {
155      *         on( this ).describe;
156      *    }
157      * }
158      * </pre></code> will result in an infinite regression when <code>getParametersMap</code> is called. It is
159      * recommended that such methods are given alternative names (for example, <code>parametersMap</code>).
160      *
161      * @return Map that contains the property names as keys and property values as values.
162      */
163     Map<String, Object> describe();
164 
165     /**
166      * Populate {@code properties} to the bean wrapped by this {@code BeanAccessor}. The map of properties passed to
167      * this method has to specify names of properties to set and corresponding values as key-value-pairs.
168      *
169      * @param properties Map keyed by property name, with the corresponding value to be set.
170      *            Must not be {@code null}.
171      */
172     void populate( Map<String, Object> properties );
173 
174     // methods invocation
175 
176     /**
177      * Invokes the method with name {@code methodName}. An {@link ArgumentsAccessor} will be returned to specify the
178      * parameters for the method invocation.
179      *
180      * @param methodName the name of the method to invoke. Must not be {@code null}!
181      * @return an {@link ArgumentsAccessor} to specify arguments for the method invocation.
182      */
183     ArgumentsAccessor invoke( String methodName );
184 
185     /**
186      * Invokes the method with name {@code methodName} and the exact arguments. An {@link ArgumentsAccessor} will be
187      * returned to specify the parameters for the method invocation.
188      *
189      * @param methodName the name of the method to invoke. Must not be {@code null}!
190      * @return a {@link ArgumentsAccessor} to specify any arguments
191      */
192     ArgumentsAccessor invokeExact( String methodName );
193 
194 }