KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > springframework > core > Constants


1 /*
2  * Copyright 2002-2006 the original author or authors.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */

16
17 package org.springframework.core;
18
19 import java.lang.reflect.Field JavaDoc;
20 import java.util.HashMap JavaDoc;
21 import java.util.HashSet JavaDoc;
22 import java.util.Iterator JavaDoc;
23 import java.util.Map JavaDoc;
24 import java.util.Set JavaDoc;
25
26 import org.springframework.util.Assert;
27 import org.springframework.util.ReflectionUtils;
28 import org.springframework.util.StringUtils;
29
30 /**
31  * This class can be used to parse other classes containing constant definitions
32  * in public static final members. The <code>asXXXX</code> methods of this class
33  * allow these constant values to be accessed via their string names.
34  *
35  * <p>Consider class Foo containing <code>public final static int CONSTANT1 = 66;</code>
36  * An instance of this class wrapping <code>Foo.class</code> will return the constant value
37  * of 66 from its <code>asNumber</code> method given the argument <code>"CONSTANT1"</code>.
38  *
39  * <p>This class is ideal for use in PropertyEditors, enabling them to
40  * recognize the same names as the constants themselves, and freeing them
41  * from maintaining their own mapping.
42  *
43  * @author Rod Johnson
44  * @author Juergen Hoeller
45  * @since 16.03.2003
46  */

47 public class Constants {
48
49     private final String JavaDoc className;
50
51     /** Map from String field name to object value */
52     private final Map JavaDoc fieldCache = new HashMap JavaDoc();
53
54
55     /**
56      * Create a new Constants converter class wrapping the given class.
57      * <p>
58      * All <b>public</b> static final variables will be exposed, whatever their type.
59      * @param clazz the class to analyze
60      * @throws IllegalArgumentException if the supplied <code>clazz</code> is <code>null</code>
61      */

62     public Constants(Class JavaDoc clazz) {
63         Assert.notNull(clazz);
64         this.className = clazz.getName();
65         Field JavaDoc[] fields = clazz.getFields();
66         for (int i = 0; i < fields.length; i++) {
67             Field JavaDoc field = fields[i];
68             if (ReflectionUtils.isPublicStaticFinal(field)) {
69                 String JavaDoc name = field.getName();
70                 try {
71                     Object JavaDoc value = field.get(null);
72                     this.fieldCache.put(name, value);
73                 }
74                 catch (IllegalAccessException JavaDoc ex) {
75                     // just leave this field and continue
76
}
77             }
78         }
79     }
80
81     /**
82      * Return the name of the analyzed class.
83      */

84     public final String JavaDoc getClassName() {
85         return className;
86     }
87
88     /**
89      * Return the number of constants exposed.
90      */

91     public final int getSize() {
92         return this.fieldCache.size();
93     }
94
95     /**
96      * Exposes the field cache to subclasses:
97      * a Map from String field name to object value.
98      */

99     protected final Map JavaDoc getFieldCache() {
100         return fieldCache;
101     }
102
103
104     /**
105      * Return a constant value cast to a Number.
106      * @param code name of the field
107      * @return long value if successful
108      * @see #asObject
109      * @throws ConstantException if the field name wasn't found
110      * or if the type wasn't compatible with Number
111      */

112     public Number JavaDoc asNumber(String JavaDoc code) throws ConstantException {
113         Object JavaDoc obj = asObject(code);
114         if (!(obj instanceof Number JavaDoc)) {
115             throw new ConstantException(this.className, code, "not a Number");
116         }
117         return (Number JavaDoc) obj;
118     }
119
120     /**
121      * Return a constant value as a String.
122      * @param code name of the field
123      * @return String string value if successful.
124      * Works even if it's not a string (invokes toString()).
125      * @see #asObject
126      * @throws ConstantException if the field name wasn't found
127      */

128     public String JavaDoc asString(String JavaDoc code) throws ConstantException {
129         return asObject(code).toString();
130     }
131
132     /**
133      * Parse the given string (upper or lower case accepted) and return
134      * the appropriate value if it's the name of a constant field in the
135      * class we're analysing.
136      * @throws ConstantException if there's no such field
137      */

138     public Object JavaDoc asObject(String JavaDoc code) throws ConstantException {
139         String JavaDoc codeToUse = code.toUpperCase();
140         Object JavaDoc val = this.fieldCache.get(codeToUse);
141         if (val == null) {
142             throw new ConstantException(this.className, codeToUse, "not found");
143         }
144         return val;
145     }
146
147     /**
148      * Return all values of the given group of constants.
149      * <p>
150      * Please note that this method assumes that constants are named
151      * in accordance with the standard Java convention for constant
152      * values (i.e. all uppercase). The supplied <code>namePrefix</code>
153      * will be uppercased (in a locale-insensitive fashion) prior to
154      * the main logic of this method kicking in.
155      *
156      * @param namePrefix prefix of the constant names to search (may be <code>null</code>)
157      * @return the set of values
158      */

159     public Set JavaDoc getValues(String JavaDoc namePrefix) {
160         String JavaDoc prefixToUse = StringUtils.hasText(namePrefix)
161                 ? namePrefix.trim().toUpperCase() : "";
162         Set JavaDoc values = new HashSet JavaDoc();
163         for (Iterator JavaDoc it = this.fieldCache.keySet().iterator(); it.hasNext();) {
164             String JavaDoc code = (String JavaDoc) it.next();
165             if (code.startsWith(prefixToUse)) {
166                 values.add(this.fieldCache.get(code));
167             }
168         }
169         return values;
170     }
171
172     /**
173      * Return all values of the group of constants for the
174      * given bean property name.
175      * @param propertyName the name of the bean property
176      * @return the set of values
177      * @see #propertyToConstantNamePrefix
178      */

179     public Set JavaDoc getValuesForProperty(String JavaDoc propertyName) {
180         return getValues(propertyToConstantNamePrefix(propertyName));
181     }
182
183     /**
184      * Look up the given value within the given group of constants.
185      * Will return the first match.
186      * @param value constant value to look up
187      * @param namePrefix prefix of the constant names to search
188      * @return the name of the constant field
189      * @throws ConstantException if the value wasn't found
190      */

191     public String JavaDoc toCode(Object JavaDoc value, String JavaDoc namePrefix) throws ConstantException {
192         String JavaDoc prefixToUse = namePrefix.toUpperCase();
193         for (Iterator JavaDoc it = this.fieldCache.entrySet().iterator(); it.hasNext();) {
194             Map.Entry JavaDoc entry = (Map.Entry JavaDoc) it.next();
195             String JavaDoc key = (String JavaDoc) entry.getKey();
196             if (key.startsWith(prefixToUse) && entry.getValue().equals(value)) {
197                 return key;
198             }
199         }
200         throw new ConstantException(this.className, prefixToUse, value);
201     }
202
203     /**
204      * Look up the given value within the group of constants for
205      * the given bean property name. Will return the first match.
206      * @param value constant value to look up
207      * @param propertyName the name of the bean property
208      * @return the name of the constant field
209      * @throws ConstantException if the value wasn't found
210      * @see #propertyToConstantNamePrefix
211      */

212     public String JavaDoc toCodeForProperty(Object JavaDoc value, String JavaDoc propertyName) throws ConstantException {
213         return toCode(value, propertyToConstantNamePrefix(propertyName));
214     }
215
216     /**
217      * Convert the given bean property name to a constant name prefix.
218      * Uses a common naming idiom: turning all lower case characters to
219      * upper case, and prepending upper case characters with an underscore.
220      * <p>Example: "imageSize" -> "IMAGE_SIZE"<br>
221      * Example: "imagesize" -> "IMAGESIZE".<br>
222      * Example: "ImageSize" -> "_IMAGE_SIZE".<br>
223      * Example: "IMAGESIZE" -> "_I_M_A_G_E_S_I_Z_E"
224      * @param propertyName the name of the bean property
225      * @return the corresponding constant name prefix
226      * @see #getValuesForProperty
227      * @see #toCodeForProperty
228      */

229     public String JavaDoc propertyToConstantNamePrefix(String JavaDoc propertyName) {
230       StringBuffer JavaDoc parsedPrefix = new StringBuffer JavaDoc();
231       for(int i = 0; i < propertyName.length(); i++) {
232         char c = propertyName.charAt(i);
233         if (Character.isUpperCase(c)) {
234           parsedPrefix.append("_");
235           parsedPrefix.append(c);
236         }
237         else {
238           parsedPrefix.append(Character.toUpperCase(c));
239         }
240       }
241         return parsedPrefix.toString();
242     }
243
244 }
245
Popular Tags